数据安全02-Base64 算法原理

2020-10-27 10:29:51 浏览数 (1)

用途
  1. 表示二进制数据,可用于传输二进制数据,如文件、缩略图等
  2. 对数据起一定加密效果
转换原理

    Base64算法,是用64个可打印字符表示二进制所有数据方法。Base64字符成包含A—Z,a—z,0—9, ,/ ,他们编码对应表如下。

编码表编码表

    一个Base64字符编码转换成二进制都是8个bit位,而前两位都00,有效数字只有6个bit位,也就是说只需要6个bit位就能表示1个Base64字符,而正常的字符是使用8个bit位表示, 8和6的最小公倍数是24,所以4个Base64字符可以表示3个标准的ascii字符。

    按照以上原理,我们将要加密的明文对应的ascii值转换成二进制并拼接在一起,将其分为每6个bit为一份,每4份为一组。不够6个bit位的用0补充,不够4份的用=补充。根据base64编码表将每一份转成对应的Base64字符,得到的也就是密文。

转换过程
  1. 得到明文每一个字符对应的ascii码
  2. 将ascii码转换成二进制,并拼接在一起
  3. 将拼接在一起的二进制,分为6个bit位为一份,4份为一组
  4. 将每一份根据base64编码表转换成base64字符
  5. 最后不够6个bit位的用0补充,不够一组的用=补充为4份
实践
不需要补充0或=(明文:Man)
  1. 将明文每一个字符对应的ascii码 M 对应ascii码 :77 a 对应ascii码 :97 n 对应ascii码 :110
  2. 将ascii码转换成二进制,并拼接在一起 77 二进制 : 01001101 97 二进制 : 01100001 110 二进制 : 01101110 拼接 : 010011010110000101101110
  3. 分为6个bit位为一份,4份为一组 010011 010110 000101 101110
  4. 每一份根据base64编码表转换成base64字符 010011 十进制 : 19 : base64字符 : T 010110 十进制 : 22 : base64字符 : W 000101 十进制 : 5 : base64字符 : F 101110 十进制 : 46 : base64字符 : u
  5. 详解图 详解图详解图
需要补充0或=(明文:BC)
  1. 将明文每一个字符对应的ascii码 B 对应ascii码 :66 C 对应ascii码 :67
  2. 将ascii码转换成二进制,并拼接在一起 66 二进制 : 01000010 67 二进制 : 01000011 拼接 : 0100001001000011
  3. 分为6个bit位为一份,4份为一组,补充0和= 010000 100100 001100 xxxxxx
  4. 每一份根据base64编码表转换成base64字符 010000 十进制 : 16 : base64字符 : Q 100100 十进制 : 36 : base64字符 : k 001100 十进制 : 12 : base64字符 : M xxxxxx : base64字符 : =
  5. 详解图 详解图详解图
使用

    java中早已提供以上算法的jar包,不用自己去实现以上算法,个人倾向使用apache提供的

代码语言:txt复制
import org.apache.commons.codec.binary.Base64;

private static final String ENCODING_UTF8 = "UTF-8";

/**
 * 二进制数据编码为BASE64字符串,根据isChunked是否输出换行
 */
public static String encodeBase64(byte[] bytes, boolean isChunked) {
    try {
        return new String(Base64.encodeBase64(bytes, isChunked), ENCODING_UTF8);
    } catch (UnsupportedEncodingException e) {
        logger.error(e.getMessage(), e);
        return "";
    }
}

/**
 * BASE64解码
 */
public static byte[] decodeBase64(String encodedStr) {
    byte[] result;
    try {
        result = Base64.decodeBase64(encodedStr);
    } catch (Exception e) {
        logger.error(e.getMessage(), e);
        return null;
    }
    return result;
}
彩蛋

    ASCII码总共128个,用来表示英文字母、数字以及英文标点符号。而简体中文、繁体中文、日文以及韩文等都是用多字节来存储的,通常称之为多字节字符。因为Base编码的输入是字符串的编码,不同编码的字符串的Base64结果是不同的

    个人觉得用base64传输缩略图,非常合适,客户端收到base64字符后,就可以显示图片,而不用依赖网络了。这样至少可以保证缩略图一定能显示出来。但是通过以上算法,可以发现base64后的字符串大小是原来的4/3.

0 人点赞