protobuf和arrow的比较

Comparison of protobuf and arrow

两者都是语言中立和平台中立的数据交换库。我想知道它们有什么区别,哪个库适用于哪些情况。

它们用于解决两个不同的问题。 Protobuf 旨在为数据创建通用的“在线”或“磁盘”格式。

Arrow 旨在为数据创建通用的“内存中”格式。

当然,下一个问题,这是什么意思?

在 Protobuf 中,如果应用程序想要处理数据,他们首先将数据反序列化为某种“内存中”表示形式。必须这样做,因为 Protobuf 格式不容易与 CPU 指令兼容。例如,protobuf 将无符号整数打包为 varint。它们具有可变的字节数,并且字段的线路类型被塞入 3 个最低有效位。您不能取两个无符号整数并在不首先将它们转换为某种“内存中”表示的情况下将它们相加。

现在,protoc 确实拥有适用于每种语言的库,可以将其转换为这些语言的“内存中”表示形式。然而,这种“在内存中”的表示并不常见。您不能获取 Protobuf 消息,将其反序列化为 C#(使用 protoc 生成的代码),然后在 Java 中处理这些内存字节而不进行某种 C#->Java 编组的数据。

另一方面,箭头解决了这个问题。如果您在 C# 中有一个 Arrow table,您可以将该内存映射到另一种语言并开始对其进行处理,而无需进行任何类型的“语言到语言”数据编组。这种零拷贝允许在语言之间进行有效的切换。 Python 已经使用这样的技巧(例如数组协议)一段时间了,它非常适合数据分析。

但是,Arrow 并不总是最适合无线传输的格式,因为它可能效率低下。我之前提到的那些 varints 帮助 Protobuf 减少了消息大小。此外,Protobuf 标记每个字段,以便在有许多可选字段时可以节省 space。事实上,Arrow 在 Arrow Flight(一个 RPC 框架)中使用 Protobuf 和 gRPC 进行元数据的无线传输。