2023.10.22
Base64的简介
Base64就是包括小写字母
a-z
,大写字母A-Z
,数字0-9
,符号+
和/
组成的64个字符的字符集,另外包括填充字符=
。任何符号都可以转换成这个字符集中的字符,这个转化过程就叫做Base64编码。
Base64实现方式
Base64编码要求把3个8位字节转化为4个6位的字节,之后在6位的前面补两个0,形成8位一个字节的形式。如果剩下的字符不足3个字节,则用0填充,输出字符使用
=
,因此编码后输出的文本末尾可能会出现1个或2个=
。
编码表
0 | A | 16 | Q | 32 | g | 48 | w |
1 | B | 17 | R | 33 | h | 49 | x |
2 | C | 18 | S | 34 | i | 50 | y |
3 | D | 19 | T | 35 | j | 51 | z |
4 | E | 20 | U | 36 | k | 52 | 0 |
5 | F | 21 | V | 37 | l | 53 | 1 |
6 | G | 22 | W | 38 | m | 54 | 2 |
7 | H | 23 | X | 39 | n | 55 | 3 |
8 | I | 24 | Y | 40 | o | 56 | 4 |
9 | J | 25 | Z | 41 | p | 57 | 5 |
10 | K | 26 | a | 42 | q | 58 | 6 |
11 | L | 27 | b | 43 | r | 59 | 7 |
12 | M | 28 | c | 44 | s | 60 | 8 |
13 | N | 29 | d | 45 | t | 61 | 9 |
14 | O | 30 | e | 46 | u | 62 | + |
15 | P | 31 | f | 47 | v | 63 | / |
编码过程
以 flag 为例
f | l | a | g | |||||
ASCII二进制 | 01100110 | 01101100 | 01100001 | 01100111 | ||||
合并 | 01100110011011000110000101100111 | |||||||
6bit为一组 | 011001 | 100110 | 110001 | 100001 | 011001 | 110000 | 000000 | 000000 |
高位补0 | 00011001 | 00100110 | 00110001 | 00100001 | 00011001 | 00110000 | 00000000 | 00000000 |
对应编码表索引 | 25 | 38 | 49 | 33 | 25 | 48 | ||
对应编码表字符 | Z | m | x | h | Z | w | = | = |
转换结果 | ZmxhZw== |
python加解密脚本实现
# Base64编码
def base64_encode(plain_text):
# Base64字符集
b64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
# 将文本转换为二进制字符串
binary_text = ''.join(format(ord(c), '08b') for c in plain_text)
# 补齐长度到6的整数倍
binary_text += '0' * ((6 - len(binary_text) % 6) % 6)
# 将6位二进制转换为Base64字符
base64_text = ''.join(b64[int(binary_text[i:i+6], 2)] for i in range(0, len(binary_text), 6))
# 在末尾补齐=
base64_text += '=' * ((4 - len(binary_text) // 6) % 4)
return base64_text
# Base64解码
def base64_decode(base64_text):
# Base64字符集
b64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
# 去除末尾的=
base64_text = base64_text.rstrip('=')
# 将Base64字符转换为二进制字符串
binary_text = ''.join(format(b64.index(c), '06b') for c in base64_text)
# 将8位二进制转换为字符
plain_text = ''.join(chr(int(binary_text[i:i+8], 2)) for i in range(0, len(binary_text), 8))
return plain_text
# 主函数
def main():
# 用户选择操作类型
num = int(input("请选择你要输入的类型的序号:\n1、加密\n2、解密\n----------\n输入序号:"))
if num == 1:
# 加密
plain_text = input("请输入:\n")
print("加密完成:\n", base64_encode(plain_text))
elif num == 2:
# 解密
cipher_text = input("请输入:\n")
print("解密完成:\n", base64_decode(cipher_text))
else:
print("输入错误")
if __name__ == "__main__":
main()
C++加解密脚本实现
//#include <bits/stdc++.h> //引用所有头文件,学习时慎用
#include <iostream>
#include <vector>
#include <string>
#include <sstream>
#include <bitset>
using namespace std;
const string base64_code = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
//编码
string base64_encode(string plain_text)
{
string base64_text, binary_text;
//转为 8bit 二进制
for(char i: plain_text)
binary_text.append(bitset<8>(static_cast<int>(i)).to_string());
//将长度补齐先到 6 的整数倍
binary_text.append((6 - binary_text.length() %6) %6,'0');
//按 6bit 为一组分割字符串并进行编码
for (int i = 0, len = binary_text.length(); i < len; i += 6)
base64_text += base64_code[stoi(binary_text.substr(i,6), nullptr, 2)];
//在末尾加上 0~3 个=
base64_text.append(((4 - binary_text.length() /6)) %4 %4,'=');
return base64_text;
}
string base64_decode(string base64_text)
{
string plain_text, binary_text;
//转为 6bit 二进制
for (auto i: base64_text)
if (i!='=')
binary_text.append(bitset<6>(base64_code.find(i)).to_string());
//按 8bit 为一组分割字符串并进行解码
for (int i = 0, len = binary_text.length()-binary_text.length()%8; i < len; i += 8)
plain_text.push_back(static_cast<char>(stoi(binary_text.substr(i,8), nullptr, 2)));
return plain_text;
}
int main()
{
int num;
string plain_text,cipher_text;
cout << "请选择你要输入的类型的序号:\n1、加密\n2、解密\n----------\n输入序号:";
cin >> num;cin.get();
switch(num)
{
case 1:
cout << "请输入:" << endl;
getline(cin,plain_text);
cout << "加密完成:\n" <<base64_encode(plain_text);
break;
case 2:
cout << "请输入:" << endl;
getline(cin,cipher_text);
cout << "解密完成:\n" << base64_decode(cipher_text);
break;
default:
cout << "输入错误" << endl;
break;
}
}