0

What is the correct way to implement the '<' operator for using the following simple class as a key in a std::map (functions are omitted)?

class Person
{
public:
   bool valid = false;
   std::string name = "";
   std::string id = "";
}
user1056903
  • 921
  • 9
  • 26
  • not a dupe but a good reference: http://stackoverflow.com/questions/4421706/operator-overloading – NathanOliver Nov 14 '16 at 21:02
  • You havea field named `id`. Its name implies that it is unique. Is it? If so, you could make use of that fact. –  Nov 14 '16 at 21:04
  • There is no "the correct" way. It is up to you really, as long as it satisfies *strict weak ordering*. – juanchopanza Nov 14 '16 at 22:46

3 Answers3

4

You could use std::tie.

class Person
{
public:
    bool valid = false;
    std::string name = "";
    std::string id = "";

    bool operator<(const Person& r) const
    {
        return std::tie(valid, name, id) < std::tie(r.valid, r.name, r.id);
    }
}

Explanation:

std::tie(xs...) creates an std::tuple of references to the passed xs... arguments. Comparison between two std::tuple instances works by lexicographically comparing the elements, thus providing an ordering for your type.

More information here on cppsamples and in this question.

Community
  • 1
  • 1
Vittorio Romeo
  • 90,666
  • 33
  • 258
  • 416
4

You can use std::tie as suggested by the other answers. If you want to clearly see the logic in your own function or don't have access to a C++11 compiler, you can implement it as:

class Person
{
   public:
      bool valid = false;
      std::string name = "";
      std::string id = "";

      bool operator<(Person const& rhs) const
      {
         if ( this->valid != rhs.valid )
         {
            return ( this->valid < rhs.valid );
         }
         if ( this->name != rhs.name )
         {
            return ( this->name < rhs.name );
         }
         return ( this->id < rhs.id );
      }
};
R Sahu
  • 204,454
  • 14
  • 159
  • 270
2
#include <string>
#include <tuple>

class Person
{
public:
   bool valid = false;
   std::string name = "";
   std::string id = "";
};

bool operator<(const Person& l, const Person& r)
{
    return std::tie(l.valid, l.name, l.id) < std::tie(r.valid, r.name, r.id);
}
Richard Hodges
  • 68,278
  • 7
  • 90
  • 142