`
ordinary
  • 浏览: 77266 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

Base 128 Varints

阅读更多

 Google Protobuf里面提出了“Base 128 Varints”编码,这是一种变字节长度的编码,官方描述为:varints是用一个或多个字节序列化整形的一种方法。我理解要点有三个(1)操作是序列化(2)操作对象是整形(3)变长编码。重点是最后一点,他是如何编码的呢?

       (1)除了最后一个字节,varint中的每个字节的最高位设为1,表示后面还有字节出现

       (2)每个字节的低7位看成是一个组(group),这个组和他相邻的下一个7位组共同存储某个整形的“组合表示”,最低有效组在前面。

    上面的定义可能比较生硬,我没看具体例子之前,也没搞明白,我们来看http://code.google.com/intl/zh-CN/apis/protocolbuffers/docs/encoding.html#varints中的例子:

        (1)一个字节。下面只有一个字节,所以最高位是0,表示十进制1

            0000 0001

        (2)两个字节。

            1010 1100 0000 0010

        由于第一个字节后面还有一个字节,所以第一个字节的最高位设置为1,表示后面还有后继字节,第二个字节的最高位为0。去掉每个字节的最高位,我们对两个字节进行分组。第一个7位组:0101100,第二个7位组:0000010,组合起来就是:0101100 0000010,由于最低有效组在前面,所以两个7位组进行调换,结果为:0000010  0101100,中间的空格是为了大家区分,去掉前面的0,也就是:100101100,十进制为1*2^8 + 1*2^5 + 1*2^3 + 1*2^2 = 256 + 32 + 8 + 4 = 300。

       (3)三个字节。我们换种方式,给定某个整形,要求写出他的varint表示,这里当然是落在需要3个字节表示的整形。16380可以吗?不可以!因为16380 < 2^14,所以2个字节足以,我们就以27491为例,27491的二进制表示为:

                     0110 1011 0110 0011

        注意这里是高字节之前,低字节在后,和varint的编码规则相反,首先按照7位一组划分为:0000001 1010110  1100011然后反转为:1100011 1010110  0000001,最后将末尾的7位组前面补0组成一个字节,两个7位组都补1分别组成一个字节:

                     11100011 11010110  00000001

       (4)更多字节。聪明的你可能发现,varint编码中4个字节最大表示的数为2^28,非常正确,同时说明了天下没有免费的午餐,有得有失。Protobuf引入了fixed32解决这个问题的,如果某个字段经常大于2^28,应当优选fixed32,他是固定长度为32位的。

     三.String和bytes

     string和bytes的表示形式一致,都是“长度+值”,其中长度采用varint编码,值为字符序列或者二进制码流

分享到:
评论
1 楼 yhxf_ie 2017-03-24  
             通俗易懂

相关推荐

    Protocol Buffers 入门应用

    NULL 博文链接:https://lfl2011.iteye.com/blog/2136272

    Protocol Buffers协议编码规则

    它是以Base 128 Varints编码基础, varints是一种将一个整数序列化为一个或者多个Bytes的方法,越小的整数,使用的Bytes越少。 基本规则 1.每个Byte的最高位(msb)是标志位,如果该位为1,表示该Byte后面还有其它Byte...

    Python库 | base128-0.1.1-py3-none-any.whl

    资源分类:Python库 所属语言:Python 使用前提:需要解压 资源全名:base128-0.1.1-py3-none-any.whl 资源来源:官方 安装方法:https://lanzao.blog.csdn.net/article/details/101784059

    这个是base的解码工具

    有base的乱码,他可以解决 http://u.115.com/file/clnern84# Base解码工具.exe

    Base64 编码 解码器 V1.6

    这是一个很好的Base64编-解码工具.转换很方便,支持中文,支持UTF-8,Unicode编码,可对对图片数据进行解码。  Base64是网络上最常见的用于传输8Bit字节代码的编码方式之一,可以参见RFC2045~RFC2049,上面有MIME...

    AES-128-CBC加密Base64编码Demo

    AES-128-CBC加密Base64编码Demo,亲测有效。而且 直接引入了BASE 64编码类 非常方便。不过只有加密算法

    nodejs的base64和aes-128-ecb加密.rar

    nodejs的base64和aes-128-ecb加密.rar

    base16 base32 base64 C语言代码

    base16,base32,base64C语言实现代码,高效率运行,非常实用。

    Base64.dll(Base64编解码,附VB示例)

    Base64编码和解码库,支持API调用和COM调用,输入参数支持VB的字节数组Byte(),输出支持VB的字节数组Byte()和...Public Declare Sub DecodeFromVBStringEx Lib "Base64" (ByRef Dest() As Byte, ByRef Src As String)

    JS 版本的base64函数实现(base64encode,base64decode)

    用js实现的base64encode,base64decode函数. 包括: function base64encode(str) { function base64decode(str) { function utf16to8(str) { function utf8to16(str) { function doit() {

    aes128base64_aes128_

    基于单片机 C 语言通用AES128加密算法

    ctf base全家桶递归解密

    ctf base全家桶递归解密,只要是常见base(base16、base32、base58、base85、base91、base92、base100)系加密,不管加多少层都能解出来

    pb-base64.zip

    pb10调用base64.dll,实现将图片转换成base64编码,将base64编码转换成图片 函数声明 function long GetFileEncode64(ref string filename, ref string encode64)library "base64" alias for "GetFileEncode64;...

    sun.misc.BASE64Decoder(Android Base64Jar包以及Java源代码)

    sun.misc.BASE64Decoder 其中包括 Android Base64Jar包 以及Java源代码 sun.misc.BASE64Decoder 其中包括 Android Base64Jar包 以及Java源代码 sun.misc.BASE64Decoder 其中包括 Android Base64Jar包 以及...

    js的base64(base64.js)

    js的base64(base64.js)

    labview 图片缩放 base64编码base64解码

    labview 图片缩放 base64编码base64解码

    js的base64和base32加密函数

    js的base64和base32加密函数 ajax通过get方式传递中文参数特殊符号的参数避免乱码终极解决方案.

    sun.misc.BASE64Decoder和sun.misc.BASE64Encoder不可用已解决

    最近项目实验发现导入工具程序后项目有错,查看发现sun.misc.BASE64Decoder和sun.misc.BASE64Encoder不可用,找不到相应的类。 二、原因分析 冲浪后发现JDK中的lib\tools.jar和JRE中的lib\rt.jar已从Java SE 9中...

    c# 用Base64实现文件上传

    Base64是网络上最常见的用于传输8Bit字节码的编码方式之一,它是一种基于64个可打印字符来表示二进制数据的方法。  使用base64进行文件上传的具体流程是:前台使用js将文件转换为base64格式,后台通过高级编程语言...

Global site tag (gtag.js) - Google Analytics