用于存储 ipv4 或 ipv6 地址的最有效的 protobuf 类型(在 C++ 中)是什么?我的地址是 boost::asio::ip::address_v4(或 v6)
What is the most efficient protobuf type (in C++) for storing ipv4 or ipv6 address? My address is a boost::asio::ip::address_v4 (or v6)
我读到 protobuf 有一个名为“bytes”的类型,它可以存储任意数量的字节,相当于 "C++ string"。我不喜欢使用 "bytes" 的原因是它期望输入为 C++ 字符串,即,boost IP 需要转换为字符串。现在我关心的是:我想执行序列化并通过 TCP 套接字发送编码的 protobuf 消息。我想确保编码的消息大小尽可能小。
目前,我正在使用以下 .proto 文件:
syntax = "proto2";
message profile
{
repeated **uint32** localEndpoint = 1;
repeated **uint32** remoteEndpoint = 2;
}
为了在protobuf消息中保存boost IP,我首先使用"boost::asio::ip::address_v4::to_bytes()"将boost IP转换为字节格式数组。因此,对于 v4 IP,结果数组大小为 4。然后我将结果字节数组中的第一个 4 个字节转换为一个 uint32_t 数字,然后存储在 protobuf 消息的 "localEndpoint" 字段中。同样,我重复接下来的 4 个字节(对于 v6)。我一次取 4 个字节,以便利用 uint32 的完整 32 位。
因此,对于 v4 地址,使用了 1 次 "localEndpoint" 字段。
同样,对于 v6 地址,使用了 4 次 "localEndpoint" 字段。
请允许我强调一下,如果我在这里使用了 "bytes",对于像 111.111.111.111
这样的 v4 ip,我的输入字符串本身的大小将是 15 个字节
使用 uint32 而不是 "bytes" 确实为我节省了一些编码数据大小,但我正在寻找一种需要更少字节数的更高效的 protobuf 类型。
抱歉,描述太长了,但我想详细解释一下我的查询。请帮助我.. 提前致谢:)
一个 ipv4 地址应该恰好需要 4 个字节。如果您以某种方式获得 8,则说明您做错了什么 - 您可能是 hex-encoding 吗?你在这里不需要那个。同样,ipv6应该是16字节。
具有 usually-set 高字节的 4 个字节最有效地存储为 fixed32
- 由于高位,varint 会在此处产生开销。 16 个字节更微妙——我会选择 bytes
(字段 header 加长度),因为形成联合更简单,如果 field-number 很大,它可以避免必须为多个 multi-byte 字段 header 付费(16 的长度前缀将始终是 single-byte)。
然后我会通过 oneof
:
创建这些的联合
oneof ip_addr {
fixed32 v4 = 1;
bytes v6 = 2;
}
我读到 protobuf 有一个名为“bytes”的类型,它可以存储任意数量的字节,相当于 "C++ string"。我不喜欢使用 "bytes" 的原因是它期望输入为 C++ 字符串,即,boost IP 需要转换为字符串。现在我关心的是:我想执行序列化并通过 TCP 套接字发送编码的 protobuf 消息。我想确保编码的消息大小尽可能小。
目前,我正在使用以下 .proto 文件:
syntax = "proto2";
message profile
{
repeated **uint32** localEndpoint = 1;
repeated **uint32** remoteEndpoint = 2;
}
为了在protobuf消息中保存boost IP,我首先使用"boost::asio::ip::address_v4::to_bytes()"将boost IP转换为字节格式数组。因此,对于 v4 IP,结果数组大小为 4。然后我将结果字节数组中的第一个 4 个字节转换为一个 uint32_t 数字,然后存储在 protobuf 消息的 "localEndpoint" 字段中。同样,我重复接下来的 4 个字节(对于 v6)。我一次取 4 个字节,以便利用 uint32 的完整 32 位。
因此,对于 v4 地址,使用了 1 次 "localEndpoint" 字段。 同样,对于 v6 地址,使用了 4 次 "localEndpoint" 字段。
请允许我强调一下,如果我在这里使用了 "bytes",对于像 111.111.111.111
这样的 v4 ip,我的输入字符串本身的大小将是 15 个字节使用 uint32 而不是 "bytes" 确实为我节省了一些编码数据大小,但我正在寻找一种需要更少字节数的更高效的 protobuf 类型。
抱歉,描述太长了,但我想详细解释一下我的查询。请帮助我.. 提前致谢:)
一个 ipv4 地址应该恰好需要 4 个字节。如果您以某种方式获得 8,则说明您做错了什么 - 您可能是 hex-encoding 吗?你在这里不需要那个。同样,ipv6应该是16字节。
具有 usually-set 高字节的4 个字节最有效地存储为 fixed32
- 由于高位,varint 会在此处产生开销。 16 个字节更微妙——我会选择 bytes
(字段 header 加长度),因为形成联合更简单,如果 field-number 很大,它可以避免必须为多个 multi-byte 字段 header 付费(16 的长度前缀将始终是 single-byte)。
然后我会通过 oneof
:
oneof ip_addr {
fixed32 v4 = 1;
bytes v6 = 2;
}