简体   繁体   中英

C++ Template to Sort Vector of Objects by Attribute

I have some working code which is based off of this: Sorting a vector of objects by a property of the object

And I re-worded it and took out a lot of un-necessary things to make it easier for me to understand. I still can't tell exactly what the code is doing, can someone please comment this code or walk me through it step by step to explain what is happening here? I'm mostly confused about the top stuff about the template.

#import <iostream>
#include <algorithm>
#include <vector>
#include <string>
#include <functional>

using namespace std;


//Can someone please explain this template stuff???
template < typename TYPE, typename MTYPE>
struct member_comparer {

    MTYPE TYPE::*val;

    explicit member_comparer( MTYPE TYPE::*p ) { 
        val = p;
    }

    bool operator ()( TYPE  lhs, TYPE  rhs )  {
        return lhs.*val < rhs.*val;
    }
};



template<typename TYPE, typename MTYPE>
member_comparer<TYPE, MTYPE> make_member_comparer( MTYPE TYPE::*p ) {
    return member_comparer<TYPE, MTYPE>( p );
}

//PLEASE EXPLAIN THE STUFF ABOVE HERE ^





struct Number
{
    //declare our strings
    int i;
    string s;

    //preset the values in the constructor!
    Number( int i, string s ) { 
        this->i = i;
        this->s = s;
    }
};



int main()
{   

    //declare a new vector of Numbers
    vector<Number> vec;

    //fill in the vector
    vec.push_back(Number(2, "two"));
    vec.push_back(Number(8, "eight"));


    // sort by i, ascending
    sort( vec.begin(), vec.end(), make_member_comparer( &Number::i ) );
    cout << vec.front().i << ", " << vec.back().i << "\n";
    //outputs 2, 8


    // sort by s, ascending
    sort( vec.begin(), vec.end(), make_member_comparer( &Number::s ) );
    cout << vec.front().s << ", " << vec.back().s << "\n";
    //outputs eight, two
}
template < typename TYPE, typename MTYPE>
struct member_comparer {

MTYPE TYPE::*val;     // public field, a pointer to MTYPE

explicit member_comparer( MTYPE TYPE::*p ) {   // explicit constructor
    val = p;
}

bool operator ()( TYPE  lhs, TYPE  rhs )  {  // operator () (TYPE lhs, TYPE rhs)
                                            // this is typical for a functor
    return lhs.*val < rhs.*val;
}
};


template<typename TYPE, typename MTYPE>
member_comparer<TYPE, MTYPE> make_member_comparer( MTYPE TYPE::*p ) {
    return member_comparer<TYPE, MTYPE>( p );      // return an instance of the functor 
}

MTYPE TYPE::*val; is a pointer on member from class TYPE . The member is of type MTYPE .

template <typename TYPE, typename MTYPE> struct it is a struct parametrised by two type. TYPE which should be the class, MTYPE which should be the type of the member.

template<typename TYPE, typename MTYPE>
member_comparer<TYPE, MTYPE> make_member_comparer( MTYPE TYPE::*p ) {
    return member_comparer<TYPE, MTYPE>( p );
}

make_member_comparer is a helper function to avoid to use:

member_comparer<Number, int>(&Number::i)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM