Search code examples
c++qtsortingqtcoreqmap

Sort actual QMap by key


I have QMap<QString, MyClass*>. I need to sort it by key using natural comparison. I do:

std::map<QString, MyClass*> map = c.toStdMap();
std::sort(map.begin(), map.end(), strnatcmp1<std::pair<QString, MyClass*>>);

However, this does not even compile. And even if it did, as far as I understand, it would sort a copy of my original QMap.

Is there any way to sort my QMap by key with the function for comparison keys provided?


Solution

  • You have several appoaches that you could take:

    • Store the keys as integers after converting QString to an integer.

    • You can use the compare class for std::map as per the example:

    • You can try to use specialize this template function that QMap uses for the comparison.

    main.cpp

    #include <QMap>
    #include <QDebug>
    #include <map>
    
    
    struct str_num_compare {
      bool operator() (const QString& lhs, const QString& rhs) const
      {return lhs.toInt()<rhs.toInt();}
    };
    
    int main()
    {
        QStringList stringList{"1", "10", "11", "2", "3", "4"};
    
        QMap<int, QString> map;
        foreach (const QString &string, stringList)
            map.insert(string.toInt(), string);
        qDebug() << "Integer key approach:" << map;
    
        std::map<QString, QString, str_num_compare> std_map;
        foreach (const QString &string, stringList)
            std_map[string] = string;
        qDebug() << "QString key approach with std::map:";
        for (auto item : std_map)
            qDebug() << item.first;
    
    
        return 0;
    }
    

    main.pro

    TEMPLATE = app
    TARGET = main
    QT = core
    CONFIG += c++11
    SOURCES += main.cpp
    

    Build and Run

    qmake && make && ./main
    

    Output

    Integer key approach: QMap((1, "1")(2, "2")(3, "3")(4, "4")(10, "10")(11, "11"))
    QString key approach:
    "1"
    "2"
    "3"
    "4"
    "10"
    "11"