如何在 Protobuf-cSharp-port 和 Protobuf-net 之间进行选择

最近我不得不寻找一个最初由 Google 开发的协议缓冲库的 C # 移植。你猜怎么着,我在这里找到了两个著名人士拥有的两个项目: Probuf-cSharp-port,由 Jon Skeet原始病毒网络编写,由 Marc Gravell编写。我的问题很简单: 我必须选择哪一个?

我非常喜欢 Marc 的解决方案,因为在我看来它更接近于 C # 哲学(例如,你可以直接为现有类的属性添加属性) ,而且它看起来可以支持。NET 内置类型,如 System。伙计。

我相信他们都是很棒的项目,但你的意见呢?

24653 次浏览

您在项目中也使用其他语言吗?如果是这样,我的 C # 端口将允许您在所有平台上编写类似的代码。如果不是这样,那么 Marc 的端口可能是 C # 中比较惯用的开始。(我试图让我的代码“感觉”像普通的 C # ,但是设计显然是基于 Java 代码开始的,故意让那些使用 Java 的人也熟悉它。)

当然,这样做的好处之一是,你可以稍后改变主意,并确信所有的数据通过其他项目仍然是有效的——据我所知,它们应该是绝对二进制兼容的(就序列化数据而言)。

我同意 Jon 的观点; 如果您在多个环境中编写代码,那么他的版本将为您提供与其他“核心”实现类似的 API。Probuf-net 与大多数。NET 序列化程序是实现的,因此更熟悉(IMO)。NET 开发人员。正如 Jon 注意到的那样,原始的二进制输出 应该是相同的,所以如果以后需要的话,可以使用不同的 API 重新实现。

对于这个实现来说,具体点的一些要点是:

  • 使用 存在类型(不仅仅是从.proto 生成的类型)
  • 可以在 WCF 和 memcached 下工作
  • 可用于为现有类型实现 ISerializable
  • 支持继承 * 和序列化回调方法
  • 支持常见的模式,如 ShouldSerialize[name]
  • 使用现有的修饰类型(XmlType/XmlElementDataContract/DataMember)-意思是(例如) LINQ-to-SQL 模型开箱即用序列化(只要在 DBML 中启用序列化)
  • 在 v2中,适用于没有任何属性的 POCO 类型
  • 在 v2中,工作在。NET 1.1(不确定这是否是一个巨大的卖点)和大多数其他框架(包括单点触摸!)
  • 可能 (尚未实现) v2可能支持全图 * 序列化(而不仅仅是树序列化)

(* = 这些特性使用100% 有效的 Protobuf 二进制文件,但是从其他语言中消费这些文件可能很困难)

我之所以从 Protobuf-cSharp-port 切换到 Protobuf-net 是因为:

  • Protobuf-net 更像“ . net”,即用描述符序列化成员而不是代码生成。
  • 如果您想编译 Protobuf-cSharp-port。您必须执行2个步骤的过程,即使用。然后用 ProtoGen 编译。Protobuf-net 可以一步完成。

在我的例子中,我想用协议缓冲代替基于 xml 的。一个网络客户端和一个 j2ee 后端。因为我已经在使用代码生成,所以我将使用 Jon 的实现。

对于不需要 java 互操作的项目,我会选择 Marc 的实现,特别是因为 v2允许在没有注释的情况下工作。

根据它的 GitHub 项目站点原型 -cSharp-port 现在已经并入了谷歌的主要协议缓冲项目,所以它将是官方的。NET 实现。然而,Protobuf-net 是 最近一次更新是在2013年,虽然已经有了 最近在 GitHub 上有一些提交