Base32 应用与原理解析

纵然是瞬间 提交于 2020-08-06 06:57:47

  简介:

  Base32编码使用32个ASCII字符对任何数据进行编码,Base32与Base64的实现原理类似,同样是将原数据二进制形式取指定位数转换为ASCII码。首先获取数据的二进制形式,将其串联起来,每5个比特为一组进行切分,每一组内的5个比特可转换到指定的32个ASCII字符中的一个,将转换后的ASCII字符连接起来,就是编码后的数据。

  字典:

  Base32依赖更小的字典,Base32编码时每5个字符为一个分组,字典的长度为25 + 1=33。

  Base32通用的字典定义如下:

Value Encoding Value Encoding Value Encoding Value Encoding
0 A 9 J 18 S 27 3
1 B 10 K 19 T 28 4
2 C 11 L 20 U 29 5
3 D 12 M 21 V 30 6
4 E 13 N 22 W 31 7
5 F 14 O 23 X padding =
6 G 15 P 24 Y
7 H 16 Q 25 Z
8 I 17 R 26 2

  Base32还提供了另外一种字典定义,即Base32十六进制字母表。Base32十六进制字母表是参照十六进制的计数规则定义:

Value Encoding Value Encoding Value Encoding Value Encoding
0 0 9 9 18 I 27 R
1 1 10 A 19 J 28 S
2 2 11 B 20 K 29 T
3 3 12 C 21 L 30 U
4 4 13 D 22 M 31 V
5 5 14 E 23 N padding =
6 6 15 F 24 O
7 7 16 G 25 P
8 8 17 H 26 Q

  两种字典没有本质的区别,只是字典不同而已。

  演示示例:

​  很多开源库都为Base32提供了实现,例如dnsjava和commons-codec,maven坐标如下:

  dnsjava:

<dependency>
    <groupId>dnsjava</groupId>
    <artifactId>dnsjava</artifactId>
    <version>3.1.0</version>
</dependency>

  commons-codec:

<dependency>
    <groupId>commons-codec</groupId>
  	<artifactId>commons-codec</artifactId>
  	<version>1.9</version>
</dependency>

  依赖dnsjava的Base32示例:

package com.securitit.serialize.bs64;

import org.xbill.DNS.utils.base32;

public class Base32Tester {

	public static void main(String[] args) throws Exception {
		base32 bs32 = null;
		base32 bs32hex = null;
		String plainStr = null;
		String bs32Str = null;
		byte[] plainBts = null;

		bs32 = new base32(base32.Alphabet.BASE32, true, false);
		bs32hex = new base32(base32.Alphabet.BASE32HEX, true, false);
		// 原文内容.
		plainStr = "Hello Base32!Now this is testing Base32!Please see the result!";
		plainBts = plainStr.getBytes("UTF-8");
		// Base32测试.
		bs32Str = bs32.toString(plainBts);
		System.out.println("Base32编码结果:" + bs32Str);
		plainBts = bs32.fromString(bs32Str);
		plainStr = new String(plainBts, "UTF-8");
		System.out.println("Base32解码结果:" + plainStr);
		System.out.println("==================================================");
		// Base32Hex测试.
		bs32Str = bs32hex.toString(plainBts);
		System.out.println("Base32Hex编码结果:" + bs32Str);
		plainBts = bs32hex.fromString(bs32Str);
		plainStr = new String(plainBts, "UTF-8");
		System.out.println("Base32Hex解码结果:" + plainStr);
	}

}

  输出结果:

Base32编码结果:JBSWY3DPEBBGC43FGMZO7PEBJZXXOIDUNBUXGIDJOMQHIZLTORUW4ZZAIJQXGZJTGLX3ZAKQNRSWC43FEBZWKZJAORUGKIDSMVZXK3DU566IC===
Base32解码结果:Hello Base32!Now this is testing Base32!Please see the result!
==================================================
Base32Hex编码结果:91IMOR3F41162SR56CPEVF419PNNE83KD1KN6839ECG78PBJEHKMSPP089GN6P9J6BNRP0AGDHIM2SR541PMAP90EHK6A83ICLPNAR3KTUU82===
Base32Hex解码结果:Hello Base32!Now this is testing Base32!Please see the result!

  依赖commons-codec的Base32示例:

package com.securitit.serialize.base32;

import org.apache.commons.codec.binary.Base32;

public class Base32Tester {

	public static void main(String[] args) throws Exception {
		Base32 bs32 = null;
		Base32 bs32hex = null;
		String plainStr = null;
		String bs32Str = null;
		byte[] plainBts = null;
		
		bs32 = new Base32();
		bs32hex = new Base32(true);
		// 原文内容.
		plainStr = "Hello Base32!Now this is testing Base32!Please see the result!";
		plainBts = plainStr.getBytes("UTF-8");
		// Base32测试.
		bs32Str = bs32.encodeAsString(plainBts);
		System.out.println("Base32编码结果:" + bs32Str);
		plainBts = bs32.decode(bs32Str);
		plainStr = new String(plainBts, "UTF-8");
		System.out.println("Base32解码结果:" + plainStr);
		System.out.println("==================================================");
		// Base32Hex测试.
		bs32Str = bs32hex.encodeAsString(plainBts);
		System.out.println("Base32Hex编码结果:" + bs32Str);
		plainBts = bs32hex.decode(bs32Str);
		plainStr = new String(plainBts, "UTF-8");
		System.out.println("Base32Hex解码结果:" + plainStr);
	}
	
}

  输出结果:

Base32编码结果:JBSWY3DPEBBGC43FGMZO7PEBJZXXOIDUNBUXGIDJOMQHIZLTORUW4ZZAIJQXGZJTGLX3ZAKQNRSWC43FEBZWKZJAORUGKIDSMVZXK3DU566IC===
Base32解码结果:Hello Base32!Now this is testing Base32!Please see the result!
==================================================
Base32Hex编码结果:91IMOR3F41162SR56CPEVF419PNNE83KD1KN6839ECG78PBJEHKMSPP089GN6P9J6BNRP0AGDHIM2SR541PMAP90EHK6A83ICLPNAR3KTUU82===
Base32Hex解码结果:Hello Base32!Now this is testing Base32!Please see the result!

  总结:

  Base32与Base64优劣对比:

  · Base32使用了更小的字典,Base32包含33个字符(0-9A-V=),Base64包含65个字符(a-zA-Z0-9+/=或a-zA-Z0-9-_=)。

  · Base32编码规则是5比特为一分组,Base64编码规则是6比特为一分组。

  · 由于编码规则的不同,Base32无法完全切分数据,需要使用=补位, 补位的个数在{0,1,2, 3, 4}范围之内;Base64无法完全切分数据,需要使用=补位, 补位的个数在{0,1,2}范围之内。

  · Base32编码后数据会膨胀3/8,Base64编码后数据会膨胀1/3。

  · Base32和Base64均包含特殊字符,在URL传输等场景下需要尤为注意特殊字符的处理。

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!