如何对具有两个变量的向量进行排序

How to sort a vector with two variables?

本文关键字:变量 两个 向量 排序      更新时间:2023-10-16

这可能是个小问题,但这是我的问题;我有一个类Card,它有两个不同的int值,看起来像这样。

#pragma once
class Card
{
public:
int value;
int suite;
Card(int v, int s);
~Card(void);
void printCard();
int getScore();
};

现在我想根据它们的价值对5张卡片进行具体排序。我试着把它们放入一个向量中,然后使用std::sort,但我无法让它发挥作用。所以我的问题是,最好的方法是什么?

您需要重载operator<:

bool operator<(const Card& lhs, const Card& rhs){
.... logic here ... 
}

然后使用std::sort。你可能需要让这个操作员成为你班的朋友。或者,在类定义中,您可以实现:

class Card {
 ....
 public:
  bool operator<(const Card& other) const {
  .... logic here...
  }
}; // end of class Card

使用std::sort有两个选项。一种是为您的类重载operator <

bool operator< (const Card &lhs, const Card &rhs) {
  return lhs.value < rhs.value;
}

但是,只有当总是像这样比较Card对象确实有意义时,才可以这样做。如果您只需要在特定的排序中使用此选项,则可以使用接受自定义比较器的sort版本。

有多种方法可以定义谓词。对于可重用但简单的标准,可以使用类中的静态函数:

class Card
{
public:
  // ... as before
  static bool lesserValue(const Card &lhs, const Card &rhs) {
    return lhs.value < rhs.value;
  }
};

用法:

std::sort(from, to, &Card::lesserValue);

对于一次性的东西(或者对于需要保持内部状态的复杂标准),使用从std::binary_function派生的类,并在其operator()中实现可编译逻辑。在C++11中,您也可以使用lambda函数来实现这一点:

std::sort(from, to, [](const Card &lhs, const Card &rhs) { return lhs.value < rhs.value; });

我给出了这个答案,它使用了比较类,这也使得比较套件变得非常容易。我还改进了你们班的公共和私人成员,因为有些价值观不应该是公共的。并且您的类当前不需要析构函数。

#include<iostream> 
#include<algorithm> 
#include<vector> 
class Card {
    public:
        Card(int v, int s)
            :
                value(v),
                suite(s)
        {
        }
        /*No need for destructor*/
        int getValue(void) const { return value;}
        int getSuite(void) const { return suite;}
        void printCard(void) const {
            std::cout << "Value = " << value << "tSuite = " << suite << std::endl;
        }
    private:
        /*these shouldn't be public*/
        int value;
        int suite;
};
class CompareCardValue {
    public:
        bool operator() ( const Card& c1, const Card& c2)
        {
            return c1.getValue() < c2.getValue();
        }
};
class CompareCardSuite{
    public:
        bool operator() ( const Card& c1, const Card& c2)
        {
            return c1.getSuite() < c2.getSuite();
        }
};
int main( ){
    std::vector<Card> deck;
    deck.push_back( Card(2,4) );
    deck.push_back( Card(1,3) );
    deck.push_back( Card(12,3) );
    deck.push_back( Card(8,2) );
    CompareCardSuite comp_suite; //compares for suite
    CompareCardValue comp_value; //compares for value
    /*We would like to use a const iterator since we are
     *not interested in changing the Card intances
     */
    std::vector<Card>::const_iterator it;
    for ( it = deck.begin(); it < deck.end(); it++){
        it->printCard();
    }
    std::cout << std::endl;
    /*sorting on value*/
    std::sort( deck.begin(), deck.end(), comp_value );
    for ( it = deck.begin(); it < deck.end(); it++){
        it->printCard();
    }
    std::cout << std::endl;
    /*sorting on suite*/
    std::sort( deck.begin(), deck.end(), comp_suite );
    for ( it = deck.begin(); it < deck.end(); it++){
        it->printCard();
    }
}