0

我正在尝试解决这个问题。我想出了这个解决方案:

typedef unordered_map<string, double> stockDictType;

class StockTicker {
  class Comparator {
  public:
    inline bool operator() (const string &a, const string &b) const {
      return stocksDict.at(a) < stocksDict.at(b);
    }
  };

  stockDictType stocksDict;

  map<string, stockDictType::iterator, Comparator> stocksTicker; // this is where I need a custom comparator method

  int tickerSize;

public:
  StockTicker(int k): tickerSize(k) {}

  // some other methods
};

很明显,这无法编译:StockTicker::stocksDict不是静态成员。现在我不能这样做,因为我可能需要StockTicker该类的多个实例。

std::map使用严格的比较器函数参数定义(std::map只会传入要比较的键),所以我不能重载它来传递对当前StockTicker类实例的引用(我可以用来StockTicker::stocksDict通过 public访问吸气剂)

我从这个 SO question随后的答案中获得了灵感:

typedef unordered_map<string, double> stockDictType;

class StockTicker {
  class Comparator {
  public:
    stockDictType &_stockDictRef;

    explicit Comparator(stockDictType &stocksDict): _stockDictRef(stocksDict) {}

    inline bool operator() (const string &a, const string &b) const {
      return _stockDictRef.at(a) < _stockDictRef.at(b);
    }
  };

  stockDictType stocksDict;
  map<string, stockDictType::iterator, Comparator> stocksTicker(Comparator{stocksDict});
  int tickerSize;

public:
  StockTicker(int k): tickerSize(k) {}

  void addOrUpdate(string name, double price) {
    stocksDict[name] = price;
    stocksTicker.at(name) = stocksDict.find(name);
  }

  vector<stockDictType::iterator> top() {
    vector<stockDictType::iterator> ret(tickerSize);

    auto it = stocksTicker.begin();
    for(int i = 0; i < tickerSize; i++, it++)
      ret[i] = it->second;

    return ret;
  }
};

这也不会编译。我在and方法 中遇到这种错误: .StockTicker::addOrUpdate()StockTicker::top()error: '((StockTicker*)this)->StockTicker::stocksTicker' does not have class type

我也尝试了很多其他的东西(比如在StockTicker类本身中声明一个公共比较器方法并尝试将它的函数指针传递给std::map. 那也失败了;StockTicker::stocksTicker在比较器方法之前声明并且编译器抱怨)。

关于如何解决这个问题的任何想法?

4

1 回答 1

2
 std::map<std::string, stockDictType::iterator, Comparator> stocksTicker(Comparator(stocksDict));

这定义了一个名为的成员函数stocksTicker,它接受一个stocksDict类型的参数Comparator并返回一个std::map.

std::map<std::string, stockDictType::iterator, Comparator> stocksTicker{Comparator{stocksDict}};

这定义了一个成员变量stocksTicker,默认情况下,它用 a 初始化Comparator,而它又用成员变量 初始化stocksDict

我假设你想要第二个。

您的语法介于两者之间。无论您对此感到困惑的是什么编译器。

活生生的例子

您应该StockTicker(StockTicker &&)=deleteStockTicker& operator=(StockTicker &&)=delete,因为包含对其包含类的引用的地图不能安全移动或复制。

在这里产生一个有效的举动是很棘手的。我怀疑 C++17 节点拼接可能会做到这一点。您可能必须嵌入 a std::shared_ptr<stocksDict*>(是的,指向指针的共享指针),并用于在目标.key_comp中重新安装stocksDict

于 2017-03-31T17:11:47.497 回答