一些基础密码算法的实现
把以前写过的几个小算法稍整理下子。
1.多表替代密码:
1 #include<iostream> 2 #include<cstdlib> 3 #include<cstdio> 4 #include<string> 5 using namespace std; 6 7 int gcd(int a,int b); //求最大公约数; 8 void jiam(string words,int* A);//加密; 9 void jiem(string words,int* A);//解密。 10 int main() 11 { 12 int A[9],i,tmp; 13 string words; 14 bool r; 15 cout<<"请随意输入一个整数,来改变随机种子:"; 16 cin>>i; 17 srand(i); 18 getchar(); 19 cout<<"系统随机生成一个三阶矩阵:"<<endl; 20 t: 21 for(i=0;i<9;i++) 22 { 23 A[i]=rand()%26; 24 } 25 tmp=A[0]*(A[4]*A[8]-A[5]*A[7])-A[1]*(A[3]*A[8]-A[5]*A[6])+A[2]*(A[3]*A[7]-A[4]*A[6]); 26 if(gcd(tmp,26)!=1) 27 goto t; 28 for(i=0;i<9;i++) 29 { 30 if(i==2||i==5||i==8) 31 cout<<A[i]<<";"<<endl; 32 else 33 cout<<A[i]<<" "; 34 } 35 cout<<endl; 36 cout<<"请输入明文或密文(大写):"; 37 getline(cin,words); 38 cout<<"加密(0)?解密(1)?请输入 0 or 1:"; 39 cin>>r; 40 if(r==0) 41 jiam(words,A); 42 else 43 jiem(words,A); 44 return 0; 45 } 46 void jiam(string words,int* A) 47 { 48 int i; 49 for(i=0;i<words.length();i+=3) 50 { 51 cout<<char((A[0]*(int(words[i])-65)+A[1]*(int(words[i+1])-65)+A[2]*(int(words[i+2])-65))%26+65); 52 cout<<char((A[3]*(int(words[i])-65)+A[4]*(int(words[i+1])-65)+A[5]*(int(words[i+2])-65))%26+65); 53 cout<<char((A[6]*(int(words[i])-65)+A[7]*(int(words[i+1])-65)+A[8]*(int(words[i+2])-65))%26+65); 54 } 55 cout<<endl; 56 } 57 void jiem(string words,int* A) 58 { 59 int i,x,y,z; 60 for(i=0;i<words.length();i+=3) 61 { 62 for(x=0;x<26;x++) 63 for(y=0;y<26;y++) 64 for(z=0;z<26;z++) 65 { 66 if(char((A[0]*x+A[1]*y+A[2]*z)%26+65)==words[i]&&char((A[3]*x+A[4]*y+A[5]*z)%26+65)==words[i+1]&&char((A[6]*x+A[7]*y+A[8]*z)%26+65)==words[i+2]) 67 goto xx; 68 } 69 xx: 70 cout<<char(x+65)<<char(y+65)<<char(z+65); 71 } 72 cout<<endl; 73 } 74 int gcd(int a,int b) 75 { 76 if(b==0) 77 return a; 78 else 79 return gcd(b,a%b); 80 }
2.多表替代密码(改进):
1 #include<iostream> 2 #include<cstdlib> 3 #include<cstdio> 4 #include<string> 5 using namespace std; 6 7 int gcd(int a,int b);// 求最大公约数; 8 void jiami(string words,int* A,int& b0,int& b1,int& b2);//加密; 9 void jiemi(string words,int* A,int& b0,int& b1,int& b2);//解密; 10 void nijz(int* A);//求逆元矩阵; 11 int niyuan(long m,long n);//求逆元; 12 int main() 13 { 14 int A[9],i,tmp,b0,b1,b2; 15 string words; 16 bool r; 17 cout<<"请随意输入一个整数,来改变随机种子:"; 18 cin>>i; 19 srand(i); 20 getchar(); 21 cout<<"系统随机生成一个三阶矩阵:"<<endl; 22 t: 23 for(i=0;i<9;i++) 24 { 25 A[i]=rand()%26; 26 } 27 tmp=A[0]*(A[4]*A[8]-A[5]*A[7])-A[1]*(A[3]*A[8]-A[5]*A[6])+A[2]*(A[3]*A[7]-A[4]*A[6]); 28 if(gcd(tmp,26)!=1) 29 goto t; 30 for(i=0;i<9;i++) 31 { 32 if(i==2||i==5||i==8) 33 cout<<A[i]<<";"<<endl; 34 else 35 cout<<A[i]<<" "; 36 } 37 cout<<"请输入明文或密文(大写,而且字数是3的倍数哦):"; 38 getline(cin,words); 39 cout<<"加密(0)?解密(1)?请输入 0 or 1:"; 40 cin>>r; 41 cout<<"请输入密钥B矩阵(三阶):"; 42 cin>>b0>>b1>>b2; 43 if(r==1) 44 { 45 nijz(A); 46 jiemi(words,A,b0,b1,b2); 47 } 48 else 49 { 50 jiami(words,A,b0,b1,b2); 51 } 52 cout<<endl; 53 return 0; 54 } 55 void jiami(string words,int* A,int& b0,int& b1,int& b2) 56 { 57 int i,t; 58 cout<<"密文是:"; 59 for(i=0;i<words.length();i+=3) 60 { 61 t=A[0]*(int(words[i])-65)+A[1]*(int(words[i+1])-65)+A[2]*(int(words[i+2])-65); 62 while(t<0) 63 { 64 t+=26; 65 } 66 cout<<char((t%26+b0%26)%26+65); 67 t=A[3]*(int(words[i])-65)+A[4]*(int(words[i+1])-65)+A[5]*(int(words[i+2])-65); 68 while(t<0) 69 { 70 t+=26; 71 } 72 cout<<char((t%26+b1%26)%26+65); 73 t=A[6]*(int(words[i])-65)+A[7]*(int(words[i+1])-65)+A[8]*(int(words[i+2])-65); 74 while(t<0) 75 { 76 t+=26; 77 } 78 cout<<char((t%26+b2%26)%26+65); 79 } 80 } 81 void jiemi(string words,int* A,int& b0,int& b1,int& b2) 82 { 83 int i,t; 84 cout<<"明文是:"; 85 for(i=0;i<words.length();i+=3) 86 { 87 t=A[0]*(int(words[i])-65-b0)+A[1]*(int(words[i+1])-65-b1)+A[2]*(int(words[i+2])-65-b2); 88 while(t<0) 89 { 90 t+=26; 91 } 92 cout<<char(t%26+65); 93 t=A[3]*(int(words[i])-65-b0)+A[4]*(int(words[i+1])-65-b1)+A[5]*(int(words[i+2])-65-b2); 94 while(t<0) 95 { 96 t+=26; 97 } 98 cout<<char(t%26+65); 99 t=A[6]*(int(words[i])-65-b0)+A[7]*(int(words[i+1])-65-b1)+A[8]*(int(words[i+2])-65-b2); 100 while(t<0) 101 { 102 t+=26; 103 } 104 cout<<char(t%26+65); 105 } 106 } 107 int gcd(int a,int b) 108 { 109 if(b==0) 110 return a; 111 else 112 return gcd(b,a%b); 113 } 114 void nijz(int* A) 115 { 116 int i,j,k,t; 117 long s0[6],s[3][6]; 118 long r1,r2,r3; 119 for(i=0;i<3;i++) 120 { 121 s[0][i]=A[i]; 122 } 123 for(i=0;i<3;i++) 124 { 125 s[1][i]=A[i+3]; 126 } 127 for(i=0;i<3;i++) 128 { 129 s[2][i]=A[i+6]; 130 } 131 s[0][3]=1; 132 s[0][4]=0; 133 s[0][5]=0; 134 s[1][3]=0; 135 s[1][4]=1; 136 s[1][5]=0; 137 s[2][3]=0; 138 s[2][4]=0; 139 s[2][5]=1; 140 i=0; 141 while(i<3) 142 { 143 j=0; 144 while(j<3) 145 { 146 if(j==i) 147 { 148 goto g; 149 } 150 for(t=0;t<6;t++) 151 { 152 s0[t]=s[i][t]; 153 } 154 for(k=0;k<6;k++) 155 { 156 s0[k]*=s[j][i]; 157 } 158 for(k=0;k<6;k++) 159 { 160 s[j][k]*=s[i][i]; 161 } 162 for(k=0;k<6;k++) 163 { 164 s[j][k]-=s0[k]; 165 } 166 g: 167 j++; 168 } 169 i++; 170 } 171 for(i=0;i<3;i++) 172 { 173 while(s[i][i]%2==0) 174 { 175 s[i][i]/=2; 176 s[i][3]/=2; 177 s[i][4]/=2; 178 s[i][5]/=2; 179 } 180 } 181 for(i=0;i<3;i++) 182 { 183 while(s[i][i]%13==0) 184 { 185 s[i][i]/=13; 186 s[i][3]/=13; 187 s[i][4]/=13; 188 s[i][5]/=13; 189 } 190 } 191 r1=niyuan(26,s[0][0]); 192 r2=niyuan(26,s[1][1]); 193 r3=niyuan(26,s[2][2]); 194 for(i=0;i<3;i++) 195 { 196 A[i]=(s[0][i+3]*r1); 197 while(A[i]<0) 198 A[i]+=26; 199 A[i]%=26; 200 } 201 for(i=0;i<3;i++) 202 { 203 A[i+3]=(s[1][i+3]*r2); 204 while(A[i+3]<0) 205 A[i+3]+=26; 206 A[i+3]%=26; 207 } 208 for(i=0;i<3;i++) 209 { 210 A[i+6]=(s[2][i+3]*r3);A[i+6]%=26; 211 while(A[i+6]<0) 212 A[i+6]+=26; 213 A[i+6]%=26; 214 } 215 } 216 int niyuan(long m,long n) 217 { 218 int a,b,c,d,t,yu,shang,mod; 219 a=m; 220 b=n; 221 mod=a; 222 c=0; 223 d=1; 224 while(b<0) 225 { 226 b+=a; 227 } 228 if(b==1) 229 return 1; 230 while(b!=1) 231 { 232 t=a%b; 233 shang=a/b; 234 a=b; 235 b=t; 236 yu=c-shang*d; 237 c=d; 238 d=yu; 239 } 240 if(yu<0) 241 yu+=mod; 242 return yu; 243 }
3.放射密码以及频率分析:
1 #include<iostream> //j=k0+ik1(mod n) 2 #include<string> 3 using namespace std; 4 5 const int n=26; 6 struct f 7 { 8 char x; 9 float y; 10 float z; 11 }; 12 void jiami(string words,const int& k0,const int& k1);//加密; 13 void jiemi(string words,const int& k0,const int& k1);//解密; 14 int niyuan(long m,long n);//求逆元; 15 int gcd(int a,int b);//求最大公约数; 16 int main() 17 { 18 string words; 19 char r; 20 int i,j; 21 struct f pinlv[26]; 22 for(i=0;i<26;i++) 23 { 24 pinlv[i].x='A'+i; 25 } 26 pinlv[0].y=0.0856; 27 pinlv[1].y=0.0139; 28 pinlv[2].y=0.0297; 29 pinlv[3].y=0.0678; 30 pinlv[4].y=0.1304; 31 pinlv[5].y=0.0289; 32 pinlv[6].y=0.0199; 33 pinlv[7].y=0.0528; 34 pinlv[8].y=0.0627; 35 pinlv[9].y=0.0013; 36 pinlv[10].y=0.0042; 37 pinlv[11].y=0.0339; 38 pinlv[12].y=0.0249; 39 pinlv[13].y=0.0707; 40 pinlv[14].y=0.0797; 41 pinlv[15].y=0.0199; 42 pinlv[16].y=0.0012; 43 pinlv[17].y=0.0677; 44 pinlv[18].y=0.0607; 45 pinlv[19].y=0.1045; 46 pinlv[20].y=0.0249; 47 pinlv[21].y=0.0092; 48 pinlv[22].y=0.0149; 49 pinlv[23].y=0.0017; 50 pinlv[24].y=0.0199; 51 pinlv[25].y=0.0008; 52 int k0,k1; 53 cout<<"请输入明文或密文(大写):"; 54 getline(cin,words); 55 cout<<"加密(0)?解密(1)?请输入 0 or 1:"; 56 cin>>r; 57 t: 58 cout<<"请输入两个密钥:k0 k1(k1与26互素):"; 59 cin>>k0>>k1; 60 if(gcd(k1,26)!=1) 61 { 62 cout<<"请注意要求!"<<endl; 63 goto t; 64 } 65 switch(r) 66 { 67 case '0': 68 jiami(words,k0,k1); 69 break; 70 case '1': 71 jiemi(words,k0,k1); 72 } 73 for(i=0;i<26;i++) 74 { 75 j=(int('A'+i)*k1+k0)%n; 76 pinlv[j].z=pinlv[i].y; 77 } 78 for(i=0;i<26;i++) 79 { 80 cout<<pinlv[i].x<<"的频率为"<<pinlv[i].z<<" "; 81 } 82 return 0; 83 } 84 void jiami(string words,const int& k0,const int& k1) 85 { 86 cout<<"密文为:"; 87 int i; 88 char t; 89 for(i=0;i<words.length();i++) 90 { 91 t=char(((words[i]*k1)%n+k0)%26+65); 92 cout<<t; 93 } 94 cout<<endl; 95 } 96 void jiemi(string words,const int& k0,const int& k1) 97 { 98 cout<<"明文为:"; 99 int i; 100 int k=niyuan(n,k1); 101 for(i=0;i<words.length();i++) 102 { 103 cout<<char(((words[i]-k0)*k)%n+65); 104 } 105 cout<<endl; 106 } 107 int niyuan(long m,long n) 108 { 109 int a,b,c,d,t,yu,shang,mod; 110 a=m; 111 b=n; 112 mod=a; 113 c=0; 114 d=1; 115 while(b<0) 116 { 117 b+=a; 118 } 119 if(b==1) 120 return 1; 121 while(b!=1) 122 { 123 t=a%b; 124 shang=a/b; 125 a=b; 126 b=t; 127 yu=c-shang*d; 128 c=d; 129 d=yu; 130 } 131 if(yu<0) 132 yu+=mod; 133 return yu; 134 } 135 int gcd(int a,int b) 136 { 137 if(b==0) 138 return a; 139 else 140 return gcd(b,a%b); 141 }
4.enigma密码机:
1 #include <iostream> 2 #include <cstdlib> 3 #include <string> 4 using namespace std; 5 6 void hl(int* x);//混合字母顺序-以数字代替字母 7 void result(string s,int* x1,int* x2,int* x3);//加解密 8 int main() 9 { 10 int x1[26],x2[26],x3[26]; 11 hl(x1); 12 hl(x2); 13 hl(x3); 14 string s; 15 cin>>s; 16 result(s,x1,x2,x3); 17 return 0; 18 } 19 void hl(int* x) 20 { 21 int i,m,y[26]; 22 for(i=0;i<26;i++) 23 { 24 y[i]=i; 25 } 26 for(i=0;i<26;) 27 { 28 m=rand()%26; 29 if(y[m]==-1) 30 { 31 continue; 32 } 33 else 34 { 35 x[i]=m; 36 y[m]=-1; 37 i++; 38 } 39 } 40 } 41 void result(string s,int* x1,int* x2,int* x3) 42 { 43 int m0=rand()%26,m1=rand()%26,m2=rand()%26,m3=rand()%26,i,j,tmp; 44 for(i=0;i<s.length();i++) 45 { 46 tmp=25-x3[(x2[(x1[(int(s[i]-65)+m0+m1)%26]+m2)%26]+m3)%26]; 47 for(j=0;j<26;j++) 48 { 49 if(x3[(j+m3)%26]==tmp) 50 { 51 tmp=j; 52 break; 53 } 54 } 55 for(j=0;j<26;j++) 56 { 57 if(x2[(j+m2)%26]==tmp) 58 { 59 tmp=j; 60 break; 61 } 62 } 63 for(j=0;j<26;j++) 64 { 65 if(x1[(j+m0+m1)%26]==tmp) 66 { 67 tmp=j; 68 break; 69 } 70 } 71 cout<<char(tmp+65); 72 while(tmp<0) 73 { 74 tmp+=26; 75 } 76 m1++; 77 if(m1==26) 78 { 79 m1=0; 80 m2++; 81 } 82 if(m2==26) 83 { 84 m2=0; 85 m3=(++m3)%26; 86 } 87 } 88 }
5.DES加解密以及雪崩效应验证:
1 #include <iostream> 2 #include <string> 3 4 using namespace std; 5 6 const int IP[]={ 7 58, 50, 42, 34, 26, 18, 10, 2, 8 60, 52, 44, 36, 28, 20, 12, 4, 9 62, 54, 46, 38, 30, 22, 14, 6, 10 64, 56, 48, 40, 32, 24, 16, 8, 11 57, 49, 41, 33, 25, 17, 9, 1, 12 59, 51, 43, 35, 27, 19, 11, 3, 13 61, 53, 45, 37, 29, 21, 13, 5, 14 63, 55, 47, 39, 31, 23, 15, 7}; 15 const int FP[]={ 16 40, 8, 48, 16, 56, 24, 64, 32, 17 39, 7, 47, 15, 55, 23, 63, 31, 18 38, 6, 46, 14, 54, 22, 62, 30, 19 37, 5, 45, 13, 53, 21, 61, 29, 20 36, 4, 44, 12, 52, 20, 60, 28, 21 35, 3, 43, 11, 51, 19, 59, 27, 22 34, 2, 42, 10, 50, 18, 58, 26, 23 33, 1, 41, 9, 49, 17, 57, 25}; 24 const int E[]={ 25 32, 1, 2, 3, 4, 5, 26 4, 5, 6, 7, 8, 9, 27 8, 9, 10, 11, 12, 13, 28 12, 13, 14, 15, 16, 17, 29 16, 17, 18, 19, 20, 21, 30 20, 21, 22, 23, 24, 25, 31 24, 25, 26, 27, 28, 29, 32 28, 29, 30, 31, 32, 1}; 33 const int P[]={ 34 16, 7, 20, 21, 35 29, 12, 28, 17, 36 1, 15, 23, 26, 37 5, 18, 31, 10, 38 2, 8, 24, 14, 39 32, 27, 3, 9, 40 19, 13, 30, 6, 41 22, 11, 4, 25};//0001 0101 1001 0101 0011 1101 0111 1000 1101 0000 1000 1011 1001 0001 1000 1110 42 const int S[8][64]={ 43 /* S1 */ 44 14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7, 45 0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8, 46 4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0, 47 15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13, 48 49 /* S2 */ 50 15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10, 51 3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5, 52 0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15, 53 13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9, 54 55 /* S3 */ 56 10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8, 57 13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1, 58 13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7, 59 1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12, 60 61 /* S4 */ 62 7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15, 63 13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9, 64 10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4, 65 3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14, 66 67 /* S5 */ 68 2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9, 69 14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6, 70 4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14, 71 11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3, 72 73 /* S6 */ 74 12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11, 75 10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8, 76 9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6, 77 4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13, 78 79 /* S7 */ 80 4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1, 81 13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6, 82 1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2, 83 6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12, 84 85 /* S8 */ 86 13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7, 87 1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2, 88 7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8, 89 2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11}; 90 const int PC_1[]={ 91 57, 49, 41, 33, 25, 17, 9, 92 1, 58, 50, 42, 34, 26, 18, 93 10, 2, 59, 51, 43, 35, 27, 94 19, 11, 3, 60, 52, 44, 36, 95 96 63, 55, 47, 39, 31, 23, 15, 97 7, 62, 54, 46, 38, 30, 22, 98 14, 6, 61, 53, 45, 37, 29, 99 21, 13, 5, 28, 20, 12, 4}; 100 const int PC_2[]={ 101 14, 17, 11, 24, 1, 5, 102 3, 28, 15, 6, 21, 10, 103 23, 19, 12, 4, 26, 8, 104 16, 7, 27, 20, 13, 2, 105 41, 52, 31, 37, 47, 55, 106 30, 40, 51, 45, 33, 48, 107 44, 49, 39, 56, 34, 53, 108 46, 42, 50, 36, 29, 32}; 109 struct w 110 { 111 unsigned int a:1; 112 unsigned int b:1; 113 unsigned int c:1; 114 unsigned int d:1; 115 unsigned int e:1; 116 unsigned int f:1; 117 unsigned int g:1; 118 unsigned int h:1; 119 }; 120 union data 121 { 122 char rr; 123 w rw; 124 }; 125 string DES(string s,string key); 126 string Key1(string s); 127 string Key2(string s); 128 int main() 129 { 130 string words0,words,key0,key,tmp; 131 bool mi; 132 int i,bit,counts; 133 cout<<"加密(0) or 解密(1):"; 134 cin>>mi; 135 cout<<"请输入密钥(8个字符):"; 136 cin>>key0; 137 if(mi==false) 138 { 139 cout<<"请输入明文(二进制数串:个数为64的倍数):"; 140 cin>>words0; 141 key=Key1(key0); 142 words=DES(words0,key); 143 } 144 else 145 { 146 cout<<"请输入密文(二进制数串:个数为64的倍数):"; 147 cin>>words0; 148 key=Key2(key0); 149 words=DES(words0,key); 150 } 151 cout<<"你想要的结果是:"<<words<<endl; 152 cout<<"退出0 or 继续测试1 :"; 153 cin>>mi; 154 if(!mi) 155 return 0; 156 cout<<"雪崩效应测试:"<<endl; 157 cout<<"你想关注密文的第几个bit位:"; 158 cin>>bit; 159 bit--; 160 counts=0; 161 for(i=0;i<words.length();i++) 162 { 163 tmp=words; 164 if(words[i]=='0') 165 tmp[i]='1'; 166 else 167 tmp[i]='0'; 168 tmp=DES(tmp,key0); 169 if(tmp[bit]=='0') 170 counts++; 171 } 172 cout<<"经测试,你关注的那个bit位,有"<<counts<<"次为0,有"<<words.length()-counts<<"次为1。"<<endl; 173 return 0; 174 } 175 string DES(string s,string key) 176 { 177 string ss=s; 178 string ts1,ts2; 179 int i,j,k,l,tmp1,tmp2; 180 bool t[8][8],tt[8][8],tmp; 181 s=""; 182 for(i=0;i<ss.length();i+=64) 183 { 184 for(j=0;j<64;j++) 185 { 186 if(ss[j]=='0') 187 { 188 *(*t+j)=false; 189 } 190 else 191 { 192 *(*t+j)=true; 193 } 194 } 195 for(j=0;j<64;j++) 196 { 197 *(*tt+j)=*(*t+IP[j]-1); 198 } 199 for(k=0;k<16;k++) 200 { 201 ts1=""; 202 for(j=32;j<64;j++) 203 { 204 if(*(*tt+j)==true) 205 ts1+="1"; 206 else 207 ts1+="0"; 208 } 209 for(j=0;j<48;j++) 210 { 211 *(*t+j)=*(*tt+E[j]+31); 212 } 213 ts2=""; 214 for(j=0;j<48;j++) 215 { 216 if((*(*t+j)==true&&key[k*48+j]==1)||(*(*t+j)==false&&key[k*48+j]==0)) 217 ts2+="0"; 218 else 219 ts2+="1"; 220 } 221 for(j=0;j<8;j++) 222 { 223 tmp1=(ts2[j*6]-'0')*2+(ts2[j*6+5]-'0'); 224 tmp2=(ts2[j*6+1]-'0')*8+(ts2[j*6+2]-'0')*4+(ts2[j*6+3]-'0')*2+(ts2[j*6+4]-'0'); 225 tmp1=S[j][tmp1*16+tmp2]; 226 *(*t+j*4+3)=tmp1&1; 227 tmp1>>=1; 228 *(*t+j*4+2)=tmp1&1; 229 tmp1>>=1; 230 *(*t+j*4+1)=tmp1&1; 231 tmp1>>=1; 232 *(*t+j*4)=tmp1; 233 } 234 for(j=32;j<64;j++) 235 { 236 *(*tt+j)=(*(*t+P[j-32]-1))^(*(*tt+j-32)); 237 } 238 for(j=0;j<32;j++) 239 { 240 if(ts1[j]=='0') 241 *(*tt+j)=false; 242 else 243 *(*tt+j)=true; 244 } 245 } 246 for(j=0;j<32;j++) 247 { 248 tmp=*(*tt+j); 249 *(*tt+j)=*(*tt+j+32); 250 *(*tt+j+32)=tmp; 251 } 252 for(j=0;j<64;j++) 253 { 254 *(*t+j)=*(*tt+FP[j]-1); 255 } 256 for(j=0;j<8;j++) 257 { 258 for(l=0;l<8;l++) 259 { 260 if(t[j][l]==true) 261 s+="1"; 262 else 263 s+="0"; 264 } 265 } 266 } 267 return s; 268 } 269 string Key1(string s) 270 { 271 string ss=s; 272 int i,j,k; 273 data d[8]; 274 bool tmp0,tmp1,tmp2,tmp3; 275 bool t[8][8],tt[8][8]; 276 for(j=0;j<8;j++) 277 { 278 d[j].rr=ss[j]; 279 t[j][6]=d[j].rw.b; 280 t[j][5]=d[j].rw.c; 281 t[j][4]=d[j].rw.d; 282 t[j][3]=d[j].rw.e; 283 t[j][2]=d[j].rw.f; 284 t[j][1]=d[j].rw.g; 285 t[j][0]=d[j].rw.h; 286 } 287 for(j=0;j<56;j++) 288 { 289 *(*tt+j)=*(*t+PC_1[j]-1); 290 } 291 tmp0=*(*tt); 292 tmp1=*(*tt+28); 293 tmp2=*(*tt+1); 294 tmp3=*(*tt+29); 295 ss=""; 296 for(i=0;i<16;i++) 297 { 298 if(i==1||i==2||i==9||i==16) 299 { 300 for(j=0;j<55;j++) 301 { 302 if(j!=27) 303 { 304 *(*tt+j)=*(*tt+j+1); 305 } 306 else 307 { 308 *(*tt+j)=tmp0; 309 } 310 } 311 *(*tt+55)=tmp1; 312 } 313 else 314 { 315 for(j=0;j<54;j++) 316 { 317 if(j!=27) 318 { 319 *(*tt+j)=*(*tt+j+2); 320 321 } 322 else 323 { 324 *(*tt+j-1)=tmp0; 325 *(*tt+j)=tmp2; 326 } 327 } 328 *(*tt+55)=tmp3; 329 *(*tt+54)=tmp1; 330 } 331 for(j=0;j<48;j++) 332 { 333 if(*(*tt+PC_2[j]-1)==true) 334 ss+="1"; 335 else 336 ss+="0"; 337 } 338 } 339 return ss; 340 } 341 string Key2(string s) 342 { 343 string ss=s; 344 int i,j,k; 345 data d[8]; 346 bool tmp0,tmp1,tmp2,tmp3; 347 bool t[8][8],tt[8][8]; 348 for(j=0;j<8;j++) 349 { 350 d[j].rr=ss[j]; 351 t[j][6]=d[j].rw.b; 352 t[j][5]=d[j].rw.c; 353 t[j][4]=d[j].rw.d; 354 t[j][3]=d[j].rw.e; 355 t[j][2]=d[j].rw.f; 356 t[j][1]=d[j].rw.g; 357 t[j][0]=d[j].rw.h; 358 } 359 for(j=0;j<56;j++) 360 { 361 *(*tt+j)=*(*t+PC_1[j]-1); 362 } 363 tmp0=*(*tt+27); 364 tmp1=*(*tt+55); 365 tmp2=*(*tt+26); 366 tmp3=*(*tt+54); 367 ss=""; 368 for(i=0;i<16;i++) 369 { 370 if(i==1||i==2||i==9||i==16) 371 { 372 for(j=55;j>0;j--) 373 { 374 if(j!=28) 375 { 376 *(*tt+j)=*(*tt+j-1); 377 } 378 else 379 { 380 *(*tt+j)=tmp1; 381 } 382 } 383 *(*tt)=tmp0; 384 } 385 else 386 { 387 for(j=55;j>1;j--) 388 { 389 if(j!=28) 390 { 391 *(*tt+j)=*(*tt+j-2); 392 393 } 394 else 395 { 396 *(*tt+j+1)=tmp1; 397 *(*tt+j)=tmp3; 398 } 399 } 400 *(*tt)=tmp2; 401 *(*tt+1)=tmp0; 402 } 403 for(j=0;j<48;j++) 404 { 405 if(*(*tt+PC_2[j]-1)==true) 406 ss+="1"; 407 else 408 ss+="0"; 409 } 410 } 411 s=ss; 412 for(j=0;j<16;j++) 413 { 414 for(k=0;k<48;k++) 415 { 416 ss[j*48+k]=s[(15-j)*48+k]; 417 } 418 } 419 return ss; 420 }