protobuf-net 缺少可选字段的 has_ 函数?. [英] protobuf-net missing has_ function for optional fields?.
问题描述
我们使用协议缓冲区进行原生 C++ 应用程序之间的通信,也用于原生 C++ 应用程序和 .NET 应用程序(都是 VS2012)之间通过 protobuf-net r666 进行通信.我们在 C++ 中严重依赖可用于可选元素的 has_ 函数.
We use protocol buffers for communication between native C++ apps, but also between native C++ app and .NET application (all is VS2012) via protobuf-net r666. We rely in C++ heavily on the has_ functions that are available for an optional element.
例如如果我们有一个带有可选 bool 字段的消息,它可以是未设置、设置为 true 或设置为 false.
E.g. if we have a message with a field optional bool, it can be that it is not set, it is set to true, or it is set to false.
在 C++ 中,这可以使用函数 has_field 进行检查,如果设置,则可以使用 get_field 函数获取内容.如果未设置,并且调用了 get_field,则 get 返回默认值,如果未显式设置则为 false(对于布尔值).
In C++ this can be checked with the function has_field and if set then the content can be fetched with get_field function. If not set, and get_field is called, then the get returns the default, which if not explicitly set is false (for a boolean).
这在 C++ 中完美运行,但是,在 protobuf-net 中,我们似乎无法找到 has_ 函数的等价物,并且,当收到消息时,该字段被添加到消息中,并将其内容设置为默认为 false.该字段默认存在并不是灾难,但问题是没有has_函数来检查它是否在消息中设置.
This works perfectly in C++, but, in protobuf-net however, we cannot seem to find the equivalent of the has_ function, and, when the message is received, the field is added to the message and it's content is set to the default, being false. It's not a disaster that the field is there with the default, but the problem is that there is no has_ function to check whether it was set in the message.
请告知这是一个错误还是我们是否遗漏了 protobuf-net 中的某些内容,这实际上是可能的
Please advise whether this is a bug or whether we missed something in protobuf-net and that this actually is possible
提前谢谢.维姆
推荐答案
(我知道我们已经在 问题跟踪器 - 这纯粹是为了可见性等)
(I know we already covered this in the issue tracker - this is purely for visibility etc)
这与从 .proto 文件生成类有关,在 protobuf-net 的情况下,这是通过 protogen 工具生成的.默认情况下,它不会创建等效的 has_*
方法,但是可以使用 -p:detectMissing
开关启用它 - 这会导致它创建 *指定的
访问器.这里的命名是 .NET 习惯用法,*Specified
被其他一些 .NET 序列化程序和内部代码识别.它还生成一个私有的 ShouldSerialize*
方法,这再次有助于一些内部 .NET 代码.
This relates to generating classes from .proto files, which in the case of protobuf-net is via the protogen tool. By default, it does not create the equivalent of has_*
methods, but this can be enabled with the -p:detectMissing
switch - which causes it to create *Specified
accessors. The naming here is a .NET idiom, with *Specified
recognised by some other .NET serializers and internal code. It also generates a private ShouldSerialize*
method, which again helps some internal .NET code.
在这种特定情况下,名为 value
的成员存在次要问题,导致混淆;csharp.xslt
文件现已更新以解决此问题.
In this specific case, there was a secondary issue with a member called value
causing confusion; the csharp.xslt
file has now been updated to account for this.
更新:在完全托管的重写中,ShouldSerialize*()
方法在使用 proto2
语法(默认)时默认生成.不需要额外的参数.*Specified
成员未被添加(它除了 ShouldSerialize*()
之外没有其他用途.
Update: in the fully managed rewrite, the ShouldSerialize*()
method is generated by default when using proto2
syntax (the default). No additional parameter is required. The *Specified
member is not added (it serves no additional purpose over ShouldSerialize*()
.
注意,在使用 proto3
时,序列化规则的变化意味着这个概念不再有意义.一个值被序列化当且仅当它不是默认值,它总是空/假/零/空.没有默认值但指定"的概念.因此,ShouldSerialize*()
方法通常不再有用,并且不会生成.我愿意让它们选择性地为 proto3
生成,它们基本上意味着非默认",如果这有助于一些真正的编码场景.
Note that when using proto3
, the changes to serialization rules mean that this concept no longer has meaning. A value is serialized if and only if it is not the default, which is always null/false/zero/empty. There is no concept of "the default value but specified". Because of this, the ShouldSerialize*()
methods are generally no longer useful, and are not generated. I'm open to making them optionally generated for proto3
, with them basically meaning "non-default", if that helps some genuine coding scenario.
这篇关于protobuf-net 缺少可选字段的 has_ 函数?.的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!