std ::在c ++中对2D向量进行排序

时间:2014-04-02 13:52:03

标签: c++ sorting stdvector

我有一个2D矢量InputVector定义如下:

vector< vector<int> > InputVector(MAX_ITER, vector<int>(inN));

还有另一个向量CR定义如下:

vector<int> CR(MAX_ITER);

CR[i]是与InputVector[i]相关的属性(通知i可能因0MAX_ITER-1而异。现在我想按InputVector的降序排序CR,即如果CR[j]在所有CR's中最高,InputVector[j]应该是新的InputVector[0] std::sort排序后1}} 是否可以使用algorithm中定义的{{1}}完成此操作?

4 个答案:

答案 0 :(得分:1)

这是一项非常奇怪的任务,但可以做到。

我会说 - 将CR [j]值push_back到InputVector [j],然后写一个自定义的&less;&#39; less&#39;比较最后元素和pop_back CR [j]值的函数。这样的事情:

但似乎你应该重新考虑如何存储你的数据 - 你需要这样的逻辑这一事实是警告。

#include <vector>
#include <algorithm>
#include <iostream>
#include <cassert>

using namespace std;

typedef vector<int> vi;
typedef vector<vi> vvi;

struct last_cmp
{
    bool operator()(const vi &lhs, const vi &rhs)
    {
        return lhs.back() > rhs.back();
    }
};

void weird_sort(vvi &InputVector, const vi &CR)
{
    assert(InputVector.size() == CR.size());

    for (size_t i = 0; i < InputVector.size(); i++)
        InputVector[i].push_back(CR[i]);

    sort(InputVector.begin(), InputVector.end(), last_cmp());

    for (size_t i = 0; i < InputVector.size(); i++)
        InputVector[i].pop_back();
}

int main()
{
    vvi InputVector;
    vi CR;

    InputVector.push_back(vector<int>(5, 0));
    InputVector.push_back(vector<int>(5, 1));
    InputVector.push_back(vector<int>(5, 2));
    InputVector.push_back(vector<int>(5, 3));
    InputVector.push_back(vector<int>(5, 4));

    CR.push_back(3);
    CR.push_back(2);
    CR.push_back(0);
    CR.push_back(1);
    CR.push_back(4);

    weird_sort(InputVector, CR);

    for (int i = 0; i < InputVector.size(); i++)
        cout << InputVector[i][0] << endl;
}

答案 1 :(得分:1)

我认为一个新的类或使用对会更好,但如果你真的想这样做

std::sort(InputVector.begin(), InputVector.end(), 
    [&CR,&InputVector](std::vector<int> &a, std::vector<int> &b){
        auto pos_a = &a - &(*InputVector.begin());
        auto pos_b = &b - &(*InputVector.begin());
        return (CR[pos_a] < CR[pos_b]);}
        );

这适用于我做的小测试,但我认为这可能很危险。

答案 2 :(得分:1)

在您提问的评论中,您明确表示您希望将这两个数组分开而不是将它们组合在一起,并且您还希望对CR以及InputVector进行排序。在这种情况下,最简单的方法是创建一个临时数组,将两个数组压缩为一个,使用std::sort,然后解压回原来的两个数组。

压缩和解压缩不应该减慢太多:这些是O(n)而排序是O(n log n)。此外,假设您的大部分数据都包含在vector<int>中的嵌套InputVector中,则可以使用vector::swap将此数据移入和移出临时数组,顾名思义,交换基础数据而不是复制它。

#include <vector>
using std::vector;
#include <algorithm>

void Sort(vector< vector<int> > &InputVector, vector<int>& CR) // assumes vectors the same size
{
    struct CRIntVec
    {
        int CR;
        vector<int> IntVec;
        bool operator<(const CRIntVec& rhs) const
        { return CR > rhs.CR; } // sort in descending order
    };
    vector<CRIntVec> combinedVec(InputVector.size());
    // Copy CR to combined vector but for efficiency swap in InputVector 
    for(int i=0; i<InputVector.size(); ++i) {
        combinedVec[i].CR = CR[i];
        combinedVec[i].IntVec.swap(InputVector[i]);
    }
    // Sort the combined vector
    std::sort(combinedVec.begin(), combinedVec.end());
    // Copy back from combined vector to CR, once again swapping for efficiency
    for(int i=0; i<InputVector.size(); ++i) {
        CR[i] = combinedVec[i].CR;
        combinedVec[i].IntVec.swap(InputVector[i]);
    }
}

答案 3 :(得分:-1)

你可以,但这会非常昂贵。您必须对CR的每个成员InputVector进行顺序搜索,以获取其相对排序值。这不是不可能,但效率很低。

为了提高效率,请CR制作地图或散列表。