[SOLVED] Sorting possible on a QVector that has a struct as elements



  • I have a QVector<marker>MarkerMap();

    marker is made up of:

    @
    typedef struct
    {
    int x;
    int y;
    quint16 intensity;
    }marker;
    @

    I would like to know if it's possible to sort the vector on the intensity member

    Thanks


  • Moderators

    Yes, either implement operator< for it or pass a lambda to qSort:
    @
    typedef struct
    {
    int x;
    int y;
    quint16 intensity;
    } marker;

    //Method 1:
    bool operator<(const marker& a, const marker& b) { return a.intensity < b.intensity; }
    //and then:
    QVector<marker> foo;
    foo << marker{1,1,10} << marker{1,1,5} << marker{1,1,23};
    qSort(foo);

    //Method 2:
    QVector<marker> foo;
    foo << marker{1,1,10} << marker{1,1,5} << marker{1,1,23};
    qSort(foo.begin(), foo.end(), [](const marker& a, const marker& b) { return a.intensity < b.intensity; });
    @



  • [quote author="Chris Kawa" date="1413309934"]Yes, either implement operator< for it or pass a lambda to qSort:
    @
    typedef struct
    {
    int x;
    int y;
    quint16 intensity;
    } marker;

    //Method 1:
    bool operator<(const marker& a, const marker& b) { return a.intensity < b.intensity; }
    //and then:
    QVector<marker> foo;
    foo << marker{1,1,10} << marker{1,1,5} << marker{1,1,23};
    qSort(foo);

    //Method 2:
    QVector<marker> foo;
    foo << marker{1,1,10} << marker{1,1,5} << marker{1,1,23};
    qSort(foo.begin(), foo.end(), [](const marker& a, const marker& b) { return a.intensity < b.intensity; });
    @[/quote]

    Thanks Chris for responding.

    I'm sorry I should have mentioned that qSort is now deprecated as of Qt 5.3 which is what I am using. Can I use the above with std:sort instead of qSort.


  • Moderators

    Sure, it works the same.



  • [quote author="Chris Kawa" date="1413313734"]Sure, it works the same.[/quote]

    Hmm. OK because both "methods" did not compile.

    Method 2 yields:

    error: C3867: 'QVector<marker>::begin': function call missing argument list; use '&QVector<marker>::begin' to create a pointer to member

    My call:

    @
    qSort(MarkerMap.begin, MarkerMap.end(), [](const marker& a, const marker& b) {return a.intensity < b.intensity;});
    @


  • Moderators

    Are you sure you didn't write begin instead of begin() ?

    Anyway I correct myself: sure, it works (almost) the same.
    std::sort always takes iterators not the whole container so in first method pass begin() and end() to it instead of just the container.



  • I left the parends out of the begin call. I'm trying it with qSort. Even though deprecated qSort still works (if used right that is).

    Method 1 for some reason still wouldn't compile


  • Moderators

    @
    #include <algorithm>
    #include <QVector>

    typedef struct
    {
    int x;
    int y;
    quint16 intensity;
    } marker;

    bool operator<(const marker& a, const marker& b) { return a.intensity < b.intensity; }

    int main()
    {
    QVector<marker> foo;
    foo << marker{1,1,10} << marker{1,1,5} << marker{1,1,23};
    std::sort(foo.begin(), foo.end());
    }
    @
    Works as expected.



  • Thanks, I need to see why this will not compile:

    @
    bool operator<(const marker& a, const marker& b) { return a.intensity < b.intensity; }
    @

    yields:

    C:\Users\Default.WIN-SHC18RVLNPH\Documents\Qt Projects\G14xx Dead Pixel Test\worker.cpp:31: error: C2601: 'operator <' : local function definitions are illegal
    worker.cpp(27): this line contains a '{' which has not yet been matched

    Update:

    I moved the operator to the top of the implementation file. The error stating the def was a local def tipped me off.

    Thanks


  • Moderators

    You need to start reading the error messages ;)
    It says that you can't declare operator< function inside another function. See my example. That operator needs to be at global scope.


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.