3

我是协议缓冲区概念的新手,如果我使用 protobuf 对象作为std::map.

我知道能够使用 protobuf 对象作为键,我需要提供一个自定义比较器std::map来维护键的顺序。

我现在有两个问题:

  1. google/protobuf/util 中是否有任何实用程序函数/类重载小于运算符来比较两个 protobuf 消息?即,与此类似的东西。
bool operator<(google::protobuf::Message m1, google::protobuf::Message m2){
    // compare the protobuf messages
    // and finally return the value
    return value;
} 
  1. 我可能知道的任何潜在副作用,可能是由于使用 protobuf 对象作为键而产生的?
4

1 回答 1

3

我建议最好使用std::unordered_map而不是std::map如果您不关心订单。这不仅是最佳的,而且更不容易出错。在比较器实现的情况下,您必须确保 ifMessage m1大于Message m2并且Message m2大于Message m3, thenMessage m1大于Message m3。(提及,因为从您的定义中我不清楚这一点)。

您可以使用MessageDifferencer作为std:equal_to. 另请参阅Google 协议缓冲区比较中的答案

但是,正如您正确指出的那样,没有等效于std::hash,您将需要提供自定义哈希函数。请参考PR-2066PR-2304讨论这个缺失的功能。

从拉取请求中,引用xfxyjwf

使用 proto 消息作为键不是一个好主意,因为它们不是真正的值类型。由于存在未知字段,一个二进制文件中的两条相同消息可能会被另一个二进制文件视为不同,因此即使给定完全相同的输入数据(如果哈希函数使用 MessageDifferencer 实现),两个不同的二进制文件可能会得到两个不同的 unordered_map<> . 编写具有所需行为的自己的哈希函数可能比回复通用哈希函数更好。

如果您没有未知字段,则通用哈希函数应该可以正常工作。

于 2019-04-07T07:17:48.950 回答