base64의 원리와 파이썬의 인코딩 및 디코딩 구현

base64

base64 소개

base64는 64 개의 인쇄 가능한 문자를 기반으로 이진 데이터를 나타내는 표현 방법입니다. 2 6 = 64이므로 모든 6 비트는 인쇄 가능한 특정 문자에 해당하는 단위입니다. 3 바이트는 4 base64 단위에 해당하는 24 비트를 갖습니다. 즉, 임의의 이진 데이터의 3 바이트는 4 개의 인쇄 가능한 문자로 표현 될 수 있습니다. base64에서 인쇄 가능한 문자에는 A ~ Z, a ~ z, 0 ~ 9, 총 62 자, + 및 / 문자가 포함됩니다. Base64는 MIME 이메일, XML 복합 데이터 등을 포함한 일부 이진 데이터를 표현, 전송 및 저장하기 위해 텍스트 데이터 만 처리 할 수있는 경우에 자주 사용됩니다.

base64 인코딩 테이블

기존 base64 코딩 테이블 :
ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789 + /
사용자는 가변 테이블 base64 코딩 및 디코딩을 실현하기 위해 필요에 따라 코딩 테이블 요소 또는 요소의 순서를 변경할 수 있습니다.

base64 인코딩의 원리

인코딩시 3 바이트의 데이터가 24 비트 버퍼에 차례로 들어가고 첫 번째 바이트가 상위 비트를 차지합니다. 데이터가 3 바이트 미만이면 버퍼의 나머지 비트가 0으로 충분하지 않습니다. 높은 값에서 낮은 값으로 매번 6 비트를 꺼내 모든 입력 데이터 변환이 완료 될 때까지 인코딩 테이블의 해당 문자를 10 진수 값에 따라 인코딩 된 출력으로 꺼냅니다.
예를 들어 "Man"
base64 이론
으로 인코딩 할 바이트 수를 3으로 나눌 수없고 끝에 1 또는 2 바이트가 더있는 경우 다음 방법을 사용하여 처리 할 수 ​​있습니다. 먼저 0 바이트 값을 사용하여 따라서 인코딩 할 바이트 수를 3으로 나눌 수 있으며 base64 인코딩이 수행됩니다. 보완 할 바이트 수를 나타내는 인코딩 된 base64 텍스트 뒤에 1 개 또는 2 개의 등호 "="를 추가합니다. 즉, 끝에 1 옥텟 (1 바이트)이 남아있는 경우 마지막 6 비트 base64 바이트 블록에는 값이 0 인 4 비트가 있고 끝에 두 개의 등호 "="가 추가됩니다. 마지막 2 옥텟 (2 바이트)이 남아있는 경우 마지막 6 비트 base64 바이트 블록에는 값이 0 인 2 비트가 있고 끝에 등호 "="가 추가됩니다.
예를 들어 "A"와 "BC"를 별도로 인코딩합니다.
base64 이론
따라서 base64 인코딩을 식별하는 한 가지 방법은 끝에 등호 "="가 있는지 확인하는 것입니다. 그러나이 인식 방법은 만병 통치약이 아니며 인코딩 된 문자 길이가 정확히 3의 배수 인 경우 인코딩 된 문자열 끝에 등호 "="가 표시되지 않습니다.

base64 인코딩 및 디코딩의 Python 구현

#coding:utf-8
#base="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"  原表
base=[0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A,
  0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, 0x51, 0x52, 0x53, 0x54,
  0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x61, 0x62, 0x63, 0x64,
  0x65, 0x66, 0x67, 0x68, 0x69, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E,
  0x6F, 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78,
  0x79, 0x7A, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
  0x38, 0x39, 0x2B, 0x2F]  #原表的ascii码表示,方便进行原表变换
#对原表进行变换,不要变表时,注释掉原表变换的代码即可
#for i in range(0,10):
    #base[i],base[19-i]=base[19-i],base[i]
#base_changed是变表,需要转成字符串的形式
base_changed=''.join(chr(i) for i in base)
print("Current Base:\n%s " %base_changed) #打印base_changed变表
def base64_encode(inputs):    #inputs是待编码的字符串
    # 将字符串转化为2进制
    bin_str = []
    for i in inputs:
        x = str(bin(ord(i))).replace('0b', '')
        bin_str.append('{:0>8}'.format(x))
    # 输出的字符串
    outputs = ""
    # 不够三倍数,需补齐的次数
    nums = 0
    while bin_str:
        # 每次取三个字符的二进制
        temp_list = bin_str[:3]
        if (len(temp_list) != 3):
            nums = 3 - len(temp_list)
            while len(temp_list) < 3:
                temp_list += ['0' * 8]
        temp_str = "".join(temp_list)
        # 将三个8字节的二进制转换为4个十进制
        temp_str_list = []
        for i in range(0, 4):
            temp_str_list.append(int(temp_str[i * 6:(i + 1) * 6], 2))
        if nums:
            temp_str_list = temp_str_list[0:4 - nums]
        for i in temp_str_list:
            outputs += base_changed[i]
        bin_str = bin_str[3:]
    outputs += nums * '='
    print("Encoded String:\n%s " % outputs)
def base64_decode(inputs): #inputs是base64字符串
    # 将字符串转化为2进制
    bin_str = []
    for i in inputs:
        if i != '=':
            x = str(bin(base_changed.index(i))).replace('0b', '')
            bin_str.append('{:0>6}'.format(x))
    # 输出的字符串
    outputs = ""
    nums = inputs.count('=')
    while bin_str:
        temp_list = bin_str[:4]
        temp_str = "".join(temp_list)
        # 补足8位字节
        if (len(temp_str) % 8 != 0):
            temp_str = temp_str[0:-1 * nums * 2]
        # 将四个6字节的二进制转换为三个字符
        for i in range(0, int(len(temp_str) / 8)):
            outputs += chr(int(temp_str[i * 8:(i + 1) * 8], 2))
        bin_str = bin_str[4:]
    print("Decoded String:\n%s " % outputs)
#plain是待编码的字符串
plain="This_is_a_base64_example"
base64_encode(plain)
#enc是经base64编码的字符串
enc="VGhpc19pc19hX2Jhc2U2NF9leGFtcGxl"
base64_decode(enc)

가동 결과
base64 스크립트

기타 기본 인코딩

base16

2 4 = 16
base16 인코딩 테이블 :
0123456789ABCDEF는
실제로 16 진수 (16 진수) 인코딩입니다.

base32

2 5 = 32
base32 인코딩 테이블 :
ABCDEFGHIJKLMNOPQRSTUVWXYZ234567

base36, base58, base62, base85, base91, base92

기본 시리즈 코딩 분석을 참조하십시오.

추천

출처blog.csdn.net/weixin_45582916/article/details/113772477