自定义模板的排序向量 class
Sort vector of custom template class
假设我有一个模板 class ComplexNumber
如下所示:
template<typename T>
class ComplexNumber {
public:
ComplexNumber() : A(), B() {}
ComplexNumber(const T& r, const T& i) : A(r), B(i) {}
~ComplexNumber(){}
void setA(T A1);
void SetB(T B1);
T getA() const {return A;};
T getB()const {return B;};
ComplexNumber<T> operator+(const ComplexNumber<T> &C){
return ComplexNumber<T>( A + C.getA(), B + C.getB());
}
ComplexNumber<T> operator -(const ComplexNumber<T> &C) {
return ComplexNumber<T>(A - C.getA(), B - C.getB());
};
friend ostream & operator << (ostream &out, const ComplexNumber<T> &c)
{
out << c.A;
out << "+i" << c.B << endl;
return out;
}
private:
T A;
T B;
};
还有一个 main()
构造这些复数并将它们存储到 std::vector
:
ComplexNumber<int> complex1(10, 3);
ComplexNumber<int> complex2(2, 56);
ComplexNumber<int> complex3(3, 55);
vector<ComplexNumber<int>> testVector;
testVector.push_back(complex1);
testVector.push_back(complex2);
testVector.push_back(complex3);
如果我想 testVector
从高到低排序,先比较实部,然后在实部相等的情况下比较虚部,我该怎么做?
我无法使用标准 std::sort()
功能。我想使用方法或仿函数来做到这一点。
编辑:尝试将其添加到函数中:
//This method is outside the scope of the ComplexNumber class
auto compare_by_magnitude = [](const auto& a, const auto& b) {
return a.A*a.A + a.B*a.B < b.A*b.A + b.B*b.B;
};
void sortComplex(vector<ComplexNumber<int>> &c){
std::sort(c.begin(),c.end(),compare_by_magnitude);
}
我的错误信息:
FAILED: complexNumber.exe
cmd.exe /C "cd . && C:\PROGRA~1\JETBRA~1\CLION2~1.3\bin\mingw\bin\G__~1.EXE -g CMakeFiles/complexNumber.dir/main.cpp.obj CMakeFiles/complexNumber.dir/ComplexNumber.cpp.obj -o complexNumber.exe -Wl,--out-implib,libcomplexNumber.dll.a -Wl,--major-image-version,0,--minor-image-version,0 -lkernel32 -luser32 -lgdi32 -lwinspool -lshell32 -lole32 -loleaut32 -luuid -lcomdlg32 -ladvapi32 && cd ."
C:\Program Files\JetBrains\CLion 2021.3.3\bin\mingw\bin/ld.exe: CMakeFiles/complexNumber.dir/ComplexNumber.cpp.obj: in function `ComplexNumber<int>::~ComplexNumber()':
C:/PROGRA~1/JETBRA~1/CLION2~1.3/bin/mingw/lib/gcc/x86_64-w64-mingw32/11.2.0/include/c++/bits/stl_heap.h:223: multiple definition of `sortComplex(std::vector<ComplexNumber<int>, std::allocator<ComplexNumber<int> > >&)'; CMakeFiles/complexNumber.dir/main.cpp.obj:C:/Users/elira/Desktop/complexNumber/complexNumber/ComplexNumber.h:51: first defined here
C:\Program Files\JetBrains\CLion 2021.3.3\bin\mingw\bin/ld.exe: CMakeFiles/complexNumber.dir/ComplexNumber.cpp.obj:C:/Users/elira/Desktop/complexNumber/complexNumber/ComplexNumber.h:48: multiple definition of `compare_by_magnitude'; CMakeFiles/complexNumber.dir/main.cpp.obj:C:/Users/elira/Desktop/complexNumber/complexNumber/ComplexNumber.h:48: first defined here
collect2.exe: error: ld returned 1 exit status
ninja: build stopped: subcommand failed.
为了使用 std::sort()
,您的 class 需要至少 operator<
定义:
bool operator< (const ComplexNumber<T>& other) const {
return A < other.A || (A == other.A && B < other.B);
}
定义 operator==
也是一个好习惯,但是 std::sort()
将单独与 operator<
一起工作。
当我对您的 class 进行上述添加时,此 main()
按实数和虚数升序排序:
int main() {
vector<ComplexNumber<float>> vc = { {4, 5}, {1, 3}, {4, 2} };
copy(vc.begin(), vc.end(), ostream_iterator<ComplexNumber<float>>(cout, " "));
cout << endl;
sort(vc.begin(), vc.end());
copy(vc.begin(), vc.end(), ostream_iterator<ComplexNumber<float>>(cout, " "));
cout << endl;
}
但是,您提到要按 降序 顺序排序。如您所想,在 class 中以相反的方式定义 operator<
是不好的做法,因此您可以将比较函数传递给 std::sort()
以反转比较的含义:
sort(vc.begin(), vc.end(),
[](const ComplexNumber<float> &f1, const ComplexNumber<float> &f2)
{ return ! (f1 < f2); }
);
撇开这些编译和语义问题不谈,当我查看您发布的错误时,我看到 link 错误,而且您的 class 被多次定义。这表明定义您的 class 的包含文件缺少包含防护。
假设我有一个模板 class ComplexNumber
如下所示:
template<typename T>
class ComplexNumber {
public:
ComplexNumber() : A(), B() {}
ComplexNumber(const T& r, const T& i) : A(r), B(i) {}
~ComplexNumber(){}
void setA(T A1);
void SetB(T B1);
T getA() const {return A;};
T getB()const {return B;};
ComplexNumber<T> operator+(const ComplexNumber<T> &C){
return ComplexNumber<T>( A + C.getA(), B + C.getB());
}
ComplexNumber<T> operator -(const ComplexNumber<T> &C) {
return ComplexNumber<T>(A - C.getA(), B - C.getB());
};
friend ostream & operator << (ostream &out, const ComplexNumber<T> &c)
{
out << c.A;
out << "+i" << c.B << endl;
return out;
}
private:
T A;
T B;
};
还有一个 main()
构造这些复数并将它们存储到 std::vector
:
ComplexNumber<int> complex1(10, 3);
ComplexNumber<int> complex2(2, 56);
ComplexNumber<int> complex3(3, 55);
vector<ComplexNumber<int>> testVector;
testVector.push_back(complex1);
testVector.push_back(complex2);
testVector.push_back(complex3);
如果我想 testVector
从高到低排序,先比较实部,然后在实部相等的情况下比较虚部,我该怎么做?
我无法使用标准 std::sort()
功能。我想使用方法或仿函数来做到这一点。
编辑:尝试将其添加到函数中:
//This method is outside the scope of the ComplexNumber class
auto compare_by_magnitude = [](const auto& a, const auto& b) {
return a.A*a.A + a.B*a.B < b.A*b.A + b.B*b.B;
};
void sortComplex(vector<ComplexNumber<int>> &c){
std::sort(c.begin(),c.end(),compare_by_magnitude);
}
我的错误信息:
FAILED: complexNumber.exe
cmd.exe /C "cd . && C:\PROGRA~1\JETBRA~1\CLION2~1.3\bin\mingw\bin\G__~1.EXE -g CMakeFiles/complexNumber.dir/main.cpp.obj CMakeFiles/complexNumber.dir/ComplexNumber.cpp.obj -o complexNumber.exe -Wl,--out-implib,libcomplexNumber.dll.a -Wl,--major-image-version,0,--minor-image-version,0 -lkernel32 -luser32 -lgdi32 -lwinspool -lshell32 -lole32 -loleaut32 -luuid -lcomdlg32 -ladvapi32 && cd ."
C:\Program Files\JetBrains\CLion 2021.3.3\bin\mingw\bin/ld.exe: CMakeFiles/complexNumber.dir/ComplexNumber.cpp.obj: in function `ComplexNumber<int>::~ComplexNumber()':
C:/PROGRA~1/JETBRA~1/CLION2~1.3/bin/mingw/lib/gcc/x86_64-w64-mingw32/11.2.0/include/c++/bits/stl_heap.h:223: multiple definition of `sortComplex(std::vector<ComplexNumber<int>, std::allocator<ComplexNumber<int> > >&)'; CMakeFiles/complexNumber.dir/main.cpp.obj:C:/Users/elira/Desktop/complexNumber/complexNumber/ComplexNumber.h:51: first defined here
C:\Program Files\JetBrains\CLion 2021.3.3\bin\mingw\bin/ld.exe: CMakeFiles/complexNumber.dir/ComplexNumber.cpp.obj:C:/Users/elira/Desktop/complexNumber/complexNumber/ComplexNumber.h:48: multiple definition of `compare_by_magnitude'; CMakeFiles/complexNumber.dir/main.cpp.obj:C:/Users/elira/Desktop/complexNumber/complexNumber/ComplexNumber.h:48: first defined here
collect2.exe: error: ld returned 1 exit status
ninja: build stopped: subcommand failed.
为了使用 std::sort()
,您的 class 需要至少 operator<
定义:
bool operator< (const ComplexNumber<T>& other) const {
return A < other.A || (A == other.A && B < other.B);
}
定义 operator==
也是一个好习惯,但是 std::sort()
将单独与 operator<
一起工作。
当我对您的 class 进行上述添加时,此 main()
按实数和虚数升序排序:
int main() {
vector<ComplexNumber<float>> vc = { {4, 5}, {1, 3}, {4, 2} };
copy(vc.begin(), vc.end(), ostream_iterator<ComplexNumber<float>>(cout, " "));
cout << endl;
sort(vc.begin(), vc.end());
copy(vc.begin(), vc.end(), ostream_iterator<ComplexNumber<float>>(cout, " "));
cout << endl;
}
但是,您提到要按 降序 顺序排序。如您所想,在 class 中以相反的方式定义 operator<
是不好的做法,因此您可以将比较函数传递给 std::sort()
以反转比较的含义:
sort(vc.begin(), vc.end(),
[](const ComplexNumber<float> &f1, const ComplexNumber<float> &f2)
{ return ! (f1 < f2); }
);
撇开这些编译和语义问题不谈,当我查看您发布的错误时,我看到 link 错误,而且您的 class 被多次定义。这表明定义您的 class 的包含文件缺少包含防护。