当我在 Java 中使用 Protocol Buffer 序列化这个对象时,我得到这个字节数组:
byte[] topic = Transport.newBuilder()
.setTopic(Topics.ORD)
.setExtension(Ord.command, Commands.INSERT)
.build()
.toByteArray();
// [8,2,16,0]
当我对 protobuf-net 做同样的事情时,我得到了这个
var transport = new Transport
{
topic = Topics.ORD,
command = Commands.INSERT
};
var stream = new MemoryStream();
Serializer.Serialize(stream, transport);
byte[] result = stream.ToArray(); // [8,2]
这在使用 zmq 和基于 bye 数组的订阅时给我带来了一些麻烦。 我如何确保两个数组看起来相同?
最佳答案
protobuf-net 在 v1 中做出了“零默认”假设。如果我从头开始,我可能不会再做出决定,而且确实可以在 v2 中禁用此行为。但就目前而言,在许多情况下,它假定零作为隐式默认值。我猜你的 command
是一个不可为 null 的枚举,在这种情况下它将应用这个逻辑(作为旁注:如果它是 nullable,它会不这样做 - 它会使用 null
检查包含/排除决定)。
因此,它决定第二个字段(字段编号 2,编码为 varint)不需要序列化。因此没有 [16, 0]
。
选项:
- 使用一个可空成员(等同于
optional
)——即public SomeEnum?命令 {get;set;}
- 将成员标记为必需(
ProtoMemberAttribute
上的IsRequired=true
) - 关闭隐式零默认行为(
RuntimeTypeModel
实例上的UseImplicitZeroDefaults
)
关于c# - 为什么在使用 java 和 protobuf-net 的 Protocol Buffer 进行序列化时 byte[] 不同?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21550677/