我需要在协议缓冲区消息中序列化.NET DateTime值。

我的计划是使用DateTime.ToBinary(),然后在消息中传递64位返回值。但我不确定选择什么作为协议缓冲数据类型来表示它。

我想我应该在使用fixed64(或sfixed64)数据类型时对感到困惑。

我假设在这种情况下我会使用签名类型,因为DateTime.ToBinary()返回的值可以是负数也可以是正数。

有帮助吗?

解决方案

嗯,你肯定想要int64sfixed64来处理正在签名的价值。

刚刚进行了快速测试,DateTime.Now.ToBinary()使用DateTime.ToBinary()编码为10个字节,而<=>将始终使用8个字节。基本上,可变长度编码对于小数字很有用,但是对于大数字而言变得比固定编码大。 (这与使用UTF-8而不是UTF-16的权衡相同 - ASCII字符可以在单个字节中以UTF-8编码,但稍后在代码点上最终编码为2然后3个字节,而UTF -16总是在BMP中使用2个字节作为字符。)

我的猜测是<=>值可能非常大(不知道它究竟是什么的详细信息)所以<=>更合适。

这有意义吗?

其他提示

protobuf-net 中,我采用了渐进式方法(事实上) ,如果你只是使用DateTime,它会为你处理所有这些 - 等效的.proto是这样的:

message DateTime {
  optional sint64 value = 1; // the offset (in units of the selected scale)
                             // from 1970/01/01
  optional TimeSpanScale scale = 2 [default = DAYS]; // the scale of the
                                                     // timespan
  enum TimeSpanScale {
    DAYS = 0;
    HOURS = 1;
    MINUTES = 2;
    SECONDS = 3;
    MILLISECONDS = 4;

    MINMAX = 15; // dubious
  }
}

即。如果ToBinary()可以在整天表达,我只发送自1970年以来的天数等 - 加上一个小标记到比例。这意味着可以更有效地发送日期,但对于其他比例而言,它并不会花费更多。

就个人而言,我不会使用<=> - 我会明确地使用已知时期的已知尺度的偏移(例如unix时代)。这使得它在平台之间更加便携。但是,如果您发送(例如)毫秒偏移量,则固定比例通常比变长比例更有效。是否需要签名或未签名取决于您是否需要在纪元之前的日期;-p

您应该使用带符号的64位数字,而不是因为DateTime可以是负数,而是因为ToBinary方法返回Int64,这是一个带符号的64位数字。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top