Operador <e estrito pedido fraco

Como definir o operator< em n-tupla (por exemplo, em 3-tupla) para que satisfaça o conceito de ordenação fraca estrita ? Eu sei que a biblioteca boost tem class tuple com operator< definido corretamente operator< mas por alguns motivos eu não posso usá-la.

 if (a1 < b1) return true; if (b1 < a1) return false; // a1==b1: continue with element 2 if (a2 < b2) return true; if (b2 < a2) return false; // a2 == b2: continue with element 3 if (a3 < b3) return true; return false; // early out 

Isso ordena que os elementos de a1 sejam os mais significativos e a3 menos significativos.

Isto pode ser continuado ad infinitum, você também pode, por exemplo, aplicá-lo a um vetor de T, iterando sobre comparações de um [i]

 while (i 

Naturalmente, se a comparação for cara, talvez você queira armazenar em cache o resultado da comparação.


[edit] removeu o código errado

ordem fraca estrita

Este é um termo matemático para definir um relacionamento entre dois objects.
Sua definição é:

Dois objects x e y são equivalentes se ambos f (x, y) e f (y, x) são falsos. Note que um object é sempre (pela irreflexividade invariante) equivalente a si mesmo.

Em termos de C ++, isso significa que, se você tiver dois objects de um determinado tipo, deverá retornar os seguintes valores quando comparado com o operador <.

 X a; X b; Condition: Test: Result a is equivalent to b: a < b false a is equivalent to bb < a false a is less than ba < b true a is less than bb < a false b is less than aa < b false b is less than ab < a true 

Como você define o equivalente / menos é totalmente dependente do tipo do seu object.

Verifique a página da SGI sobre o assunto:
http://www.sgi.com/tech/stl/StrictWeakOrdering.html

… uma nova resposta para uma pergunta muito antiga, mas a resposta existente erra a solução fácil do C ++ 11 …

Solução C ++ 11

C ++ 11 em diante fornece std::tuple , que você pode usar para armazenar seus dados. tuple têm um operator< correspondência operator< que inicialmente compara o elemento mais à esquerda e, em seguida, trabalha ao longo da tupla até que o resultado seja limpo. Isso é adequado para fornecer o ordenamento estrito esperado por, por exemplo, std::set e std::map .

Se você tem dados em algumas outras variables ​​(por exemplo, campos em uma struct ), você pode até usar std::tie() para criar uma tupla de referências , que pode ser comparada a outra tupla. Isso torna mais fácil escrever o operator< para campos de dados de membros específicos em um tipo de class / struct definida pelo usuário:

 struct My_Struct { int a_; double b_; std::string c_; }; bool operator<(const My_Struct& lhs, const My_Struct& rhs) { return std::tie(lhs.a_, lhs.b_, lhs.c_) < std::tie(rhs.a_, rhs.b_, rhs.c_); } 

Você poderia simplesmente usar vetores de três elementos, que já terão o operador <() adequadamente definido. Isso tem a vantagem de se estender aos elementos-N sem que você precise fazer nada.

O stream básico deve estar ao longo das linhas: se os elementos Kth forem diferentes, retorne o que é menor senão vá para o próximo elemento . O código a seguir assume que você não tem uma tupla de reforço, caso contrário você usaria get(tuple) e não teria o problema para começar.

 if (lhs.first != rhs.first) return lhs.first < rhs.first; if (lhs.second != rhs.second) return lhs.second< rhs.second; return lhs.third < rhs.third; 

Mesmo se você não puder usar a versão do boost, você deve ser capaz de digitar o código. Eu cortei isso de std :: pair – um 3 tuple será semelhante, eu acho.

 return (_Left.first < _Right.first || !(_Right.first < _Left.first) && _Left.second < _Right.second); 

Edit: Como um par de pessoas têm apontado, se você roubar o código da biblioteca padrão para usar em seu código, você deve renomear as coisas que têm sublinhados na frente como esses nomes são reservados.