Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Equality in QMap - operator== doesn't get invoked?
Forum Updated to NodeBB v4.3 + New Features

Equality in QMap - operator== doesn't get invoked?

Scheduled Pinned Locked Moved Unsolved General and Desktop
qmapequalitycustom type
4 Posts 2 Posters 2.3k Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • T Offline
    T Offline
    tmladek
    wrote on 26 Jul 2016, 17:30 last edited by tmladek
    #1

    I have a custom class that I serialize into QVariant, which I then store in a QMap.
    QMap's documentation states:

    Returns true if other is equal to this map; otherwise returns false.
    Two maps are considered equal if they contain the same (key, value) pairs.
    This function requires the value type to implement operator==().

    So I assumed that the operator== of my type would be called, but when I put breakpoints into it, or debug statements, the debugger doesn't stop there, nor do the debug statements get printed out.

    edit: And this is even though I've called QMetaType::registerEqualsComparator() on my custom type.

    Any ideas? Thank you!

    K 1 Reply Last reply 26 Jul 2016, 17:35
    0
    • T tmladek
      26 Jul 2016, 17:30

      I have a custom class that I serialize into QVariant, which I then store in a QMap.
      QMap's documentation states:

      Returns true if other is equal to this map; otherwise returns false.
      Two maps are considered equal if they contain the same (key, value) pairs.
      This function requires the value type to implement operator==().

      So I assumed that the operator== of my type would be called, but when I put breakpoints into it, or debug statements, the debugger doesn't stop there, nor do the debug statements get printed out.

      edit: And this is even though I've called QMetaType::registerEqualsComparator() on my custom type.

      Any ideas? Thank you!

      K Offline
      K Offline
      kshegunov
      Moderators
      wrote on 26 Jul 2016, 17:35 last edited by
      #2

      @tmladek
      Hi,
      Here's the implementation. It should be working normally. Can you show a minimal snippet that reproduces the behavior you're experiencing?

      Kind regards.

      Read and abide by the Qt Code of Conduct

      1 Reply Last reply
      0
      • T Offline
        T Offline
        tmladek
        wrote on 26 Jul 2016, 17:50 last edited by tmladek
        #3

        Hm, it seems like it's actually in the fact that it's a QList. Anyway.

        #include <QCoreApplication>
        #include <QVariant>
        #include <QMap>
        #include <QMetaType>
        #include <QDataStream>
        #include <QDebug>
        
        struct Cat {
            QString name;
            QString color;
            bool operator==(const Cat &other) const;
        }; Q_DECLARE_METATYPE(Cat)
        
        bool Cat::operator==(const Cat &other) const {
            if (this->name != other.name) return false;
            if (this->color != other.color) return false;
            return true;
        }
        
        QDataStream &operator<<(QDataStream &out, const Cat &obj) {
            out << obj.name << obj.color;
            return out;
        }
        QDataStream &operator>>(QDataStream &in, Cat &obj) {
            in >> obj.name >> obj.color;
            return in;
        }
        
        int main(int argc, char *argv[])
        {
            qRegisterMetaType<Cat>("Cat");
            qRegisterMetaTypeStreamOperators<Cat>("Cat");
            QMetaType::registerEqualsComparator<Cat>();
        
            Cat cat_1;
            cat_1.name = "Bob";
            cat_1.color = "black";
            QList<Cat> list_1;
            list_1.append(cat_1);
            QVariant variant_1 = QVariant::fromValue(list_1);
            QMap<QString, QVariant> map_1;
            map_1.insert("cat", variant_1);
        
            Cat cat_2;
            cat_2.name = "Bob";
            cat_2.color = "black";
            QList<Cat> list_2;
            list_2.append(cat_2);
            QVariant variant_2 = QVariant::fromValue(list_2);
            QMap<QString, QVariant> map_2;
            map_2.insert("cat", variant_2);
        
            qDebug() << (list_1 == list_2) << (map_1 == map_2);
        }
        

        Outputs true false.

        K 1 Reply Last reply 26 Jul 2016, 18:09
        0
        • T tmladek
          26 Jul 2016, 17:50

          Hm, it seems like it's actually in the fact that it's a QList. Anyway.

          #include <QCoreApplication>
          #include <QVariant>
          #include <QMap>
          #include <QMetaType>
          #include <QDataStream>
          #include <QDebug>
          
          struct Cat {
              QString name;
              QString color;
              bool operator==(const Cat &other) const;
          }; Q_DECLARE_METATYPE(Cat)
          
          bool Cat::operator==(const Cat &other) const {
              if (this->name != other.name) return false;
              if (this->color != other.color) return false;
              return true;
          }
          
          QDataStream &operator<<(QDataStream &out, const Cat &obj) {
              out << obj.name << obj.color;
              return out;
          }
          QDataStream &operator>>(QDataStream &in, Cat &obj) {
              in >> obj.name >> obj.color;
              return in;
          }
          
          int main(int argc, char *argv[])
          {
              qRegisterMetaType<Cat>("Cat");
              qRegisterMetaTypeStreamOperators<Cat>("Cat");
              QMetaType::registerEqualsComparator<Cat>();
          
              Cat cat_1;
              cat_1.name = "Bob";
              cat_1.color = "black";
              QList<Cat> list_1;
              list_1.append(cat_1);
              QVariant variant_1 = QVariant::fromValue(list_1);
              QMap<QString, QVariant> map_1;
              map_1.insert("cat", variant_1);
          
              Cat cat_2;
              cat_2.name = "Bob";
              cat_2.color = "black";
              QList<Cat> list_2;
              list_2.append(cat_2);
              QVariant variant_2 = QVariant::fromValue(list_2);
              QMap<QString, QVariant> map_2;
              map_2.insert("cat", variant_2);
          
              qDebug() << (list_1 == list_2) << (map_1 == map_2);
          }
          

          Outputs true false.

          K Offline
          K Offline
          kshegunov
          Moderators
          wrote on 26 Jul 2016, 18:09 last edited by kshegunov
          #4

          @tmladek
          You are comparing QVariants that contain QList<Cat>, so you need to provide registered comparison operator for QList<Cat> (or conversions might take place), which you don't do.

          PS.
          Also, this:

          qRegisterMetaType<Cat>("Cat");
          

          should be:

          qRegisterMetaType<Cat>(); 
          

          as specifically mentioned in the documentation.

          Read and abide by the Qt Code of Conduct

          1 Reply Last reply
          1

          1/4

          26 Jul 2016, 17:30

          • Login

          • Login or register to search.
          1 out of 4
          • First post
            1/4
            Last post
          0
          • Categories
          • Recent
          • Tags
          • Popular
          • Users
          • Groups
          • Search
          • Get Qt Extensions
          • Unsolved