多种对象

时间:2015-11-09 18:04:52

标签: c++ sorting

我需要对一个对象的矢量进行排序,但不像普通的排序那样,因为我需要首先用第一个参数进行排序,然后用第二个参数进行排序,然后用第三个参数进行排序等。

例:

RandomObject.h:

class RandomObject
{
public:
    RandomObject(int firstParamater, int secondParameter, int thirdParameter);
    int firstParameter();
    int secondParameter();
    int thirdParameter();
    ~ContainerFrame();
private:
    int m_firstParameter; //These aren't constant
    int m_secondParameter;
    int m_thirdParameter;
};

RandomObject.cpp:

ContainerFrame::ContainerFrame(int firstParamater, int secondParameter, int thirdParameter) : m_firstParameter(firstParamater), m_secondParameter(secondParameter), m_thirdParameter(thirdParameter)
{

}

ContainerFrame::~ContainerFrame()
{

}

[...function that just return members int...]

现在我想按第一个参数排序,然后按第二个参数排序,然后按第三个参数排序:

RandomObject(1,1,1);
RandomObject(1,3,1);
RandomObject(2,1,5);
RandomObject(2,2,1);
RandomObject(3,1,1);
[...]

我知道要对矢量进行排序,你需要做一个:

sort (randomObjectV.begin(), randomObjectV.end(), sortFunc);

而sortFunc应该是这样的:

bool sortFunc(const RandomObject& firstObject, const RandomObject& secondObject);

但我不知道如何制作类似的程序。

提前感谢您的帮助!

1 个答案:

答案 0 :(得分:2)

你对排序的工作方式有一点误解:

sort (randomObjectV.begin(), randomObjectV.end(), comparisonFunction);

comparisonFunction比较两个相同类型的对象,并决定哪个更小。如果第一个参数是Less而不是第二个参数(对于Less的某些定义),则返回true。

所以你需要决定如何比较两个对象。

bool comparisonFunction(const RandomObject& firstObject, const RandomObject& secondObject)
{
    // Here is an example how how you can compare.
    return firstObject.firstParameter() < secondObject.firstParameter();
}

注意:因为上面函数中的参数是const,所以只能在对象上调用const版本函数。目前你还没有。但是我相信你所有的getter都是const,所以我打赌你可以添加const来使它们工作。

class RandomObject
{
public:
    int firstParameter()   const; // <- Add const here

但另类。而不是提供排序的比较方法,您可以使用默认比较方法。这基本上使用对象上的operator<来比较两个对象。您只需要为您的班级提供operator<的定义。

    sort (randomObjectV.begin(), randomObjectV.end());

    // This will use `operator<` on your object.

    class RandomObject
    {
        public:
             bool operator<(RandomObject const& rhs) const {

                 // Again just an example of how you can implement less.
                 // The current object is the lhs.
                 return m_firstParameter < rhs. m_firstParameter;
             }

有人建议您学习如何比较两个对象。这完全取决于你(只有你知道如何比较你的对象)。

但是常见的技术如下。

if (lhs.m_firstParameter < rhs.m_firstParameter) return true;
if (lhs.m_firstParameter > rhs.m_firstParameter) return false;

// Otherwise the m_firstParameter is equal (so you compare the second)
if (lhs.m_secondParameter < rhs.m_secondParameter) return true;
if (lhs.m_secondParameter > rhs.m_secondParameter) return false;

// Otherwise the m_firstParameter and m_secondParameter are equal (so you compare the third)
if (lhs.m_thirdParameter < rhs.m_thirdParameter) return true;
if (lhs.m_thirdParameter > rhs.m_thirdParameter) return false;

// Otherwise all three are equal
return false

这通常也会缩短:

return lhs.m_firstParameter < rhs.m_firstParameter ||
       (lhs.m_firstParameter == rhs.m_firstParameter && lhs.m_secondParameter < rhs.m_secondParameter) ||
       (lhs.m_firstParameter == rhs.m_firstParameter && lhs.m_secondParameter == rhs.m_secondParameter  && lhs.m_thirdParameter < rhs.m_thirdParameter);

但写起来更容易:

return std::make_tuple(lhs.m_firstParameter, lhs.m_secondParameter, lhs.m_thirdParameter) 
     < std::make_tuple(rhs.m_firstParameter, rhs.m_secondParameter, rhs.m_thirdParameter);

但写作效率更高(但含义相同)

return std::forward_as_tuple(lhs.m_firstParameter, lhs.m_secondParameter, lhs.m_thirdParameter) 
     < std::forward_as_tuple(rhs.m_firstParameter, rhs.m_secondParameter, rhs.m_thirdParameter);

这是有效的,因为std::tuple有一个预定义的operator<,它完全按照上面描述的内容进行操作(也被认为是正确有效的)。所以这应该是比较对象的默认方式。