ruby base64通过以2位字符开头来编码128位数字,以防止结尾填充 [英] ruby base64 encode 128 bit number by starting with a 2 bit character to prevent padding at the end

查看:144
本文介绍了ruby base64通过以2位字符开头来编码128位数字,以防止结尾填充的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这个问题是我在这里之前的问题的跟进:

This question is a follow up to my previous question here: How can I convert a UUID to a string using a custom character set in Ruby? But I will try to formulate it as a separate and specific question.

我确实有一个Ruby 128位UUID作为十六进制值:

I do have a Ruby 128 bit UUID as hex value:

SecureRandom.uuid #=> "2d931510-d99f-494a-8c67-87feb05e1594"

如果我正确地获得了IFC规范( http://www.buildingsmart-tech.org/ifc/IFC2x3/TC1/html/ifcutilityresource/lexical/ifcgloballyuniqueid.htm ),我想对此进行Base64编码,但不要在最后添加填充,我希望输出以2位字符(4个选项)开头,而不是6位(需要64个选项).

If I get the IFC specification correctly (http://www.buildingsmart-tech.org/ifc/IFC2x3/TC1/html/ifcutilityresource/lexical/ifcgloballyuniqueid.htm), I want to Base64 encode this, but instead of getting padding at the end, I want the output to begin with a 2bit character(4 options), instead of 6 bits(needed for 64 options).

这样,我想我可以得到一个22个字符的字符串(1个2位,和21个6位,总共128位).

This way I think I can end up with a string of 22 characters (1 of 2bits, and 21 of 6bits for a total of 128 bits).

是否可以通过这种方式调整Ruby base64?

Is it possible to tweak the Ruby base64 in this way?

推荐答案

简短答案:否.从技术上讲,这不是标准的Base64,因此Ruby的标准库不会处理它.

Short answer: no. Technically speaking, that is not standard Base64 so Ruby's standard lib will not deal with it.

Ruby的Base64库将其输入作为字节,因此您需要将输入数据除以8.但是,您希望UUID前面有4个零位,所以它是4 + 128 = 132,所以下一个最接近的倍数8是136,即17个字节.您可以在最后丢弃多余的随机性:

Ruby's Base64 lib takes its input as bytes, so you need to get your input data to be divisible by 8. But you want 4 zero bits in front of your UUID, so that's 4+128=132 so the next closest multiple of 8 is 136 i.e. 17 bytes. You can discard the extra randomness at the end:

x = SecureRandom.gen_random 17   # get a little extra randomness
x[0] = (x[0].ord & 0x0f).chr     # 0 out the first four bits
Base64.strict_encode64(x)[0...22] # discard extra randomness

这种方法的一个缺点是您的128位UUID在x内部怪异地对齐并且很难单独查看.如果要取出128位,可以使用一些打包/拆包的方法:

The one downside of this approach is that your 128 bit UUID is weirdly aligned inside x and hard to see on its own. If you want to get the 128 bits out you can do that with some pack/unpack:

[x.unpack("B*")[0][4...132]].pack("B*")

这篇关于ruby base64通过以2位字符开头来编码128位数字,以防止结尾填充的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆