【发布时间】:2022-01-28 04:13:18
【问题描述】:
我有一个简单的MyElement 类,我想使用bool MyElement::SomeMethod(...) {...} 作为std::set 的MyElement 项目的自定义比较器。
我已经进行了研究,并且已经了解了一些替代解决方案,我在下面列出了这些解决方案。
我也知道如何更改比较器,例如使用std::greater 而不是默认的std::less,代码如下:
std::set<MyElement, std::greater<MyElement> > s;
我的确切问题是我想使用bool MyElement::SomeMethod(...) {...} 作为自定义比较器。
我想出的唯一解决方案类似于下面列表中的最后一个,即布尔函数的解决方案:
using Cmp = std::integral_constant<decltype(&MyElement::SomeMethod),
&MyElement::SomeMethod>;
std::set<MyElement, Cmp> my_set;
不过,此解决方案仅适用于 static MyElement::SomeMethod。
我想知道非静态方法是否有类似或更简洁的方法。
替代解决方案列表:
C++20 方法
auto cmp = [](const MyElement& lhs, const MyElement& rhs) { return ... };
std::set<MyElement, decltype(cmp)> s;
C++11 方法
auto cmp = [](const MyElement& lhs, const MyElement& rhs) { return ... };
std::set<MyElement, decltype(cmp)> s(cmp);
函数而不是 lambda
bool cmp(const MyElement& lhs, const MyElement& rhs) { return ...; }
然后
std::set<MyElement, decltype(cmp)*> s(cmp);
或
std::set<int, decltype(&cmp)> s(&cmp);
结构和操作符()
struct cmp {
bool operator() (const MyElement& lhs, const MyElement& rhs) const {
return ...
}
};
然后
std::set<MyElement, cmp> s;
布尔函数
bool cmp(const MyElement& lhs, const MyElement& rhs) {
return ...;
}
然后
#include <type_traits>
using Cmp = std::integral_constant<decltype(&cmp), &cmp>;
std::set<MyElement, Cmp> s;
【问题讨论】:
-
C++20也可以做
std::set<MyElement, decltype([](const MyElement& lhs, const MyElement& rhs) { return ... })> s; -
MyElement::SomeMethod是静态的吗? -
那么
integral_constant技巧不起作用:gcc.godbolt.org/z/3e41zzsY4 -
您在寻找
typedef std::function<bool(const MyElement&, const MyElement&)> comparer; std::set<MyElement,comparer>{comparer{&MyElement::SomeNonStaticMemberFunction}};吗? -
@vaeVictis:是的,
std::function构造函数会将指向非静态成员函数的指针转换为第一个参数是目标对象的可调用对象,即this在该成员函数内部,并且可调用的其余参数与该成员函数的实际参数匹配。
标签: c++ c++11 set custom-compare