C++ 对延迟计算连接中断元素的向量进行排序

C++ 对延迟计算连接中断元素的向量进行排序,c++,C++,我想按主字段对结构的向量进行排序,并使用辅助字段作为平分符。通常的做法是: struct element { int primary; int secondary; }; bool comparator(const element& e1, const element& e2) { if (e1.primary != e2.primary) { return e1.primary < e2.primary; } return e1.second

我想按主字段对结构的向量进行排序,并使用辅助字段作为平分符。通常的做法是:

struct element {
  int primary;
  int secondary;
};

bool comparator(const element& e1, const element& e2) {
  if (e1.primary != e2.primary) {
    return e1.primary < e2.primary;
  }
  return e1.secondary < e2.secondary;
}
struct元素{
int小学;
int中学;
};
布尔比较器(常量元素和e1、常量元素和e2){
if(e1.primary!=e2.primary){
返回e1.primary
但二次数据的计算成本很高。因为只有当主值相等时才需要它,所以我想惰性地计算它

看来我唯一能做这种惰性评估的地方就是比较器本身。比如:

bool comparator(const element& e1, const element& e2) {
  if (e1.primary != e2.primary) {
    return e1.primary < e2.primary;
  }

  return e1.computeSecondary() < e2.computeSecondary();
}
bool比较器(常量元素&e1、常量元素&e2){
if(e1.primary!=e2.primary){
返回e1.primary
虽然这样可以避免在主值不同的情况下计算次值,但每次将同一元素与另一个元素进行比较时,都会重新计算该元素的次值。我要排序的数据是长尾的,大约有30%的值等于1,20%等于2,5%等于3,对于较高的值,更低的是%。因此,将有相当多的情况下,次要元素将得到计算,而不存储计算值可能会导致它们被重新计算太多次


因此,我希望每个元素最多对次值求值一次。但是比较器接受const ref参数,因此它不能修改元素的次值。如何实现这一点?

简单地说,可能的选择是

  • 声明
    secondary
    mutable
  • 在比较器中使用
    const\u cast
  • computeSecondary
    中使用
    const\u cast
  • 创建一个简单的
    Lazy
    模板类,该类保存一个值或一个thunk,当被要求时,如果尚未对值进行计算,则在内部强制该值,并报告结果(或立即报告结果,如果已经知道),不会花费很长时间;并将
    secondary
    声明为类型
    Lazy
  • 或者更确切地说,不要重新发明轮子并使用
    std::future
    ,这实际上是非常懒惰的模板(在一种情况下)
  • 或者其他任何事情,我们可以创造更多的方法

  • 在比较器中使用const_cast似乎是最简单的方法。我会将每个参数强制转换为比较器,然后调用它的computeSecondary(),这也会更新次要值本身吗?例如,是的。如果主键上有一个连接,你只需要
    const\u cast
    。缓存或记忆成员变量通常声明为
    mutable
    ,以避免需要
    const\u cast
    。谢谢。我不知道易变的。做了一些谷歌搜索。正如你所说,在这种情况下,这是一个更好的选择。