古典密碼--->凱撒密碼
一丶凱撒密碼
1.1 什么是凱撒密碼
凱撒密碼,想必很多人聽說過.沒聽說過的簡單說一下.
相傳在很久很久以前,有一位皇帝,叫做 尤利烏斯 · 凱撒 為了縮短名字,我們稱為凱撒大帝.是在公元前100年左右單身與古羅馬,是一名著名的軍事統帥.由它發明的密碼.叫做凱撒密碼
1.2 凱撒密碼的加密原理
凱撒密碼其實很簡單. 需要我們理解 平移概念 ,就是將 一段數據 平移多少位, 最后解密的時候進行反平移即可得出.
以字母 a-z來說 我們將a 進行平移3位得出密文
如下圖:
將a 平移三位,得出 D b則是E 以此類推. 如果到達末尾,則從頭開始. 例如Z 是字母的末尾.平移三位則是 C
那么由此得出公式
密文 = 函數(明文 + 平移位數(key) Mod 26;
明文 = 函數(密文 - 平移位數(key) mod 26;
其中 密文 明文 函數 平移位數 等都是有英文含義的.
所以我們很多時候都能看到如下寫法
c = E(p + k) mod 26
p = D(c - k) mod 26
C = Ciphertext 英文意思 是密碼密文的意思
p = plainttext 英文意思 是明文的意思,也就是未加密之前的數據
E = encrypt 英文的意思是加密的意思. 放在我們編程中則可以理解為是一個方法.專門用於加密的方法
D = Decrypt 英文意思是 解密的意思 同加密一樣
k = key 英文意思是鑰匙的意思. 也就是解密的鑰匙或者加密的鑰匙
mod 數學上 取余數的意思 10 % 2 == 0 取得余數為0
綜上所述,大概是了解以下基本的術語
密文 = 加密函數(明文 + key) % 26
明文 = 解密函數(密文 - key) % 26
1.3 凱撒密碼的破解
其實凱撒密碼是非常好破解的. 假設你不知道明文.只知道密文.那么總是可以嘗試出來的. 總共是26次.依次破解. 我們常聽的暴力破解就是這個意思. 也稱為窮舉
那怎么知道凱撒密碼破解出來是否正確. 是這樣的. 明文一般都是有意義的.當你用密文破解的時候會出現很多無意義的數據.而有些數據是很有意義的.所以我可推斷以下.假設不是.那么總過26組破解密碼.一個一個嘗試也能知道的.
二丶凱撒密碼代碼編寫
2.1 C/C++代碼,編寫加解密函數
既然我們知道了公式
c = e(p + k) % 26
那么我們根據公式來即可
代碼
void Entrypt(IN char* PlaintText, IN int PlaintTextSize, OUT char* CipText)
{
//加密PlaintText
for (auto i = 0; i < PlaintTextSize; i++)
{
/*
1.首先字符 - 字符'a'得出下標.
2.下標 + 則是代表假面
3.如果是加密,怎么下標不能超過26. 所以 % 26
4.計算完的結果 加上'a' 就等於實際加密的密文了
*/
char ch = (PlaintText[i] - 'a' + 3); //得出下標
char ch1 = ch % 26 + 'a'; //得出實際密文
//接受的密文數組
CipText[i] = ch1;
}
return;
}
//解密數據,與加密相反
void Detrypt(IN char* CipText, IN int CipTextSize, OUT char* PlaintText)
{
//加密PlaintText
for (auto i = 0; i < CipTextSize; i++)
{
/*
1.首先字符 - 字符'a'得出下標.
2.下標 - 則是代表解密
3.如果是- 則會出現復數情況, 如 a的下標為0 a - 3 = 負數. 那么需要加26進行調整. 調整之后是絕對不會超過26的
4.雖然不會超過.但是也要 % 26.因為如果是正數的情況,如果你加26那么還是會超過26
*/
char ch = (CipText[i] - 'a' - 3); //得出下標
char ch1 = (ch + 26); //負數調整,
char ch3 = ch1 % 26 + 'a'; //正數 % 26得出下標,下標 + 'a'
//接受的密文數組
PlaintText[i] = ch3;
}
return;
}
int main()
{
//c = entrypt(p + k) % 26
//char szBuffer[] = "ibinary";
char PlaintText[] = "ibinary";
char CipText[8] = { 0 };
char PlanitText1[8] = { 0 };
Entrypt(PlaintText, strlen(PlaintText), CipText);
printf("加密明文后的密文 = %s \r\n", CipText);
Detrypt(CipText, strlen(CipText), PlanitText1);
printf("解密密文后的明文 = %s \r\n", PlanitText1);
system("pause");
return 0;
}