用行对列进行排序

sorting a column with rows

本文关键字:排序      更新时间:2023-10-16

我有一组点(x,y,z)。我想用第一列对这些数据进行排序,第二列和第三列应该根据第一列的排序重新排列。是否有可能在c++中做到这一点,如果是的话,请帮助我。

在这里,我附加了我的实现代码,但我得到了一个错误消息"从' const ' vod* '到' const int[*][3] '的无效转换"在第31行和第32行。我尝试了几种方法,但我的努力还没有成功。我在这里用了' qsort ',有没有其他方法或者我可以用' sort ' in来做这个。由于我有一个非常大的数据集,我希望使用一个快速的方法。所以我需要在结束时的数据集,这是排序仅使用第一列,像下面的例子:之前那种

34  12  12
12  34 15
24  20  34
13  11  10
40  23  32

排序后
12  34 15
13  11  10
24  20  34
34  12  12
40  23  32

如果有任何好的方法可以帮助我编写代码…谢谢

#include <iostream>
#include <cstdlib>
#include <vector>
#include <stdio.h>
#include <stdlib.h>
using namespace std;
class Point
{
   private:          
    double x;
    double y;
    double z;
   public:
     Point(){};
     ~Point(){};
   Point(double X, double Y, double Z){
     x=X;y=Y;z=Z; }
   double X(){return x;}
   double Y(){return y;}
   double Z(){return z;}
};
int cmp ( const void *pa, const void *pb ) {
const int (*a)[3] = pa;
const int (*b)[3] = pb;
if ( (*a)[1] < (*b)[1] ) return -1;
if ( (*a)[1] > (*b)[1] ) return +1;
return 0;
}
int main ( ) {
vector<Point> points;
int input_x,input_y,input_z;       
   int i=0;
   while(i<6){//data set,it is a example, actual data come from a file 
         cout<<"x: ";cin>>input_x;
         cout<<"y: ";cin>>input_y;
         cout<<"z: ";cin>>input_z;
         Point point(input_x,input_y,input_z);                        
         points.push_back(point);
        i++;                         
         }        
for (int i=0;i<points.size();i++){//before sort
cout<<points[i].X()<<" "<<points[i].Y()<<" "<<points[i].Z()<<endl;
}
qsort( points, 6, sizeof points[0], cmp );
for (int i=0;i<points.size();i++){//after sort
cout<<points[i].X()<<" "<<points[i].Y()<<" "<<points[i].Z()<<endl;
}            
system("PAUSE");
return 0;
}

使用std::sort比使用qsort更简单:

class Point { 
    int x, y, z;
public:
    Point(int x, int y, int z) : x(x), y(y), z(z) {}
    bool operator<(Point const &other) { 
        return x < other.x;
    }
    // skipping the reading and other stuff for now...
};
int main() { 
    std::vector<Point> points;
    // add some Points to `points` here.
    // sort using order defined in Point::operator<:
    std::sort(points.begin(), points.end());
    return 0;
}

编辑:为了使比较与被比较的项目分开,您使用单独的函数或函子进行比较,并将其传递给std::sort。有一些关于你的类的事情,你真的想在任何情况下改变——至少,因为你的Point::X(), Point::Y()Point::Z()不修改点对象,你想让他们const成员函数。一旦完成了这些,排序就相当简单了:

#include <vector>
#include <algorithm>
#include <iterator>
#include <iostream>
class Point { 
    double x, y, z;
public:
    double X() const { return x; }
    double Y() const { return y; }
    double Z() const { return z; }
    Point(double x=0.0, double y=0.0, double z=0.0) : x(x), y(y), z(z) {}
};
namespace std { 
ostream &operator<<(ostream &os, Point const &p) { 
    return os << "(" << p.X() << ", " << p.Y() << ", " << p.Z() << ")";
}
}
struct byX { 
    bool operator()(Point const &a, Point const &b) { 
        return a.X() < b.X();
    }
};
int main(){ 
    std::vector<Point> points;
    for (int i=0; i<10; i++)
        points.push_back(Point(rand(), i, i));
    std::cout << "Unsorted:n";
    std::copy(points.begin(), points.end(), 
        std::ostream_iterator<Point>(std::cout, "n"));
    std::sort(points.begin(), points.end(), byX());
    std::cout << "nSorted:n";
    std::copy(points.begin(), points.end(), 
        std::ostream_iterator<Point>(std::cout, "n"));
    return 0;
}

从技术上讲,我想我应该添加一个更小的细节:如果你的任何点的x值是NaN,这将无法正常工作。NaN不等于任何违反std::sort所要求的严格弱排序的东西(甚至不等于它本身)。

在您的示例中,cmp函数的参数实际上是const Point *px。您可能无法以这种方式将它们声明为参数,但稍后您肯定可以cast void指针。