gpt4 book ai didi

perl - 你能扩展 pack() 来处理自定义的可变长度字段吗?

转载 作者:行者123 更新时间:2023-12-02 03:34:13 25 4
gpt4 key购买 nike

Bitcoin protocol ,为了节省空间,使用他们所谓的可变长度整数或 varints 对他们的整数进行编码。 varint 的第一个字节对其长度及其解释进行编码:

FirstByte  Value
< 0xfd treat the byte itself as an 8 bit integer
0xfd next 2 bytes form a 16 bit integer
0xfe next 4 bytes form a 32 bit integer
0xff next 8 bytes form a 64 bit integer

(所有整数都是小端字节序且无符号)。我编写了以下函数来解压 varint:

my $varint = "\xfd\x00\xff"; # \x00\xff in little endian == 65280 
say unpack_varint($varint); # print 65280

sub unpack_varint{
my $v = shift;
my $first_byte = unpack "C", $v;
say $first_byte;
if ($first_byte < 253) { # \xfd == 253
return $first_byte;
}
elsif ($first_byte == 253){
return unpack "S<", substr $v, 1, 2;
}
elsif ($first_byte == 254){
return unpack "L<", substr $v, 1, 4;
}
elsif ($first_byte == 255){
return unpack "Q<", substr $v, 1, 8;
}
else{
die "error";
}
}

这行得通...但是如果我有一个带有嵌入式 varint 的长字节串,它会非常不优雅编码的 varint 是等等。有没有更好的方法来写这个?特别是,我能否以某种方式扩展 pack() 以支持这种结构?

最佳答案

您可以创建一组 shift_$type 函数来读取和删除给定字符串开头的一些值,因此您的代码如下所示:

my $buffer = ...;

my $val1 = shift_varint($buffer);
my $val2 = shift_string($buffer);
my $val3 = shift_uint32($buffer);
...

您还可以添加多记录“shifter”:

my ($val1, $val2, $val3) = shift_multi($buffer, qw(varint string uint32));

如果您需要更快的速度,您还可以编写一个编译器,它可以将一组类型转换为一个解包子。

关于perl - 你能扩展 pack() 来处理自定义的可变长度字段吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24798648/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com