信息安全-简易的DES加解密--3DES

在此感谢大佬:https://www.cnblogs.com/yinbiao/p/10460453.html 一步一步都有数据
https://blog.csdn.net/lisonglisonglisong/article/details/41777413 按着这个大佬的思路来的

#include<bits/stdc++.h>
#define TLE ios::sync_with_stdio(0),cin.tie(0)
using namespace std;
bitset<64> bitencrypt;
bitset<64> bitkey;
bitset<64> bitdecrypt;
bitset<48> keyarray[16];//48位!!!
// 初始置换表
int IP[] = { 58, 50, 42, 34, 26, 18, 10, 2,
			 60, 52, 44, 36, 28, 20, 12, 4,
			 62, 54, 46, 38, 30, 22, 14, 6,
			 64, 56, 48, 40, 32, 24, 16, 8,
			 57, 49, 41, 33, 25, 17, 9,  1,
			 59, 51, 43, 35, 27, 19, 11, 3,
			 61, 53, 45, 37, 29, 21, 13, 5,
			 63, 55, 47, 39, 31, 23, 15, 7 };

/*------------------下面是生成密钥所用表-----------------*/
int PC_1[] = {57, 49, 41, 33, 25, 17, 9,
			   1, 58, 50, 42, 34, 26, 18,
			  10,  2, 59, 51, 43, 35, 27,
			  19, 11,  3, 60, 52, 44, 36,
			  63, 55, 47, 39, 31, 23, 15,
			   7, 62, 54, 46, 38, 30, 22,
			  14,  6, 61, 53, 45, 37, 29,
			  21, 13,  5, 28, 20, 12,  4};
int PC_2[] = {14, 17, 11, 24,  1,  5,
			   3, 28, 15,  6, 21, 10,
			  23, 19, 12,  4, 26,  8,
			  16,  7, 27, 20, 13,  2,
			  41, 52, 31, 37, 47, 55,
			  30, 40, 51, 45, 33, 48,
			  44, 49, 39, 56, 34, 53,
			  46, 42, 50, 36, 29, 32};
int shiftBits[] = {1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1};

/*------------------轮函数-----------------*/
// 扩展置换表,将32位扩展至48位
int E[] = {32,  1,  2,  3,  4,  5,
		    4,  5,  6,  7,  8,  9,
		    8,  9, 10, 11, 12, 13,
		   12, 13, 14, 15, 16, 17,
		   16, 17, 18, 19, 20, 21,
		   20, 21, 22, 23, 24, 25,
		   24, 25, 26, 27, 28, 29,
		   28, 29, 30, 31, 32,  1};
// S盒,每个S盒是4x16的置换表,6位 -> 4位
int S_BOX[8][4][16] = {
	{
		{14,4,13,1,2,15,11,8,3,10,6,12,5,9,0,7},
		{0,15,7,4,14,2,13,1,10,6,12,11,9,5,3,8},
		{4,1,14,8,13,6,2,11,15,12,9,7,3,10,5,0},
		{15,12,8,2,4,9,1,7,5,11,3,14,10,0,6,13}
	},
	{
		{15,1,8,14,6,11,3,4,9,7,2,13,12,0,5,10},
		{3,13,4,7,15,2,8,14,12,0,1,10,6,9,11,5},
		{0,14,7,11,10,4,13,1,5,8,12,6,9,3,2,15},
		{13,8,10,1,3,15,4,2,11,6,7,12,0,5,14,9}
	},
	{
		{10,0,9,14,6,3,15,5,1,13,12,7,11,4,2,8},
		{13,7,0,9,3,4,6,10,2,8,5,14,12,11,15,1},
		{13,6,4,9,8,15,3,0,11,1,2,12,5,10,14,7},
		{1,10,13,0,6,9,8,7,4,15,14,3,11,5,2,12}
	},
	{
		{7,13,14,3,0,6,9,10,1,2,8,5,11,12,4,15},
		{13,8,11,5,6,15,0,3,4,7,2,12,1,10,14,9},
		{10,6,9,0,12,11,7,13,15,1,3,14,5,2,8,4},
		{3,15,0,6,10,1,13,8,9,4,5,11,12,7,2,14}
	},
	{
		{2,12,4,1,7,10,11,6,8,5,3,15,13,0,14,9},
		{14,11,2,12,4,7,13,1,5,0,15,10,3,9,8,6},
		{4,2,1,11,10,13,7,8,15,9,12,5,6,3,0,14},
		{11,8,12,7,1,14,2,13,6,15,0,9,10,4,5,3}
	},
	{
		{12,1,10,15,9,2,6,8,0,13,3,4,14,7,5,11},
		{10,15,4,2,7,12,9,5,6,1,13,14,0,11,3,8},
		{9,14,15,5,2,8,12,3,7,0,4,10,1,13,11,6},
		{4,3,2,12,9,5,15,10,11,14,1,7,6,0,8,13}
	},
	{
		{4,11,2,14,15,0,8,13,3,12,9,7,5,10,6,1},
		{13,0,11,7,4,9,1,10,14,3,5,12,2,15,8,6},
		{1,4,11,13,12,3,7,14,10,15,6,8,0,5,9,2},
		{6,11,13,8,1,4,10,7,9,5,0,15,14,2,3,12}
	},
	{
		{13,2,8,4,6,15,11,1,10,9,3,14,5,0,12,7},
		{1,15,13,8,10,3,7,4,12,5,6,11,0,14,9,2},
		{7,11,4,1,9,12,14,2,0,6,10,13,15,3,5,8},
		{2,1,14,7,4,10,8,13,15,12,9,0,3,5,6,11}
	}
};
// P盒置换
int P[] = {16,  7, 20, 21,
		   29, 12, 28, 17,
		    1, 15, 23, 26,
		    5, 18, 31, 10,
		    2,  8, 24, 14,
		   32, 27,  3,  9,
		   19, 13, 30,  6,
		   22, 11,  4, 25 };
/*--------------------------------------*/
//初始逆置换
int IP_1[] = {40, 8, 48, 16, 56, 24, 64, 32,
			  39, 7, 47, 15, 55, 23, 63, 31,
			  38, 6, 46, 14, 54, 22, 62, 30,
			  37, 5, 45, 13, 53, 21, 61, 29,
			  36, 4, 44, 12, 52, 20, 60, 28,
			  35, 3, 43, 11, 51, 19, 59, 27,
			  34, 2, 42, 10, 50, 18, 58, 26,
			  33, 1, 41,  9, 49, 17, 57, 25};


//===================================================
void producekey(){
//过程:64位密钥经置换选择1去除奇偶校验位变成56位 分开左右各28位
//循环移位:第一轮L1左移一位+R1(共56位)经过压缩置换2成48位:key1
//L1(28)继续左移一位:L2+R1(28):R2(共56位)经过压缩置换成48位:key2
//L2(28)继续左移2位:L2+R1(28):R2(共56位)经过压缩置换成48位...
//共移位16轮 每轮移位位数不同 所以直接拿数组存 到时候直接取
      bitset<56>trans1;
      bitset<28>left1,left2;
      bitset<28>right1,right2;
      bitset<56>trans2;
      bitset<48>trans3;
      for(int i=0;i<56;++i){//缩成56位:去除了奇偶校验位
        trans1[55-i] = bitkey[64-PC_1[i]];
      }
     // cout<<"producekey()--trans1: "<<trans1<<endl;
      //分左右
      for(int i=0;i<28;++i){
        right1[i] = trans1[i];
        left1[i] = trans1[i+28];
      }
      //cout<<"producekey()--right1: "<<right1<<endl;
      //cout<<"producekey()--left1: "<<left1<<endl;
      for(int round=0;round<16;round++){//一轮生成1个密钥(48)
              if(shiftBits[round] == 1){
                for(int i=27; i>0; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                }
                left2[0] = left1[27];
                right2[0] = right1[27];
              }else{
                  for(int i=27; i>1; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                 }
                  left2[1] = left1[27];left2[0] = left1[26];
                  right2[1] = right1[27];right2[0] = right1[26];
              }
              //cout<<"round: "<<round<<" left2: "<<left2<<endl;
             // cout<<"round: "<<round<<" right2: "<<right2<<endl;

              for(int i=0;i<28;i++){ //数组合并 这肯定不行啊trans2 = left2+right2;//28!!
                trans2[i] = right2[i] ;
                trans2[i+28] = left2[i];
              }
              //压缩置换成48位
              for(int i=0;i<48;++i){
                trans3[47-i] = trans2[56-PC_2[i]];
              }
              keyarray[round] = trans3;
              //cout<<"producekey()--round: "<<round<<"  "<<keyarray[round]<<endl;
              left1 = left2;
              right1 = right2;
      }

}
int changetoten(string s){//二进制的字符串转成10进制的数字

    int a,m,b=0,k=0;
    //a = atoi(s);//string转int C++中若需要将string类型转为int类型,需先将string转为const char*。
    char c[100];strcpy(c,s.c_str());
    a = atoi(c);
    while(a!=0){
        m = a%10;
        a/=10;
        b+=m*pow(2,k++);
    }
    return b;

}
string changetotwo(int a){//10进制数字转成二进制字符串
       string s;
       int result = 0, temp = a, j = 1;
	   while(temp){
		  result = result + j * (temp % 2);
		  temp = temp / 2;
		  j = j * 10;
	   }
       char t[256];
       sprintf(t, "%04d", result);//字符串位数不足高位补0
       s = t;
       return s;//都要经过中间商char数组
}
void encrypt(){ //得到64位密文

        bitset<64> trans1;
        bitset<32> left1;
        bitset<32> right1;
        bitset<32> temp;
        bitset<48> trans2;
        bitset<32> transsbox;
        bitset<32> transpbox;
        bitset<48> transleft;
        //NO1:初始置换IP 就是一个简单的for循环
        //cout<<"encrypt()--bitencrypt: "<<bitencrypt<<endl;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitencrypt[64-IP[i]];
        }
        //cout<<"encrypt()--trans1: "<<trans1<<endl;
        //分成左右各32位的bitset
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];//左右都要移位啊
        }
        //cout<<"encrypt()--left1: "<<left1<<endl;
       // cout<<"encrypt()--right1: "<<right1<<endl;

        //NO2:密钥整体的生成
        producekey();
        //回来了
        //N03:16轮轮函数
        for(int round=0;round<16;round++){//密钥key48位
//过程:Li(32)位经位拓展表变成48位,和密钥key异或,再S盒[48位分成8个6位,每个6位输入S盒输出变成4位]32位
//32位经P盒置换 输出置换后的32位==>Ri+1 Li+1==Ri
             //cout<<"right1: "<<right1<<endl;
             for(int i=0;i<48;++i){//轮函数no1:32位经E拓展成48位 ///48!!
                  transleft[47-i] = right1[32-E[i]];//拿R去做S盒
             }
             //cout<<"right2: "<<transleft<<endl;
             //轮函数no2:和key异或
             transleft = transleft^keyarray[round];
             //cout<<"transleft: "<<transleft<<endl;
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             //cout<<middles.length()<<endl;//48
             for(int i=0;i<48;i+=6){//轮函数no3:S盒替代 48位变成32位
//六位:首加末:行号 中间四位:列号 对应si盒找到该位置后用4位二进制表达
                   middles1 = strtransleft.substr(i,6);//起始位置 数目
                   string bemiddles1,mimiddles1;//清零
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);//string连接 什么烂毛病
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);//
                   resu = S_BOX[i/6][row][column];//i/6表面当前是哪个盒子
                   middles2.append(changetotwo(resu));
                   //每一轮结果:4位
             }//middles2:32位str
             //cout<<middles2.length()<<endl;长度不足32位
             //cout<<"middles2: "<<middles2<<endl;
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             //轮函数no4:P盒置换
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }//f函数的输出
             //Li=Ri-1  Ri=Li^f();
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
//             cout<<"left1: "<<left1<<endl;
//             cout<<"right1: "<<right1<<endl;
        }

        //合并R16L16
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }

        //NO4:初始逆置换
        for(int i=0;i<64;++i){
             bitdecrypt[63-i] = trans2[64-IP_1[i]];
        }
        cout<<"密文: "<<bitdecrypt<<endl;

}

void decrypt(){

        bitset<64> trans1;
        bitset<32> left1;
        bitset<32> right1;
        bitset<32> temp;
        bitset<48> trans2;
        bitset<32> transsbox;
        bitset<32> transpbox;
        bitset<48> transleft;
        //NO1:初始置换IP 就是一个简单的for循环
        //cout<<"encrypt()--bitencrypt: "<<bitencrypt<<endl;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitdecrypt[64-IP[i]];//!!!!!!
        }
        //cout<<"encrypt()--trans1: "<<trans1<<endl;
        //分成左右各32位的bitset
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];//左右都要移位啊
        }
        //cout<<"encrypt()--left1: "<<left1<<endl;
       // cout<<"encrypt()--right1: "<<right1<<endl;

        //NO2:密钥整体的生成
        producekey();
        //回来了
        //N03:16轮轮函数
        for(int round=0;round<16;round++){//密钥key48位
//过程:Li(32)位经位拓展表变成48位,和密钥key异或,再S盒[48位分成8个6位,每个6位输入S盒输出变成4位]32位
//32位经P盒置换 输出置换后的32位==>Ri+1 Li+1==Ri
             //cout<<"right1: "<<right1<<endl;
             for(int i=0;i<48;++i){//轮函数no1:32位经E拓展成48位 ///48!!
                  transleft[47-i] = right1[32-E[i]];//拿R去做S盒
             }
             //cout<<"right2: "<<transleft<<endl;
             //轮函数no2:和key异或
             transleft = transleft^keyarray[15-round];//!!!!
             //cout<<"transleft: "<<transleft<<endl;
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             //cout<<middles.length()<<endl;//48
             for(int i=0;i<48;i+=6){//轮函数no3:S盒替代 48位变成32位
//六位:首加末:行号 中间四位:列号 对应si盒找到该位置后用4位二进制表达
                   middles1 = strtransleft.substr(i,6);//起始位置 数目
                   string bemiddles1,mimiddles1;//清零
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);//string连接 什么烂毛病
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);//
                   resu = S_BOX[i/6][row][column];//i/6表面当前是哪个盒子
                   middles2.append(changetotwo(resu));
                   //每一轮结果:4位
             }//middles2:32位str
             //cout<<middles2.length()<<endl;长度不足32位
             //cout<<"middles2: "<<middles2<<endl;
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             //轮函数no4:P盒置换
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }//f函数的输出
             //Li=Ri-1  Ri=Li^f();
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
//             cout<<"left1: "<<left1<<endl;
//             cout<<"right1: "<<right1<<endl;
        }

        //合并R16L16
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }

        //NO4:初始逆置换
        for(int i=0;i<64;++i){
             bitencrypt[63-i] = trans2[64-IP_1[i]];
        }
        cout<<"明文: "<<bitencrypt<<endl;
}


int main(){
        TLE;

        string transsstr = "0000000100100011010001010110011110001001101010111100110111101111";
        string transmystr = "0001001100110100010101110111100110011011101111001101111111110001";
        bitset<64>bitencrypt1(transsstr);cout<<"明文: "<<bitencrypt1<<endl;//64位明文
        bitset<64>bitkey1(transmystr);cout<<"密钥: "<<bitkey1<<endl;//64位密钥
        bitencrypt = bitencrypt1;
        bitkey = bitkey1;


        //加密函数
        encrypt();
        //解密函数 跟加密函数
        decrypt();


        return 0;
}

其实很郁闷的是明明上周六就写好了 结果昨晚一看完全不是 只是不报错的版本 连做的word笔记都缺少了内容 不知道是怎么回事
又花了一节课的时间缓缓改过来TT有点纳闷到底是怎么回事 每次都会保存的 别的朋友也不会动我的东西呀 就完全是订正前的样子 唉 于是先粘贴在这里吧
开心的是S盒功能一次性写对了
这是最初的版本 之后会在完善的

进一步改善的3DES 还是不是很全面 但能实现8*n长度的string加解密 写入写出文件

#include<bits/stdc++.h>
#define TLE ios::sync_with_stdio(0),cin.tie(0)
using namespace std;

bitset<48> keyarray[16];
// 初始置换表
int IP[] = { 58, 50, 42, 34, 26, 18, 10, 2,
			 60, 52, 44, 36, 28, 20, 12, 4,
			 62, 54, 46, 38, 30, 22, 14, 6,
			 64, 56, 48, 40, 32, 24, 16, 8,
			 57, 49, 41, 33, 25, 17, 9,  1,
			 59, 51, 43, 35, 27, 19, 11, 3,
			 61, 53, 45, 37, 29, 21, 13, 5,
			 63, 55, 47, 39, 31, 23, 15, 7 };

/*------------------下面是生成密钥所用表-----------------*/
int PC_1[] = {57, 49, 41, 33, 25, 17, 9,
			   1, 58, 50, 42, 34, 26, 18,
			  10,  2, 59, 51, 43, 35, 27,
			  19, 11,  3, 60, 52, 44, 36,
			  63, 55, 47, 39, 31, 23, 15,
			   7, 62, 54, 46, 38, 30, 22,
			  14,  6, 61, 53, 45, 37, 29,
			  21, 13,  5, 28, 20, 12,  4};
int PC_2[] = {14, 17, 11, 24,  1,  5,
			   3, 28, 15,  6, 21, 10,
			  23, 19, 12,  4, 26,  8,
			  16,  7, 27, 20, 13,  2,
			  41, 52, 31, 37, 47, 55,
			  30, 40, 51, 45, 33, 48,
			  44, 49, 39, 56, 34, 53,
			  46, 42, 50, 36, 29, 32};
int shiftBits[] = {1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1};

/*------------------轮函数-----------------*/
// 扩展置换表,将32位扩展至48位
int E[] = {32,  1,  2,  3,  4,  5,
		    4,  5,  6,  7,  8,  9,
		    8,  9, 10, 11, 12, 13,
		   12, 13, 14, 15, 16, 17,
		   16, 17, 18, 19, 20, 21,
		   20, 21, 22, 23, 24, 25,
		   24, 25, 26, 27, 28, 29,
		   28, 29, 30, 31, 32,  1};
// S盒,每个S盒是4x16的置换表,6位 -> 4位
int S_BOX[8][4][16] = {
	{
		{14,4,13,1,2,15,11,8,3,10,6,12,5,9,0,7},
		{0,15,7,4,14,2,13,1,10,6,12,11,9,5,3,8},
		{4,1,14,8,13,6,2,11,15,12,9,7,3,10,5,0},
		{15,12,8,2,4,9,1,7,5,11,3,14,10,0,6,13}
	},
	{
		{15,1,8,14,6,11,3,4,9,7,2,13,12,0,5,10},
		{3,13,4,7,15,2,8,14,12,0,1,10,6,9,11,5},
		{0,14,7,11,10,4,13,1,5,8,12,6,9,3,2,15},
		{13,8,10,1,3,15,4,2,11,6,7,12,0,5,14,9}
	},
	{
		{10,0,9,14,6,3,15,5,1,13,12,7,11,4,2,8},
		{13,7,0,9,3,4,6,10,2,8,5,14,12,11,15,1},
		{13,6,4,9,8,15,3,0,11,1,2,12,5,10,14,7},
		{1,10,13,0,6,9,8,7,4,15,14,3,11,5,2,12}
	},
	{
		{7,13,14,3,0,6,9,10,1,2,8,5,11,12,4,15},
		{13,8,11,5,6,15,0,3,4,7,2,12,1,10,14,9},
		{10,6,9,0,12,11,7,13,15,1,3,14,5,2,8,4},
		{3,15,0,6,10,1,13,8,9,4,5,11,12,7,2,14}
	},
	{
		{2,12,4,1,7,10,11,6,8,5,3,15,13,0,14,9},
		{14,11,2,12,4,7,13,1,5,0,15,10,3,9,8,6},
		{4,2,1,11,10,13,7,8,15,9,12,5,6,3,0,14},
		{11,8,12,7,1,14,2,13,6,15,0,9,10,4,5,3}
	},
	{
		{12,1,10,15,9,2,6,8,0,13,3,4,14,7,5,11},
		{10,15,4,2,7,12,9,5,6,1,13,14,0,11,3,8},
		{9,14,15,5,2,8,12,3,7,0,4,10,1,13,11,6},
		{4,3,2,12,9,5,15,10,11,14,1,7,6,0,8,13}
	},
	{
		{4,11,2,14,15,0,8,13,3,12,9,7,5,10,6,1},
		{13,0,11,7,4,9,1,10,14,3,5,12,2,15,8,6},
		{1,4,11,13,12,3,7,14,10,15,6,8,0,5,9,2},
		{6,11,13,8,1,4,10,7,9,5,0,15,14,2,3,12}
	},
	{
		{13,2,8,4,6,15,11,1,10,9,3,14,5,0,12,7},
		{1,15,13,8,10,3,7,4,12,5,6,11,0,14,9,2},
		{7,11,4,1,9,12,14,2,0,6,10,13,15,3,5,8},
		{2,1,14,7,4,10,8,13,15,12,9,0,3,5,6,11}
	}
};
// P盒置换
int P[] = {16,  7, 20, 21,
		   29, 12, 28, 17,
		    1, 15, 23, 26,
		    5, 18, 31, 10,
		    2,  8, 24, 14,
		   32, 27,  3,  9,
		   19, 13, 30,  6,
		   22, 11,  4, 25 };
/*--------------------------------------*/
//初始逆置换
int IP_1[] = {40, 8, 48, 16, 56, 24, 64, 32,
			  39, 7, 47, 15, 55, 23, 63, 31,
			  38, 6, 46, 14, 54, 22, 62, 30,
			  37, 5, 45, 13, 53, 21, 61, 29,
			  36, 4, 44, 12, 52, 20, 60, 28,
			  35, 3, 43, 11, 51, 19, 59, 27,
			  34, 2, 42, 10, 50, 18, 58, 26,
			  33, 1, 41,  9, 49, 17, 57, 25};


//===================================================
void producekey(bitset<64> bitkey){
//过程:64位密钥经置换选择1去除奇偶校验位变成56位 分开左右各28位
//循环移位:第一轮L1左移一位+R1(共56位)经过压缩置换2成48位:key1
//L1(28)继续左移一位:L2+R1(28):R2(共56位)经过压缩置换成48位:key2
//L2(28)继续左移2位:L2+R1(28):R2(共56位)经过压缩置换成48位...
//共移位16轮 每轮移位位数不同 所以直接拿数组存 到时候直接取
      bitset<56>trans1;
      bitset<28>left1,left2;
      bitset<28>right1,right2;
      bitset<56>trans2;
      bitset<48>trans3;
      for(int i=0;i<56;++i){//缩成56位:去除了奇偶校验位
        trans1[55-i] = bitkey[64-PC_1[i]];
      }
     // cout<<"producekey()--trans1: "<<trans1<<endl;
      //分左右
      for(int i=0;i<28;++i){
        right1[i] = trans1[i];
        left1[i] = trans1[i+28];
      }
      //cout<<"producekey()--right1: "<<right1<<endl;
      //cout<<"producekey()--left1: "<<left1<<endl;
      for(int round=0;round<16;round++){//一轮生成1个密钥(48)
              if(shiftBits[round] == 1){
                for(int i=27; i>0; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                }
                left2[0] = left1[27];
                right2[0] = right1[27];
              }else{
                  for(int i=27; i>1; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                 }
                  left2[1] = left1[27];left2[0] = left1[26];
                  right2[1] = right1[27];right2[0] = right1[26];
              }
              //cout<<"round: "<<round<<" left2: "<<left2<<endl;
             // cout<<"round: "<<round<<" right2: "<<right2<<endl;

              for(int i=0;i<28;i++){ //数组合并 这肯定不行啊trans2 = left2+right2;//28!!
                trans2[i] = right2[i] ;
                trans2[i+28] = left2[i];
              }
              //压缩置换成48位
              for(int i=0;i<48;++i){
                trans3[47-i] = trans2[56-PC_2[i]];
              }
              keyarray[round] = trans3;
              //cout<<"producekey()--round: "<<round<<"  "<<keyarray[round]<<endl;
              left1 = left2;
              right1 = right2;
      }

}
int changetoten(string s){//二进制的字符串转成10进制的数字

    int a,m,b=0,k=0;
    //a = atoi(s);//string转int C++中若需要将string类型转为int类型,需先将string转为const char*。
    char c[100];strcpy(c,s.c_str());
    a = atoi(c);
    while(a!=0){
        m = a%10;
        a/=10;
        b+=m*pow(2,k++);
    }
    return b;
}
string changetotwo(int a){//10进制数字转成二进制字符串
       string s;
       int result = 0, temp = a, j = 1;
	   while(temp){
		  result = result + j * (temp % 2);
		  temp = temp / 2;
		  j = j * 10;
	   }
       char t[256];
       sprintf(t, "%04d", result);//字符串位数不足高位补0
       s = t;
       return s;//都要经过中间商char数组
}
string encrypt(bitset<64>bitkey,string strwen){ //参数得是64位bitset明文 返回64位密文
        bitset<64> bitencrypt(strwen);
        bitset<64> bitdecrypt;

        bitset<64> trans1;
        bitset<32> left1;
        bitset<32> right1;
        bitset<32> temp;
        bitset<48> trans2;
        bitset<32> transsbox;
        bitset<32> transpbox;
        bitset<48> transleft;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitencrypt[64-IP[i]];
        }
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];
        }
        //NO2:密钥整体的生成
        producekey(bitkey);
        //回来了
        for(int round=0;round<16;round++){
             for(int i=0;i<48;++i){
                  transleft[47-i] = right1[32-E[i]];
             }
             transleft = transleft^keyarray[round];
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             for(int i=0;i<48;i+=6){
                   middles1 = strtransleft.substr(i,6);
                   string bemiddles1,mimiddles1;
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);
                   resu = S_BOX[i/6][row][column];
                   middles2.append(changetotwo(resu));
             }
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
        }
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }
        for(int i=0;i<64;++i){
             bitdecrypt[63-i] = trans2[64-IP_1[i]];
        }
        cout<<"encrypt()---密文: "<<bitdecrypt<<endl;
        return bitdecrypt.to_string();//转成64位二进制字符串


}

string decrypt(bitset<64>bitkey,string strwen){
        bitset<64> bitencrypt;
        bitset<64> bitdecrypt(strwen);

        bitset<64> trans1;
        bitset<32> left1;
        bitset<32> right1;
        bitset<32> temp;
        bitset<48> trans2;
        bitset<32> transsbox;
        bitset<32> transpbox;
        bitset<48> transleft;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitdecrypt[64-IP[i]];
        }
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];
        }
        //NO2:密钥整体的生成
        producekey(bitkey);

        for(int round=0;round<16;round++){
             for(int i=0;i<48;++i){
                  transleft[47-i] = right1[32-E[i]];
             }
             transleft = transleft^keyarray[15-round];
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             for(int i=0;i<48;i+=6){
                   middles1 = strtransleft.substr(i,6);
                   string bemiddles1,mimiddles1;
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);
                   resu = S_BOX[i/6][row][column];
                   middles2.append(changetotwo(resu));
             }
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
        }
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }
        for(int i=0;i<64;++i){
             bitencrypt[63-i] = trans2[64-IP_1[i]];
        }
        cout<<"decrypt()--明文: "<<bitencrypt<<endl;
        return bitencrypt.to_string();//转成64位二进制字符串
}

string stringtotwo(string str){//字符转二进制 一个字符转8位二进制  这里改  改成字符串的
      unsigned char k=0x80;//https://blog.csdn.net/caiyaodeng/article/details/48998469
      string transsstr;
      //string转char*
      const char *schar = str.c_str();
      for(int i=0;i<strlen(schar);++i){
        unsigned char k=0x80;
        for(int j=0; j<8; j++, k >>= 1){
            if (schar[i]&k){
                transsstr.append("1");
            }else{
                transsstr.append("0");
            }
        }
     }
     return transsstr;
}

string convert(char p[]){ //16进制转成文本
    int i=0;
    while(p[2*i]!='\0'&&p[2*i+1]!='\0')//'\0' :ASCII码为0,表示一个字符串结束的标志
    {
        char c = p[2*i];
        if(c<='9')
          p[i] = (c-'0')<<4;
        else if(c<='F')
          p[i] = (c-'A'+10)<<4;
        else
          p[i] = (c-'a'+10)<<4;
        c = p[2*i+1];
        if(c<='9')
          p[i] += (c-'0');
        else if(c<='F')
          p[i] += (c-'A'+10);
        else
          p[i] += (c-'a'+10);
        i++;
    }
    p[i] = '\0';
    return p;
}
string totwostring(string str){ //32位二进制转成string
    string binary = str;
    string hex;
    stringstream ss;
    ss << std::hex << stoi(binary, nullptr, 2);//https://www.cnblogs.com/tsruixi/p/12944470.html
    ss >> hex;
    transform(hex.begin(), hex.end(), hex.begin(), ::toupper);//将某操作应用于指定范围的每个元素
    cout << hex <<endl;
    char a[100];
    strcpy(a,hex.c_str());
    return convert(a);
}
string process1(string mingw,int quesizezz){//该函数对这段64位明文 返回二进制的string密文

    string mystr3[3] = {"11223344","22334455","33445566"};
    string mytwo[3] = {"","",""};
    for(int z=0;z<3;z++){
        mytwo[z] = stringtotwo(mystr3[z]);
    }
    bitset<64>bitkey11(mytwo[0]);//用string初始化
    bitset<64>bitkey22(mytwo[1]);
    bitset<64>bitkey33(mytwo[2]);//k1 k2 k3

    bitset<64>one(encrypt(bitkey33,decrypt(bitkey22,encrypt(bitkey11,mingw))));//加密过程 得到64位密文
    cout<<"process1--one"<<endl;
    return one.to_string();
}
string process2(string mew,int quesizezz){//该函数对这段64位密文 返回二进制的string明文
    cout<<"process2--mew: "<<mew<<endl;
    string mystr3[3] = {"11223344","22334455","33445566"};
    string mytwo[3] = {"","",""};
    for(int z=0;z<3;z++){
        mytwo[z] = stringtotwo(mystr3[z]);
    }
    bitset<64>bitkey11(mytwo[0]);
    bitset<64>bitkey22(mytwo[1]);
    bitset<64>bitkey33(mytwo[2]);

    bitset<64>one(decrypt(bitkey11,encrypt(bitkey22,decrypt(bitkey33,mew))));//解密过程 得到64位明文
    cout<<"process2--one"<<endl;
    return one.to_string();
}
int main(){
        TLE;
        ofstream out1("ciphertext.txt");
        ofstream out2("later.txt");//写

        string returnmew;
        string returnmingw;

        //读明文文件 并补足 并分组
        ifstream in;
        in.open("former.txt");
        if(!in.is_open()){
            cerr<<"could not open this file"<<endl;
            exit(0);
        }
        char ch;
        string mingw;
        while(in.get(ch)){
            mingw.push_back(ch);
        }
        in.close();
        cout<<"mingw1: "<<mingw<<endl;
        mingw = stringtotwo(mingw);
        cout<<"mingw2: "<<mingw<<" mingw2.size(): "<<mingw.size()<<endl;
        int quesize = 64-(mingw.size()%64);
        int i=0;
        if(quesize==64){//证明不缺
             quesize = 0;
        }else{
            while(i < quesize){
                mingw += '0';
                i++;
            }
        }
        //mingw:有足够64倍数位的二进制string


        for(i=0;i<mingw.size();i=i+64){
            string s64 = mingw.substr(i,64);//每次都截取64位
            if(i == (mingw.size()-63)){//判断得出这是最后一组64位
//               returnmew = process1(s64,quesize);//证明后面补0了 mew不足64位
//                //删去补足的位数 写入文件
//                //再进行解密 密文还得是64位啊 翻译回来的明文也是64位 可对应的明文位数明明不是64位的
//               returnmingw =  process2(mew,quesize);
//               returnmingw = totwostring(returnming);
                 cout<<"最后一组"<<endl;
            }else{ //正常的64位
                cout<<"正常的64位"<<endl;
                returnmew = process1(s64,0);
                cout<<"returnmew: "<<returnmew<<endl;
                //写入加密文件
                if (out1.is_open()) {
                    out1<<returnmew;
                }
                //这里不安排读了 传回来的参数直接给process2函数
                //再进行解密
               returnmingw = process2(returnmew,0);//64位string二进制 转成字符串
               returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
               //写入解密文件:
               if (out2.is_open()) {
                    out2<<returnmingw;
               }
            }
        }
        out1.close();
        out2.close();

        return 0;
}

二进制转string 困扰了我很久妈蛋

#include<bits/stdc++.h>
using namespace std;

string convert(char p[]){ //16进制转成文本
    int i=0;
    while(p[2*i]!='\0'&&p[2*i+1]!='\0')//'\0' :ASCII码为0,表示一个字符串结束的标志
    {
        char c = p[2*i];
        if(c<='9')
          p[i] = (c-'0')<<4;
        else if(c<='F')
          p[i] = (c-'A'+10)<<4;
        else
          p[i] = (c-'a'+10)<<4;
        c = p[2*i+1];
        if(c<='9')
          p[i] += (c-'0');
        else if(c<='F')
          p[i] += (c-'A'+10);
        else
          p[i] += (c-'a'+10);
        i++;
    }
    p[i] = '\0';
    return p;
}
string totwostring(string str){ //64位二进制转成string
    string binary = str;
    string hex;
    stringstream ss;
    ss << std::hex << stoi(binary, nullptr, 2);//https://www.cnblogs.com/tsruixi/p/12944470.html
    ss >> hex;
    transform(hex.begin(), hex.end(), hex.begin(), ::toupper);//将某操作应用于指定范围的每个元素
    cout << hex <<endl;
    char a[100];
    strcpy(a,hex.c_str());
    return convert(a);
}
int main()
{  

     string s1 = "0111001001101111011011010110000101101110011101000110100101100011";
     cout<<totwostring(s1.substr(0,32))<<endl;
     cout<<totwostring(s1.substr(32,32))<<endl;
     s1 = totwostring(s1.substr(0,32)) + totwostring(s1.substr(32,32));
     cout<<s1<<endl;
}

上面函数无法处理多位数据 所以分开了

#include<bits/stdc++.h>
#define TLE ios::sync_with_stdio(0),cin.tie(0)
using namespace std;

bitset<48> keyarray[16];
// 初始置换表
int IP[] = { 58, 50, 42, 34, 26, 18, 10, 2,
			 60, 52, 44, 36, 28, 20, 12, 4,
			 62, 54, 46, 38, 30, 22, 14, 6,
			 64, 56, 48, 40, 32, 24, 16, 8,
			 57, 49, 41, 33, 25, 17, 9,  1,
			 59, 51, 43, 35, 27, 19, 11, 3,
			 61, 53, 45, 37, 29, 21, 13, 5,
			 63, 55, 47, 39, 31, 23, 15, 7 };

/*------------------下面是生成密钥所用表-----------------*/
int PC_1[] = {57, 49, 41, 33, 25, 17, 9,
			   1, 58, 50, 42, 34, 26, 18,
			  10,  2, 59, 51, 43, 35, 27,
			  19, 11,  3, 60, 52, 44, 36,
			  63, 55, 47, 39, 31, 23, 15,
			   7, 62, 54, 46, 38, 30, 22,
			  14,  6, 61, 53, 45, 37, 29,
			  21, 13,  5, 28, 20, 12,  4};
int PC_2[] = {14, 17, 11, 24,  1,  5,
			   3, 28, 15,  6, 21, 10,
			  23, 19, 12,  4, 26,  8,
			  16,  7, 27, 20, 13,  2,
			  41, 52, 31, 37, 47, 55,
			  30, 40, 51, 45, 33, 48,
			  44, 49, 39, 56, 34, 53,
			  46, 42, 50, 36, 29, 32};
int shiftBits[] = {1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1};

/*------------------轮函数-----------------*/
// 扩展置换表,将32位扩展至48位
int E[] = {32,  1,  2,  3,  4,  5,
		    4,  5,  6,  7,  8,  9,
		    8,  9, 10, 11, 12, 13,
		   12, 13, 14, 15, 16, 17,
		   16, 17, 18, 19, 20, 21,
		   20, 21, 22, 23, 24, 25,
		   24, 25, 26, 27, 28, 29,
		   28, 29, 30, 31, 32,  1};
// S盒,每个S盒是4x16的置换表,6位 -> 4位
int S_BOX[8][4][16] = {
	{
		{14,4,13,1,2,15,11,8,3,10,6,12,5,9,0,7},
		{0,15,7,4,14,2,13,1,10,6,12,11,9,5,3,8},
		{4,1,14,8,13,6,2,11,15,12,9,7,3,10,5,0},
		{15,12,8,2,4,9,1,7,5,11,3,14,10,0,6,13}
	},
	{
		{15,1,8,14,6,11,3,4,9,7,2,13,12,0,5,10},
		{3,13,4,7,15,2,8,14,12,0,1,10,6,9,11,5},
		{0,14,7,11,10,4,13,1,5,8,12,6,9,3,2,15},
		{13,8,10,1,3,15,4,2,11,6,7,12,0,5,14,9}
	},
	{
		{10,0,9,14,6,3,15,5,1,13,12,7,11,4,2,8},
		{13,7,0,9,3,4,6,10,2,8,5,14,12,11,15,1},
		{13,6,4,9,8,15,3,0,11,1,2,12,5,10,14,7},
		{1,10,13,0,6,9,8,7,4,15,14,3,11,5,2,12}
	},
	{
		{7,13,14,3,0,6,9,10,1,2,8,5,11,12,4,15},
		{13,8,11,5,6,15,0,3,4,7,2,12,1,10,14,9},
		{10,6,9,0,12,11,7,13,15,1,3,14,5,2,8,4},
		{3,15,0,6,10,1,13,8,9,4,5,11,12,7,2,14}
	},
	{
		{2,12,4,1,7,10,11,6,8,5,3,15,13,0,14,9},
		{14,11,2,12,4,7,13,1,5,0,15,10,3,9,8,6},
		{4,2,1,11,10,13,7,8,15,9,12,5,6,3,0,14},
		{11,8,12,7,1,14,2,13,6,15,0,9,10,4,5,3}
	},
	{
		{12,1,10,15,9,2,6,8,0,13,3,4,14,7,5,11},
		{10,15,4,2,7,12,9,5,6,1,13,14,0,11,3,8},
		{9,14,15,5,2,8,12,3,7,0,4,10,1,13,11,6},
		{4,3,2,12,9,5,15,10,11,14,1,7,6,0,8,13}
	},
	{
		{4,11,2,14,15,0,8,13,3,12,9,7,5,10,6,1},
		{13,0,11,7,4,9,1,10,14,3,5,12,2,15,8,6},
		{1,4,11,13,12,3,7,14,10,15,6,8,0,5,9,2},
		{6,11,13,8,1,4,10,7,9,5,0,15,14,2,3,12}
	},
	{
		{13,2,8,4,6,15,11,1,10,9,3,14,5,0,12,7},
		{1,15,13,8,10,3,7,4,12,5,6,11,0,14,9,2},
		{7,11,4,1,9,12,14,2,0,6,10,13,15,3,5,8},
		{2,1,14,7,4,10,8,13,15,12,9,0,3,5,6,11}
	}
};
// P盒置换
int P[] = {16,  7, 20, 21,
		   29, 12, 28, 17,
		    1, 15, 23, 26,
		    5, 18, 31, 10,
		    2,  8, 24, 14,
		   32, 27,  3,  9,
		   19, 13, 30,  6,
		   22, 11,  4, 25 };
/*--------------------------------------*/
//初始逆置换
int IP_1[] = {40, 8, 48, 16, 56, 24, 64, 32,
			  39, 7, 47, 15, 55, 23, 63, 31,
			  38, 6, 46, 14, 54, 22, 62, 30,
			  37, 5, 45, 13, 53, 21, 61, 29,
			  36, 4, 44, 12, 52, 20, 60, 28,
			  35, 3, 43, 11, 51, 19, 59, 27,
			  34, 2, 42, 10, 50, 18, 58, 26,
			  33, 1, 41,  9, 49, 17, 57, 25};


//===================================================
void producekey(bitset<64> bitkey){
//过程:64位密钥经置换选择1去除奇偶校验位变成56位 分开左右各28位
//循环移位:第一轮L1左移一位+R1(共56位)经过压缩置换2成48位:key1
//L1(28)继续左移一位:L2+R1(28):R2(共56位)经过压缩置换成48位:key2
//L2(28)继续左移2位:L2+R1(28):R2(共56位)经过压缩置换成48位...
//共移位16轮 每轮移位位数不同 所以直接拿数组存 到时候直接取
      bitset<56>trans1;
      bitset<28>left1,left2;
      bitset<28>right1,right2;
      bitset<56>trans2;
      bitset<48>trans3;
      for(int i=0;i<56;++i){//缩成56位:去除了奇偶校验位
        trans1[55-i] = bitkey[64-PC_1[i]];
      }
     // cout<<"producekey()--trans1: "<<trans1<<endl;
      //分左右
      for(int i=0;i<28;++i){
        right1[i] = trans1[i];
        left1[i] = trans1[i+28];
      }
      //cout<<"producekey()--right1: "<<right1<<endl;
      //cout<<"producekey()--left1: "<<left1<<endl;
      for(int round=0;round<16;round++){//一轮生成1个密钥(48)
              if(shiftBits[round] == 1){
                for(int i=27; i>0; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                }
                left2[0] = left1[27];
                right2[0] = right1[27];
              }else{
                  for(int i=27; i>1; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                 }
                  left2[1] = left1[27];left2[0] = left1[26];
                  right2[1] = right1[27];right2[0] = right1[26];
              }
              //cout<<"round: "<<round<<" left2: "<<left2<<endl;
             // cout<<"round: "<<round<<" right2: "<<right2<<endl;

              for(int i=0;i<28;i++){ //数组合并 这肯定不行啊trans2 = left2+right2;//28!!
                trans2[i] = right2[i] ;
                trans2[i+28] = left2[i];
              }
              //压缩置换成48位
              for(int i=0;i<48;++i){
                trans3[47-i] = trans2[56-PC_2[i]];
              }
              keyarray[round] = trans3;
              //cout<<"producekey()--round: "<<round<<"  "<<keyarray[round]<<endl;
              left1 = left2;
              right1 = right2;
      }

}
int changetoten(string s){//二进制的字符串转成10进制的数字

    int a,m,b=0,k=0;
    //a = atoi(s);//string转int C++中若需要将string类型转为int类型,需先将string转为const char*。
    char c[100];strcpy(c,s.c_str());
    a = atoi(c);
    while(a!=0){
        m = a%10;
        a/=10;
        b+=m*pow(2,k++);
    }
    return b;
}
string changetotwo(int a){//10进制数字转成二进制字符串
       string s;
       int result = 0, temp = a, j = 1;
	   while(temp){
		  result = result + j * (temp % 2);
		  temp = temp / 2;
		  j = j * 10;
	   }
       char t[256];
       sprintf(t, "%04d", result);//字符串位数不足高位补0
       s = t;
       return s;//都要经过中间商char数组
}
string encrypt(bitset<64>bitkey,string strwen){ //参数得是64位bitset明文 返回64位密文
        bitset<64> bitencrypt(strwen);
        bitset<64> bitdecrypt;

        bitset<64> trans1;
        bitset<32> left1;
        bitset<32> right1;
        bitset<32> temp;
        bitset<48> trans2;
        bitset<32> transsbox;
        bitset<32> transpbox;
        bitset<48> transleft;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitencrypt[64-IP[i]];
        }
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];
        }
        //NO2:密钥整体的生成
        producekey(bitkey);
        //回来了
        for(int round=0;round<16;round++){
             for(int i=0;i<48;++i){
                  transleft[47-i] = right1[32-E[i]];
             }
             transleft = transleft^keyarray[round];
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             for(int i=0;i<48;i+=6){
                   middles1 = strtransleft.substr(i,6);
                   string bemiddles1,mimiddles1;
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);
                   resu = S_BOX[i/6][row][column];
                   middles2.append(changetotwo(resu));
             }
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
        }
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }
        for(int i=0;i<64;++i){
             bitdecrypt[63-i] = trans2[64-IP_1[i]];
        }
        cout<<"encrypt()---密文: "<<bitdecrypt<<endl;
        return bitdecrypt.to_string();//转成64位二进制字符串


}

string decrypt(bitset<64>bitkey,string strwen){
        bitset<64> bitencrypt;
        bitset<64> bitdecrypt(strwen);

        bitset<64> trans1;
        bitset<32> left1;
        bitset<32> right1;
        bitset<32> temp;
        bitset<48> trans2;
        bitset<32> transsbox;
        bitset<32> transpbox;
        bitset<48> transleft;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitdecrypt[64-IP[i]];
        }
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];
        }
        //NO2:密钥整体的生成
        producekey(bitkey);

        for(int round=0;round<16;round++){
             for(int i=0;i<48;++i){
                  transleft[47-i] = right1[32-E[i]];
             }
             transleft = transleft^keyarray[15-round];
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             for(int i=0;i<48;i+=6){
                   middles1 = strtransleft.substr(i,6);
                   string bemiddles1,mimiddles1;
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);
                   resu = S_BOX[i/6][row][column];
                   middles2.append(changetotwo(resu));
             }
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
        }
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }
        for(int i=0;i<64;++i){
             bitencrypt[63-i] = trans2[64-IP_1[i]];
        }
        cout<<"decrypt()--明文: "<<bitencrypt<<endl;
        return bitencrypt.to_string();//转成64位二进制字符串
}

string stringtotwo(string str){//字符转二进制 一个字符转8位二进制  这里改  改成字符串的
      unsigned char k=0x80;//https://blog.csdn.net/caiyaodeng/article/details/48998469
      string transsstr;
      //string转char*
      const char *schar = str.c_str();
      for(int i=0;i<strlen(schar);++i){
        unsigned char k=0x80;
        for(int j=0; j<8; j++, k >>= 1){
            if (schar[i]&k){
                transsstr.append("1");
            }else{
                transsstr.append("0");
            }
        }
     }
     return transsstr;
}

string convert(char p[]){ //16进制转成文本
    int i=0;
    while(p[2*i]!='\0'&&p[2*i+1]!='\0')//'\0' :ASCII码为0,表示一个字符串结束的标志
    {
        char c = p[2*i];
        if(c<='9')
          p[i] = (c-'0')<<4;
        else if(c<='F')
          p[i] = (c-'A'+10)<<4;
        else
          p[i] = (c-'a'+10)<<4;
        c = p[2*i+1];
        if(c<='9')
          p[i] += (c-'0');
        else if(c<='F')
          p[i] += (c-'A'+10);
        else
          p[i] += (c-'a'+10);
        i++;
    }
    p[i] = '\0';
    return p;
}
string totwostring(string str){ //32位二进制转成string
    string binary = str;
    string hex;
    stringstream ss;
    ss << std::hex << stoi(binary, nullptr, 2);//https://www.cnblogs.com/tsruixi/p/12944470.html
    ss >> hex;
    transform(hex.begin(), hex.end(), hex.begin(), ::toupper);//将某操作应用于指定范围的每个元素
    char a[100];
    strcpy(a,hex.c_str());
    return convert(a);
}
string process1(string mingw,int quesizezz){//该函数对这段64位明文 返回二进制的string密文

    string mystr3[3] = {"11223344","22334455","33445566"};
    string mytwo[3] = {"","",""};
    for(int z=0;z<3;z++){
        mytwo[z] = stringtotwo(mystr3[z]);
    }
    bitset<64>bitkey11(mytwo[0]);//用string初始化
    bitset<64>bitkey22(mytwo[1]);
    bitset<64>bitkey33(mytwo[2]);//k1 k2 k3

    bitset<64>one(encrypt(bitkey33,decrypt(bitkey22,encrypt(bitkey11,mingw))));//加密过程 得到64位密文
    return one.to_string();
}
string process2(string mew,int quesizezz){//该函数对这段64位密文 返回二进制的string明文

    string mystr3[3] = {"11223344","22334455","33445566"};
    string mytwo[3] = {"","",""};
    for(int z=0;z<3;z++){
        mytwo[z] = stringtotwo(mystr3[z]);
    }
    bitset<64>bitkey11(mytwo[0]);
    bitset<64>bitkey22(mytwo[1]);
    bitset<64>bitkey33(mytwo[2]);

    bitset<64>one(decrypt(bitkey11,encrypt(bitkey22,decrypt(bitkey33,mew))));//解密过程 得到64位明文
    return one.to_string();
}
int main(){
        TLE;
        ofstream out1("ciphertext.txt");
        ofstream out2("later.txt");//写

        string returnmew;
        string returnmingw;

        //读明文文件 并补足 并分组
        ifstream in;
        in.open("former.txt");
        if(!in.is_open()){
            cerr<<"could not open this file"<<endl;
            exit(0);
        }
        char ch;
        string mingw;
        while(in.get(ch)){
            mingw.push_back(ch);
        }
        in.close();
        cout<<"mingw1: "<<mingw<<endl;
        mingw = stringtotwo(mingw);
        cout<<"mingw2: "<<mingw<<" mingw2.size(): "<<mingw.size()<<endl;
        int quesize = 64-(mingw.size()%64);
        cout<<"quesize: "<<quesize<<endl;
        int i=0;
        if(quesize==64){//证明不缺
             quesize = 0;
        }else{
            while(i < quesize){
                mingw += '0';
                i++;
            }
        }
        cout<<"mingw: "<<mingw<<endl;
        //mingw:有足够64倍数位的二进制string

        for(i=0;i<mingw.size();i=i+64){
            string s64 = mingw.substr(i,64);
            if((i == (mingw.size()-64)) && (quesize!=0)){//判断得出这是有缺失的最后一组64位
               cout<<"最后一组且有缺失"<<endl;
               cout<<"quesize: "<<quesize<<endl;
               returnmew = process1(s64,quesize);//证明后面补0了
                if (out1.is_open()) {
                    out1<<returnmew;
                }
               returnmingw = process2(returnmew,quesize);
               returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
               if (out2.is_open()) {
                    out2<<returnmingw;
               }
            }else{
                cout<<"正常的64位"<<endl;
                returnmew = process1(s64,0);
                if (out1.is_open()) {
                    out1<<returnmew;
                }
               returnmingw = process2(returnmew,0);
               returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
               if (out2.is_open()) {
                    out2<<returnmingw;
               }
            }
        }
        out1.close();
        out2.close();

        return 0;
}
//还没做页面 其他感觉差不多了
string IVstr= "0000000000000000000000000000000000000000000000000000000000000000" ;
string xorxor(string w){ //都是64位数据
    //cout<<"ivstr.length"<<IVstr.length()<<endl;
    string resultxor = "";
     for(int i=0;i<w.size();i++){

        resultxor += to_string((w[i]^IVstr[i]));
    }
    //cout<<"resultxor.length"<<resultxor.length()<<endl;
    return resultxor;
}
//===================================================
void producekey(bitset<64> bitkey){
//过程:64位密钥经置换选择1去除奇偶校验位变成56位 分开左右各28位
//循环移位:第一轮L1左移一位+R1(共56位)经过压缩置换2成48位:key1
//L1(28)继续左移一位:L2+R1(28):R2(共56位)经过压缩置换成48位:key2
//L2(28)继续左移2位:L2+R1(28):R2(共56位)经过压缩置换成48位...
//共移位16轮 每轮移位位数不同 所以直接拿数组存 到时候直接取
      bitset<56>trans1;
      bitset<28>left1,left2;
      bitset<28>right1,right2;
      bitset<56>trans2;
      bitset<48>trans3;
      for(int i=0;i<56;++i){//缩成56位:去除了奇偶校验位
        trans1[55-i] = bitkey[64-PC_1[i]];
      }
     // cout<<"producekey()--trans1: "<<trans1<<endl;
      //分左右
      for(int i=0;i<28;++i){
        right1[i] = trans1[i];
        left1[i] = trans1[i+28];
      }
      //cout<<"producekey()--right1: "<<right1<<endl;
      //cout<<"producekey()--left1: "<<left1<<endl;
      for(int round=0;round<16;round++){//一轮生成1个密钥(48)
              if(shiftBits[round] == 1){
                for(int i=27; i>0; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                }
                left2[0] = left1[27];
                right2[0] = right1[27];
              }else{
                  for(int i=27; i>1; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                 }
                  left2[1] = left1[27];left2[0] = left1[26];
                  right2[1] = right1[27];right2[0] = right1[26];
              }
              //cout<<"round: "<<round<<" left2: "<<left2<<endl;
             // cout<<"round: "<<round<<" right2: "<<right2<<endl;

              for(int i=0;i<28;i++){ //数组合并 这肯定不行啊trans2 = left2+right2;//28!!
                trans2[i] = right2[i] ;
                trans2[i+28] = left2[i];
              }
              //压缩置换成48位
              for(int i=0;i<48;++i){
                trans3[47-i] = trans2[56-PC_2[i]];
              }
              keyarray[round] = trans3;
              //cout<<"producekey()--round: "<<round<<"  "<<keyarray[round]<<endl;
              left1 = left2;
              right1 = right2;
      }

}
int changetoten(string s){//二进制的字符串转成10进制的数字

    int a,m,b=0,k=0;
    //a = atoi(s);//string转int C++中若需要将string类型转为int类型,需先将string转为const char*。
    char c[100];strcpy(c,s.c_str());
    a = atoi(c);
    while(a!=0){
        m = a%10;
        a/=10;
        b+=m*pow(2,k++);
    }
    return b;
}
string changetotwo(int a){//10进制数字转成二进制字符串
       string s;
       int result = 0, temp = a, j = 1;
	   while(temp){
		  result = result + j * (temp % 2);
		  temp = temp / 2;
		  j = j * 10;
	   }
       char t[256];
       sprintf(t, "%04d", result);//字符串位数不足高位补0
       s = t;
       return s;//都要经过中间商char数组
}
string encrypt(bitset<64>bitkey,string strwen){ //参数得是64位bitset明文 返回64位密文
       // cout<<"first--xor: "<<strwen<<endl;
        bitset<64> bitencrypt(strwen);
        bitset<64> bitdecrypt;
        bitset<64> trans1;
        bitset<32> left1;
        bitset<32> right1;
        bitset<32> temp;
        bitset<48> trans2;
        bitset<32> transsbox;
        bitset<32> transpbox;
        bitset<48> transleft;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitencrypt[64-IP[i]];
        }
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];
        }
        //NO2:密钥整体的生成
        producekey(bitkey);
        //回来了
        for(int round=0;round<16;round++){
             for(int i=0;i<48;++i){
                  transleft[47-i] = right1[32-E[i]];
             }
             transleft = transleft^keyarray[round];
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             for(int i=0;i<48;i+=6){
                   middles1 = strtransleft.substr(i,6);
                   string bemiddles1,mimiddles1;
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);
                   resu = S_BOX[i/6][row][column];
                   middles2.append(changetotwo(resu));
             }
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
        }
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }
        for(int i=0;i<64;++i){
             bitdecrypt[63-i] = trans2[64-IP_1[i]];
        }
        cout<<"encrypt()---密文: "<<bitdecrypt<<endl;
        return bitdecrypt.to_string();//转成64位二进制字符串

}

string decrypt(bitset<64>bitkey,string strwen){
        bitset<64> bitencrypt;
        bitset<64> bitdecrypt(strwen);
        bitset<64> trans1;
        bitset<32> left1;
        bitset<32> right1;
        bitset<32> temp;
        bitset<48> trans2;
        bitset<32> transsbox;
        bitset<32> transpbox;
        bitset<48> transleft;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitdecrypt[64-IP[i]];
        }
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];
        }
        //NO2:密钥整体的生成
        producekey(bitkey);

        for(int round=0;round<16;round++){
             for(int i=0;i<48;++i){
                  transleft[47-i] = right1[32-E[i]];
             }
             transleft = transleft^keyarray[15-round];
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             for(int i=0;i<48;i+=6){
                   middles1 = strtransleft.substr(i,6);
                   string bemiddles1,mimiddles1;
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);
                   resu = S_BOX[i/6][row][column];
                   middles2.append(changetotwo(resu));
             }
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
        }
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }
        for(int i=0;i<64;++i){
             bitencrypt[63-i] = trans2[64-IP_1[i]];
        }
        cout<<"decrypt()--明文: "<<bitencrypt<<endl;
        return bitencrypt.to_string();//转成64位二进制字符串
}

string stringtotwo(string str){//字符转二进制 一个字符转8位二进制  这里改  改成字符串的
      unsigned char k=0x80;//https://blog.csdn.net/caiyaodeng/article/details/48998469
      string transsstr;
      //string转char*
      const char *schar = str.c_str();
      for(int i=0;i<strlen(schar);++i){
        unsigned char k=0x80;
        for(int j=0; j<8; j++, k >>= 1){
            if (schar[i]&k){
                transsstr.append("1");
            }else{
                transsstr.append("0");
            }
        }
     }
     return transsstr;
}

string convert(char p[]){ //16进制转成文本
    int i=0;
    while(p[2*i]!='\0'&&p[2*i+1]!='\0')//'\0' :ASCII码为0,表示一个字符串结束的标志
    {
        char c = p[2*i];
        if(c<='9')
          p[i] = (c-'0')<<4;
        else if(c<='F')
          p[i] = (c-'A'+10)<<4;
        else
          p[i] = (c-'a'+10)<<4;
        c = p[2*i+1];
        if(c<='9')
          p[i] += (c-'0');
        else if(c<='F')
          p[i] += (c-'A'+10);
        else
          p[i] += (c-'a'+10);
        i++;
    }
    p[i] = '\0';
    return p;
}
string totwostring(string str){ //32位二进制转成string
    string binary = str;
    string hex;
    stringstream ss;
    ss << std::hex << stoi(binary, nullptr, 2);//https://www.cnblogs.com/tsruixi/p/12944470.html
    ss >> hex;
    transform(hex.begin(), hex.end(), hex.begin(), ::toupper);//将某操作应用于指定范围的每个元素
    char a[100];
    strcpy(a,hex.c_str());
    return convert(a);
}
string process1(string mingw,int quesizezz){//该函数对这段64位明文 返回二进制的string密文

    string mystr3[3] = {"11223344","22334455","33445566"};
    string mytwo[3] = {"","",""};
    for(int z=0;z<3;z++){
        mytwo[z] = stringtotwo(mystr3[z]);
    }
    bitset<64>bitkey11(mytwo[0]);//用string初始化
    bitset<64>bitkey22(mytwo[1]);
    bitset<64>bitkey33(mytwo[2]);//k1 k2 k3
    mingw = xorxor(mingw);
    bitset<64>one(encrypt(bitkey33,decrypt(bitkey22,encrypt(bitkey11,mingw))));//加密过程 得到64位密文
    return one.to_string();
}
string process2(string mew,int quesizezz){//该函数对这段64位密文 返回二进制的string明文

    string mystr3[3] = {"11223344","22334455","33445566"};
    string mytwo[3] = {"","",""};
    for(int z=0;z<3;z++){
        mytwo[z] = stringtotwo(mystr3[z]);
    }
    bitset<64>bitkey11(mytwo[0]);
    bitset<64>bitkey22(mytwo[1]);
    bitset<64>bitkey33(mytwo[2]);
    mew = xorxor(mew);
    bitset<64>one(decrypt(bitkey11,encrypt(bitkey22,decrypt(bitkey33,mew))));//解密过程 得到64位明文
    return one.to_string();
}
int main(){
        TLE;//加快执行速度
        ofstream out1("ciphertext.txt");
        ofstream out2("later.txt");//写

        string returnmew;
        string returnmingw;

        //读明文文件 并补足 并分组
        ifstream in;
        in.open("former.txt");
        if(!in.is_open()){
            cerr<<"could not open this file"<<endl;
            exit(0);
        }
        char ch;
        string mingw;
        while(in.get(ch)){
            mingw.push_back(ch);
        }
        in.close();
        //cout<<"mingw1: "<<mingw<<endl;
        mingw = stringtotwo(mingw);
        //cout<<"mingw2: "<<mingw<<" mingw2.size(): "<<mingw.size()<<endl;
        int quesize = 64-(mingw.size()%64);
        //cout<<"quesize: "<<quesize<<endl;
        int i=0;
        if(quesize==64){//证明不缺
             quesize = 0;
        }else{
            while(i < quesize){
                mingw += '0';
                i++;
            }
        }
        cout<<"mingw: "<<mingw<<endl;
        //mingw:有足够64倍数位的二进制string

        for(i=0;i<mingw.size();i=i+64){
            string s64 = mingw.substr(i,64);
            if((i == (mingw.size()-64)) && (quesize!=0)){//判断得出这是有缺失的最后一组64位
               //cout<<"最后一组且有缺失"<<endl;
               //cout<<"quesize: "<<quesize<<endl;
               returnmew = process1(s64,quesize);//证明后面补0了
                if (out1.is_open()) {
                    out1<<returnmew;
                }
               returnmingw = process2(returnmew,quesize);
               returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
               if (out2.is_open()) {
                    out2<<returnmingw;
               }
            }else{
                //cout<<"正常的64位"<<endl;
                returnmew = process1(s64,0);
                if (out1.is_open()) {
                    out1<<returnmew;
                }
               returnmingw = process2(returnmew,0);
               returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
               if (out2.is_open()) {
                    out2<<returnmingw;
               }
            }
        }
        out1.close();
        out2.close();

        return 0;
}

#include<bits/stdc++.h>
#define TLE ios::sync_with_stdio(0),cin.tie(0)
using namespace std;

bitset<48> keyarray[16];
// 初始置换表
int IP[] = { 58, 50, 42, 34, 26, 18, 10, 2,
			 60, 52, 44, 36, 28, 20, 12, 4,
			 62, 54, 46, 38, 30, 22, 14, 6,
			 64, 56, 48, 40, 32, 24, 16, 8,
			 57, 49, 41, 33, 25, 17, 9,  1,
			 59, 51, 43, 35, 27, 19, 11, 3,
			 61, 53, 45, 37, 29, 21, 13, 5,
			 63, 55, 47, 39, 31, 23, 15, 7 };

/*------------------下面是生成密钥所用表-----------------*/
int PC_1[] = {57, 49, 41, 33, 25, 17, 9,
			   1, 58, 50, 42, 34, 26, 18,
			  10,  2, 59, 51, 43, 35, 27,
			  19, 11,  3, 60, 52, 44, 36,
			  63, 55, 47, 39, 31, 23, 15,
			   7, 62, 54, 46, 38, 30, 22,
			  14,  6, 61, 53, 45, 37, 29,
			  21, 13,  5, 28, 20, 12,  4};
int PC_2[] = {14, 17, 11, 24,  1,  5,
			   3, 28, 15,  6, 21, 10,
			  23, 19, 12,  4, 26,  8,
			  16,  7, 27, 20, 13,  2,
			  41, 52, 31, 37, 47, 55,
			  30, 40, 51, 45, 33, 48,
			  44, 49, 39, 56, 34, 53,
			  46, 42, 50, 36, 29, 32};
int shiftBits[] = {1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1};

/*------------------轮函数-----------------*/
// 扩展置换表,将32位扩展至48位
int E[] = {32,  1,  2,  3,  4,  5,
		    4,  5,  6,  7,  8,  9,
		    8,  9, 10, 11, 12, 13,
		   12, 13, 14, 15, 16, 17,
		   16, 17, 18, 19, 20, 21,
		   20, 21, 22, 23, 24, 25,
		   24, 25, 26, 27, 28, 29,
		   28, 29, 30, 31, 32,  1};
// S盒,每个S盒是4x16的置换表,6位 -> 4位
int S_BOX[8][4][16] = {
	{
		{14,4,13,1,2,15,11,8,3,10,6,12,5,9,0,7},
		{0,15,7,4,14,2,13,1,10,6,12,11,9,5,3,8},
		{4,1,14,8,13,6,2,11,15,12,9,7,3,10,5,0},
		{15,12,8,2,4,9,1,7,5,11,3,14,10,0,6,13}
	},
	{
		{15,1,8,14,6,11,3,4,9,7,2,13,12,0,5,10},
		{3,13,4,7,15,2,8,14,12,0,1,10,6,9,11,5},
		{0,14,7,11,10,4,13,1,5,8,12,6,9,3,2,15},
		{13,8,10,1,3,15,4,2,11,6,7,12,0,5,14,9}
	},
	{
		{10,0,9,14,6,3,15,5,1,13,12,7,11,4,2,8},
		{13,7,0,9,3,4,6,10,2,8,5,14,12,11,15,1},
		{13,6,4,9,8,15,3,0,11,1,2,12,5,10,14,7},
		{1,10,13,0,6,9,8,7,4,15,14,3,11,5,2,12}
	},
	{
		{7,13,14,3,0,6,9,10,1,2,8,5,11,12,4,15},
		{13,8,11,5,6,15,0,3,4,7,2,12,1,10,14,9},
		{10,6,9,0,12,11,7,13,15,1,3,14,5,2,8,4},
		{3,15,0,6,10,1,13,8,9,4,5,11,12,7,2,14}
	},
	{
		{2,12,4,1,7,10,11,6,8,5,3,15,13,0,14,9},
		{14,11,2,12,4,7,13,1,5,0,15,10,3,9,8,6},
		{4,2,1,11,10,13,7,8,15,9,12,5,6,3,0,14},
		{11,8,12,7,1,14,2,13,6,15,0,9,10,4,5,3}
	},
	{
		{12,1,10,15,9,2,6,8,0,13,3,4,14,7,5,11},
		{10,15,4,2,7,12,9,5,6,1,13,14,0,11,3,8},
		{9,14,15,5,2,8,12,3,7,0,4,10,1,13,11,6},
		{4,3,2,12,9,5,15,10,11,14,1,7,6,0,8,13}
	},
	{
		{4,11,2,14,15,0,8,13,3,12,9,7,5,10,6,1},
		{13,0,11,7,4,9,1,10,14,3,5,12,2,15,8,6},
		{1,4,11,13,12,3,7,14,10,15,6,8,0,5,9,2},
		{6,11,13,8,1,4,10,7,9,5,0,15,14,2,3,12}
	},
	{
		{13,2,8,4,6,15,11,1,10,9,3,14,5,0,12,7},
		{1,15,13,8,10,3,7,4,12,5,6,11,0,14,9,2},
		{7,11,4,1,9,12,14,2,0,6,10,13,15,3,5,8},
		{2,1,14,7,4,10,8,13,15,12,9,0,3,5,6,11}
	}
};
// P盒置换
int P[] = {16,  7, 20, 21,
		   29, 12, 28, 17,
		    1, 15, 23, 26,
		    5, 18, 31, 10,
		    2,  8, 24, 14,
		   32, 27,  3,  9,
		   19, 13, 30,  6,
		   22, 11,  4, 25 };
/*--------------------------------------*/
//初始逆置换
int IP_1[] = {40, 8, 48, 16, 56, 24, 64, 32,
			  39, 7, 47, 15, 55, 23, 63, 31,
			  38, 6, 46, 14, 54, 22, 62, 30,
			  37, 5, 45, 13, 53, 21, 61, 29,
			  36, 4, 44, 12, 52, 20, 60, 28,
			  35, 3, 43, 11, 51, 19, 59, 27,
			  34, 2, 42, 10, 50, 18, 58, 26,
			  33, 1, 41,  9, 49, 17, 57, 25};

string IVstr= "0000000000000000000000000000000000000000000000000000000000000000" ;
string xorxor(string w){ //都是64位数据
    //cout<<"ivstr.length"<<IVstr.length()<<endl;
    string resultxor = "";
     for(int i=0;i<w.size();i++){

        resultxor += to_string((w[i]^IVstr[i]));
    }
    //cout<<"resultxor.length"<<resultxor.length()<<endl;
    return resultxor;
}
//===================================================
void producekey(bitset<64> bitkey){
//过程:64位密钥经置换选择1去除奇偶校验位变成56位 分开左右各28位
//循环移位:第一轮L1左移一位+R1(共56位)经过压缩置换2成48位:key1
//L1(28)继续左移一位:L2+R1(28):R2(共56位)经过压缩置换成48位:key2
//L2(28)继续左移2位:L2+R1(28):R2(共56位)经过压缩置换成48位...
//共移位16轮 每轮移位位数不同 所以直接拿数组存 到时候直接取
      bitset<56>trans1;
      bitset<28>left1,left2;
      bitset<28>right1,right2;
      bitset<56>trans2;
      bitset<48>trans3;
      for(int i=0;i<56;++i){//缩成56位:去除了奇偶校验位
        trans1[55-i] = bitkey[64-PC_1[i]];
      }
     // cout<<"producekey()--trans1: "<<trans1<<endl;
      //分左右
      for(int i=0;i<28;++i){
        right1[i] = trans1[i];
        left1[i] = trans1[i+28];
      }
      //cout<<"producekey()--right1: "<<right1<<endl;
      //cout<<"producekey()--left1: "<<left1<<endl;
      for(int round=0;round<16;round++){//一轮生成1个密钥(48)
              if(shiftBits[round] == 1){
                for(int i=27; i>0; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                }
                left2[0] = left1[27];
                right2[0] = right1[27];
              }else{
                  for(int i=27; i>1; i--){
                    //循环向左移位
                    left2[i]=left1[i-shiftBits[round]];
                    right2[i]=right1[i-shiftBits[round]];
                 }
                  left2[1] = left1[27];left2[0] = left1[26];
                  right2[1] = right1[27];right2[0] = right1[26];
              }
              //cout<<"round: "<<round<<" left2: "<<left2<<endl;
             // cout<<"round: "<<round<<" right2: "<<right2<<endl;

              for(int i=0;i<28;i++){ //数组合并 这肯定不行啊trans2 = left2+right2;//28!!
                trans2[i] = right2[i] ;
                trans2[i+28] = left2[i];
              }
              //压缩置换成48位
              for(int i=0;i<48;++i){
                trans3[47-i] = trans2[56-PC_2[i]];
              }
              keyarray[round] = trans3;
              //cout<<"producekey()--round: "<<round<<"  "<<keyarray[round]<<endl;
              left1 = left2;
              right1 = right2;
      }

}
int changetoten(string s){//二进制的字符串转成10进制的数字

    int a,m,b=0,k=0;
    //a = atoi(s);//string转int C++中若需要将string类型转为int类型,需先将string转为const char*。
    char c[100];strcpy(c,s.c_str());
    a = atoi(c);
    while(a!=0){
        m = a%10;
        a/=10;
        b+=m*pow(2,k++);
    }
    return b;
}
string changetotwo(int a){//10进制数字转成二进制字符串
       string s;
       int result = 0, temp = a, j = 1;
	   while(temp){
		  result = result + j * (temp % 2);
		  temp = temp / 2;
		  j = j * 10;
	   }
       char t[256];
       sprintf(t, "%04d", result);//字符串位数不足高位补0
       s = t;
       return s;//都要经过中间商char数组
}
string encrypt(bitset<64>bitkey,string strwen){ //参数得是64位bitset明文 返回64位密文
       // cout<<"first--xor: "<<strwen<<endl;
        bitset<64> bitencrypt(strwen);
        bitset<64> bitdecrypt;
        bitset<64> trans1;
        bitset<32> left1;
        bitset<32> right1;
        bitset<32> temp;
        bitset<48> trans2;
        bitset<32> transsbox;
        bitset<32> transpbox;
        bitset<48> transleft;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitencrypt[64-IP[i]];
        }
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];
        }
        //NO2:密钥整体的生成
        producekey(bitkey);
        //回来了
        for(int round=0;round<16;round++){
             for(int i=0;i<48;++i){
                  transleft[47-i] = right1[32-E[i]];
             }
             transleft = transleft^keyarray[round];
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             for(int i=0;i<48;i+=6){
                   middles1 = strtransleft.substr(i,6);
                   string bemiddles1,mimiddles1;
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);
                   resu = S_BOX[i/6][row][column];
                   middles2.append(changetotwo(resu));
             }
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
        }
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }
        for(int i=0;i<64;++i){
             bitdecrypt[63-i] = trans2[64-IP_1[i]];
        }
        //cout<<"encrypt()---密文: "<<bitdecrypt<<endl;
        return bitdecrypt.to_string();//转成64位二进制字符串

}

string decrypt(bitset<64>bitkey,string strwen){
        bitset<64> bitencrypt;bitset<64> bitdecrypt(strwen);bitset<64> trans1;
        bitset<32> left1;bitset<32> right1;bitset<32> temp;
        bitset<48> trans2;bitset<32> transsbox;bitset<32> transpbox;
        bitset<48> transleft;
        for(int i=0;i<64;++i){
            trans1[63-i] = bitdecrypt[64-IP[i]];
        }
        for(int i=0;i<32;++i){
            right1[i] =trans1[i];
            left1[i] = trans1[i+32];
        }
        producekey(bitkey);
        for(int round=0;round<16;round++){
             for(int i=0;i<48;++i){
                  transleft[47-i] = right1[32-E[i]];
             }
             transleft = transleft^keyarray[15-round];//区别之一
             string strtransleft = transleft.to_string();
             string middles1,middles2;
             int row,column,resu;
             for(int i=0;i<48;i+=6){
                   middles1 = strtransleft.substr(i,6);
                   string bemiddles1,mimiddles1;
                   bemiddles1+=middles1[0];
                   bemiddles1+=middles1[5];
                   row = changetoten(bemiddles1);
                   mimiddles1+=middles1[1];
                   mimiddles1+=middles1[2];
                   mimiddles1+=middles1[3];
                   mimiddles1+=middles1[4];
                   column = changetoten(mimiddles1);
                   resu = S_BOX[i/6][row][column];
                   middles2.append(changetotwo(resu));
             }
             bitset<32> strtobit(middles2);
             transsbox = strtobit;
             for(int i=0;i<32;++i){
                 transpbox[31-i] = transsbox[32-P[i]];
             }
             temp = right1;
             right1=left1^transpbox;
             left1 = temp;
        }
        for(int i=0;i<32;++i){
            trans2[i] = left1[i];
            trans2[i+32] = right1[i];
        }
        for(int i=0;i<64;++i){
             bitencrypt[63-i] = trans2[64-IP_1[i]];
        }
        return bitencrypt.to_string();//转成64位二进制字符串
}

string stringtotwo(string str){//字符转二进制 一个字符转8位二进制  这里改  改成字符串的
      unsigned char k=0x80;//https://blog.csdn.net/caiyaodeng/article/details/48998469
      string transsstr;
      //string转char*
      const char *schar = str.c_str();
      for(int i=0;i<strlen(schar);++i){
        unsigned char k=0x80;
        for(int j=0; j<8; j++, k >>= 1){
            if (schar[i]&k){
                transsstr.append("1");
            }else{
                transsstr.append("0");
            }
        }
     }
     return transsstr;
}

string convert(char p[]){ //16进制转成文本
    int i=0;
    while(p[2*i]!='\0'&&p[2*i+1]!='\0')//'\0' :ASCII码为0,表示一个字符串结束的标志
    {
        char c = p[2*i];
        if(c<='9')
          p[i] = (c-'0')<<4;
        else if(c<='F')
          p[i] = (c-'A'+10)<<4;
        else
          p[i] = (c-'a'+10)<<4;
        c = p[2*i+1];
        if(c<='9')
          p[i] += (c-'0');
        else if(c<='F')
          p[i] += (c-'A'+10);
        else
          p[i] += (c-'a'+10);
        i++;
    }
    p[i] = '\0';
    return p;
}
string totwostring(string str){ //32位二进制转成string
    string binary = str;
    string hex;
    stringstream ss;
    ss << std::hex << stoi(binary, nullptr, 2);//https://www.cnblogs.com/tsruixi/p/12944470.html
    ss >> hex;
    transform(hex.begin(), hex.end(), hex.begin(), ::toupper);//将某操作应用于指定范围的每个元素
    char a[100];
    strcpy(a,hex.c_str());
    return convert(a);
}
string process1(string mingw,int quesizezz){//该函数对这段64位明文 返回二进制的string密文

    string mystr3[3] = {"11223344","22334455","33445566"};
    string mytwo[3] = {"","",""};
    for(int z=0;z<3;z++){
        mytwo[z] = stringtotwo(mystr3[z]);
    }
    bitset<64>bitkey11(mytwo[0]);//用string初始化
    bitset<64>bitkey22(mytwo[1]);
    bitset<64>bitkey33(mytwo[2]);//k1 k2 k3
    mingw = xorxor(mingw);
    bitset<64>one(encrypt(bitkey33,decrypt(bitkey22,encrypt(bitkey11,mingw))));//加密过程 得到64位密文
    return one.to_string();
}
string process2(string mew,int quesizezz){//该函数对这段64位密文 返回二进制的string明文

    string mystr3[3] = {"11223344","22334455","33445566"};
    string mytwo[3] = {"","",""};
    for(int z=0;z<3;z++){
        mytwo[z] = stringtotwo(mystr3[z]);
    }
    bitset<64>bitkey11(mytwo[0]);
    bitset<64>bitkey22(mytwo[1]);
    bitset<64>bitkey33(mytwo[2]);
    mew = xorxor(mew);
    bitset<64>one(decrypt(bitkey11,encrypt(bitkey22,decrypt(bitkey33,mew))));//解密过程 得到64位明文
    return one.to_string();
}
void start(){ //一句话没写完 换行了 换行符应该处理
    ofstream out1("ciphertext.txt");
    ofstream out2("later.txt");//写

    string returnmew;
    string returnmingw;
    //读明文文件 并补足 并分组
    ifstream in;
    in.open("former.txt");
    if(!in.is_open()){
        cerr<<"could not open this file"<<endl;
        exit(0);
    }//对文件内容开始处理
    string str;
    while(getline(in,str)){ //按行处理
         cout<<str<<endl;
         char ch;
         string mingw = str;
//        while(in.get(ch)){
//            mingw.push_back(ch);
//        }
//        in.close();
        //cout<<"mingw1: "<<mingw<<endl;
        mingw = stringtotwo(mingw);
        //cout<<"mingw2: "<<mingw<<" mingw2.size(): "<<mingw.size()<<endl;
        int quesize = 64-(mingw.size()%64);
        //cout<<"quesize: "<<quesize<<endl;
        int i=0;
        if(quesize==64){//证明不缺
             quesize = 0;
        }else{
            while(i < quesize){
                mingw += '0';
                i++;
            }
        }
        //cout<<"mingw: "<<mingw<<endl;
        for(i=0;i<mingw.size();i=i+64){//mingw:有足够64倍数位的二进制string
            string s64 = mingw.substr(i,64);
            if((i == (mingw.size()-64)) && (quesize!=0)){//判断得出这是有缺失的最后一组64位
               //cout<<"最后一组且有缺失"<<endl;
               //cout<<"quesize: "<<quesize<<endl;
               returnmew = process1(s64,quesize);//证明后面补0了
                if (out1.is_open()) {
                    out1<<returnmew;
                }
               returnmingw = process2(returnmew,quesize);
               returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
               if (out2.is_open()) {
                    out2<<returnmingw;
               }
            }else{
                //cout<<"正常的64位"<<endl;
                returnmew = process1(s64,0);
                if (out1.is_open()) {
                    out1<<returnmew;
                }
               returnmingw = process2(returnmew,0);
               returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
               if (out2.is_open()) {
                    out2<<returnmingw;
               }
            }
        }
       out2<<endl;//输出到文件时也换行操作
    }

//    char ch;
//    string mingw;
//    while(in.get(ch)){
//        mingw.push_back(ch);
//    }
//    in.close();
//    //cout<<"mingw1: "<<mingw<<endl;
//    mingw = stringtotwo(mingw);
//    //cout<<"mingw2: "<<mingw<<" mingw2.size(): "<<mingw.size()<<endl;
//    int quesize = 64-(mingw.size()%64);
//    //cout<<"quesize: "<<quesize<<endl;
//    int i=0;
//    if(quesize==64){//证明不缺
//         quesize = 0;
//    }else{
//        while(i < quesize){
//            mingw += '0';
//            i++;
//        }
//    }
//    //cout<<"mingw: "<<mingw<<endl;
//    for(i=0;i<mingw.size();i=i+64){//mingw:有足够64倍数位的二进制string
//        string s64 = mingw.substr(i,64);
//        if((i == (mingw.size()-64)) && (quesize!=0)){//判断得出这是有缺失的最后一组64位
//           //cout<<"最后一组且有缺失"<<endl;
//           //cout<<"quesize: "<<quesize<<endl;
//           returnmew = process1(s64,quesize);//证明后面补0了
//            if (out1.is_open()) {
//                out1<<returnmew;
//            }
//           returnmingw = process2(returnmew,quesize);
//           returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
//           if (out2.is_open()) {
//                out2<<returnmingw;
//           }
//        }else{
//            //cout<<"正常的64位"<<endl;
//            returnmew = process1(s64,0);
//            if (out1.is_open()) {
//                out1<<returnmew;
//            }
//           returnmingw = process2(returnmew,0);
//           returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
//           if (out2.is_open()) {
//                out2<<returnmingw;
//           }
//        }
//    }

    //文件内容处理完毕
    out1.close();
    out2.close();

}
int main(){
        TLE;//加快执行速度
        start();

        return 0;
}

代码移植到QT上

#ifndef WIDGET_H
#define WIDGET_H
#include<bits/stdc++.h>//https://blog.csdn.net/Niro_z/article/details/8028996
#include <QWidget>
#include <QPushButton>
using namespace std;


namespace Ui {
class Widget;
}

class Widget : public QWidget
{
    Q_OBJECT

public:
    explicit Widget(QWidget *parent = 0);
    ~Widget();

    string xorxor(string w);
    void producekey(bitset<64> bitkey);
    int changetoten(string s);
    string changetotwo(int a);
    string encrypt(bitset<64>bitkey,string strwen);
    string decrypt(bitset<64>bitkey,string strwen);
    string stringtotwo(string str);
    string convert(char p[]);
    string totwostring(string str);
    string process1(string mingw,int quesizezz);
    string process2(string mew,int quesizezz);
    void start();

private:
    Ui::Widget *ui;
    QPushButton button;
};

#endif // WIDGET_H

'''

include "widget.h"

include "ui_widget.h"

include

include<bits/stdc++.h>

include

include

include //可以指定编码

include

include

define TLE ios::sync_with_stdio(0),cin.tie(0)

using namespace std;

bitset<48> keyarray[16];
int IP[] = { 58, 50, 42, 34, 26, 18, 10, 2,
60, 52, 44, 36, 28, 20, 12, 4,
62, 54, 46, 38, 30, 22, 14, 6,
64, 56, 48, 40, 32, 24, 16, 8,
57, 49, 41, 33, 25, 17, 9, 1,
59, 51, 43, 35, 27, 19, 11, 3,
61, 53, 45, 37, 29, 21, 13, 5,
63, 55, 47, 39, 31, 23, 15, 7 };

int PC_1[] = {57, 49, 41, 33, 25, 17, 9,
1, 58, 50, 42, 34, 26, 18,
10, 2, 59, 51, 43, 35, 27,
19, 11, 3, 60, 52, 44, 36,
63, 55, 47, 39, 31, 23, 15,
7, 62, 54, 46, 38, 30, 22,
14, 6, 61, 53, 45, 37, 29,
21, 13, 5, 28, 20, 12, 4};
int PC_2[] = {14, 17, 11, 24, 1, 5,
3, 28, 15, 6, 21, 10,
23, 19, 12, 4, 26, 8,
16, 7, 27, 20, 13, 2,
41, 52, 31, 37, 47, 55,
30, 40, 51, 45, 33, 48,
44, 49, 39, 56, 34, 53,
46, 42, 50, 36, 29, 32};
int shiftBits[] = {1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1};

int E[] = {32, 1, 2, 3, 4, 5,
4, 5, 6, 7, 8, 9,
8, 9, 10, 11, 12, 13,
12, 13, 14, 15, 16, 17,
16, 17, 18, 19, 20, 21,
20, 21, 22, 23, 24, 25,
24, 25, 26, 27, 28, 29,
28, 29, 30, 31, 32, 1};
int S_BOX[8][4][16] = {
{
{14,4,13,1,2,15,11,8,3,10,6,12,5,9,0,7},
{0,15,7,4,14,2,13,1,10,6,12,11,9,5,3,8},
{4,1,14,8,13,6,2,11,15,12,9,7,3,10,5,0},
{15,12,8,2,4,9,1,7,5,11,3,14,10,0,6,13}
},
{
{15,1,8,14,6,11,3,4,9,7,2,13,12,0,5,10},
{3,13,4,7,15,2,8,14,12,0,1,10,6,9,11,5},
{0,14,7,11,10,4,13,1,5,8,12,6,9,3,2,15},
{13,8,10,1,3,15,4,2,11,6,7,12,0,5,14,9}
},
{
{10,0,9,14,6,3,15,5,1,13,12,7,11,4,2,8},
{13,7,0,9,3,4,6,10,2,8,5,14,12,11,15,1},
{13,6,4,9,8,15,3,0,11,1,2,12,5,10,14,7},
{1,10,13,0,6,9,8,7,4,15,14,3,11,5,2,12}
},
{
{7,13,14,3,0,6,9,10,1,2,8,5,11,12,4,15},
{13,8,11,5,6,15,0,3,4,7,2,12,1,10,14,9},
{10,6,9,0,12,11,7,13,15,1,3,14,5,2,8,4},
{3,15,0,6,10,1,13,8,9,4,5,11,12,7,2,14}
},
{
{2,12,4,1,7,10,11,6,8,5,3,15,13,0,14,9},
{14,11,2,12,4,7,13,1,5,0,15,10,3,9,8,6},
{4,2,1,11,10,13,7,8,15,9,12,5,6,3,0,14},
{11,8,12,7,1,14,2,13,6,15,0,9,10,4,5,3}
},
{
{12,1,10,15,9,2,6,8,0,13,3,4,14,7,5,11},
{10,15,4,2,7,12,9,5,6,1,13,14,0,11,3,8},
{9,14,15,5,2,8,12,3,7,0,4,10,1,13,11,6},
{4,3,2,12,9,5,15,10,11,14,1,7,6,0,8,13}
},
{
{4,11,2,14,15,0,8,13,3,12,9,7,5,10,6,1},
{13,0,11,7,4,9,1,10,14,3,5,12,2,15,8,6},
{1,4,11,13,12,3,7,14,10,15,6,8,0,5,9,2},
{6,11,13,8,1,4,10,7,9,5,0,15,14,2,3,12}
},
{
{13,2,8,4,6,15,11,1,10,9,3,14,5,0,12,7},
{1,15,13,8,10,3,7,4,12,5,6,11,0,14,9,2},
{7,11,4,1,9,12,14,2,0,6,10,13,15,3,5,8},
{2,1,14,7,4,10,8,13,15,12,9,0,3,5,6,11}
}
};
int P[] = {16, 7, 20, 21,
29, 12, 28, 17,
1, 15, 23, 26,
5, 18, 31, 10,
2, 8, 24, 14,
32, 27, 3, 9,
19, 13, 30, 6,
22, 11, 4, 25 };
int IP_1[] = {40, 8, 48, 16, 56, 24, 64, 32,
39, 7, 47, 15, 55, 23, 63, 31,
38, 6, 46, 14, 54, 22, 62, 30,
37, 5, 45, 13, 53, 21, 61, 29,
36, 4, 44, 12, 52, 20, 60, 28,
35, 3, 43, 11, 51, 19, 59, 27,
34, 2, 42, 10, 50, 18, 58, 26,
33, 1, 41, 9, 49, 17, 57, 25};
string IVstr= "0000000000000000000000000000000000000000000000000000000000000000" ;

Widget::Widget(QWidget *parent) :
QWidget(parent),
ui(new Ui::Widget)
{
ui->setupUi(this);

//构造函数
button.setParent(this);
button.setText("3DES加密");
button.move(100,100);
//connect(&button,&QPushButton::clicked,this,&Widget::close);
connect(&button,&QPushButton::clicked,this,&Widget::start);

}

Widget::~Widget()
{
delete ui;
}

string Widget::xorxor(string w){
string resultxor = "";
for(int i=0;i<w.size();i++){

    resultxor += to_string((w[i]^IVstr[i]));
}
return resultxor;

}

void Widget::producekey(bitset<64> bitkey){
bitset<56>trans1;
bitset<28>left1,left2;
bitset<28>right1,right2;
bitset<56>trans2;
bitset<48>trans3;
for(int i=0;i<56;++i){
trans1[55-i] = bitkey[64-PC_1[i]];
}

  for(int i=0;i<28;++i){
    right1[i] = trans1[i];
    left1[i] = trans1[i+28];
  }
  for(int round=0;round<16;round++){
          if(shiftBits[round] == 1){
            for(int i=27; i>0; i--){
                left2[i]=left1[i-shiftBits[round]];
                right2[i]=right1[i-shiftBits[round]];
            }
            left2[0] = left1[27];
            right2[0] = right1[27];
          }else{
              for(int i=27; i>1; i--){
                left2[i]=left1[i-shiftBits[round]];
                right2[i]=right1[i-shiftBits[round]];
             }
              left2[1] = left1[27];left2[0] = left1[26];
              right2[1] = right1[27];right2[0] = right1[26];
          }
          for(int i=0;i<28;i++){
            trans2[i] = right2[i] ;
            trans2[i+28] = left2[i];
          }
          for(int i=0;i<48;++i){
            trans3[47-i] = trans2[56-PC_2[i]];
          }
          keyarray[round] = trans3;
          left1 = left2;
          right1 = right2;
  }

}

int Widget::changetoten(string s){
int a,m,b=0,k=0;
char c[100];strcpy(c,s.c_str());
a = atoi(c);
while(a!=0){
m = a%10;
a/=10;
b+=m*pow(2,k++);
}
return b;
}

string Widget::changetotwo(int a){
string s;
int result = 0, temp = a, j = 1;
while(temp){
result = result + j * (temp % 2);
temp = temp / 2;
j = j * 10;
}
char t[256];
sprintf(t, "%04d", result);
s = t;
return s;
}

string Widget::encrypt(bitset<64>bitkey,string strwen){
bitset<64> bitencrypt(strwen);
bitset<64> bitdecrypt;
bitset<64> trans1;
bitset<32> left1;
bitset<32> right1;
bitset<32> temp;
bitset<48> trans2;
bitset<32> transsbox;
bitset<32> transpbox;
bitset<48> transleft;
for(int i=0;i<64;++i){
trans1[63-i] = bitencrypt[64-IP[i]];
}
for(int i=0;i<32;++i){
right1[i] =trans1[i];
left1[i] = trans1[i+32];
}
producekey(bitkey);
for(int round=0;round<16;round++){
for(int i=0;i<48;++i){
transleft[47-i] = right1[32-E[i]];
}
transleft = transleft^keyarray[round];
string strtransleft = transleft.to_string();
string middles1,middles2;
int row,column,resu;
for(int i=0;i<48;i+=6){
middles1 = strtransleft.substr(i,6);
string bemiddles1,mimiddles1;
bemiddles1+=middles1[0];
bemiddles1+=middles1[5];
row = changetoten(bemiddles1);
mimiddles1+=middles1[1];
mimiddles1+=middles1[2];
mimiddles1+=middles1[3];
mimiddles1+=middles1[4];
column = changetoten(mimiddles1);
resu = S_BOX[i/6][row][column];
middles2.append(changetotwo(resu));
}
bitset<32> strtobit(middles2);
transsbox = strtobit;
for(int i=0;i<32;++i){
transpbox[31-i] = transsbox[32-P[i]];
}
temp = right1;
right1=left1^transpbox;
left1 = temp;
}
for(int i=0;i<32;++i){
trans2[i] = left1[i];
trans2[i+32] = right1[i];
}
for(int i=0;i<64;++i){
bitdecrypt[63-i] = trans2[64-IP_1[i]];
}
return bitdecrypt.to_string();
}

string Widget::decrypt(bitset<64>bitkey,string strwen){
bitset<64> bitencrypt;bitset<64> bitdecrypt(strwen);bitset<64> trans1;
bitset<32> left1;bitset<32> right1;bitset<32> temp;
bitset<48> trans2;bitset<32> transsbox;bitset<32> transpbox;
bitset<48> transleft;
for(int i=0;i<64;++i){
trans1[63-i] = bitdecrypt[64-IP[i]];
}
for(int i=0;i<32;++i){
right1[i] =trans1[i];
left1[i] = trans1[i+32];
}
producekey(bitkey);
for(int round=0;round<16;round++){
for(int i=0;i<48;++i){
transleft[47-i] = right1[32-E[i]];
}
transleft = transleft^keyarray[15-round];//区别之一
string strtransleft = transleft.to_string();
string middles1,middles2;
int row,column,resu;
for(int i=0;i<48;i+=6){
middles1 = strtransleft.substr(i,6);
string bemiddles1,mimiddles1;
bemiddles1+=middles1[0];
bemiddles1+=middles1[5];
row = changetoten(bemiddles1);
mimiddles1+=middles1[1];
mimiddles1+=middles1[2];
mimiddles1+=middles1[3];
mimiddles1+=middles1[4];
column = changetoten(mimiddles1);
resu = S_BOX[i/6][row][column];
middles2.append(changetotwo(resu));
}
bitset<32> strtobit(middles2);
transsbox = strtobit;
for(int i=0;i<32;++i){
transpbox[31-i] = transsbox[32-P[i]];
}
temp = right1;
right1=left1^transpbox;
left1 = temp;
}
for(int i=0;i<32;++i){
trans2[i] = left1[i];
trans2[i+32] = right1[i];
}
for(int i=0;i<64;++i){
bitencrypt[63-i] = trans2[64-IP_1[i]];
}
return bitencrypt.to_string();
}

string Widget::stringtotwo(string str){
unsigned char k=0x80;
string transsstr;
const char *schar = str.c_str();
for(int i=0;i<strlen(schar);++i){
unsigned char k=0x80;
for(int j=0; j<8; j++, k >>= 1){
if (schar[i]&k){
transsstr.append("1");
}else{
transsstr.append("0");
}
}
}
return transsstr;
}

string Widget::convert(char p[]){
int i=0;
while(p[2i]!='\0'&&p[2i+1]!='\0')
{
char c = p[2i];
if(c<='9')
p[i] = (c-'0')<<4;
else if(c<='F')
p[i] = (c-'A'+10)<<4;
else
p[i] = (c-'a'+10)<<4;
c = p[2
i+1];
if(c<='9')
p[i] += (c-'0');
else if(c<='F')
p[i] += (c-'A'+10);
else
p[i] += (c-'a'+10);
i++;
}
p[i] = '\0';
return p;
}

string Widget::totwostring(string str){
string binary = str;
string hex;
stringstream ss;
ss << std::hex << stoi(binary, nullptr, 2);
ss >> hex;
transform(hex.begin(), hex.end(), hex.begin(), ::toupper);
char a[100];
strcpy(a,hex.c_str());
return convert(a);
}

string Widget::process1(string mingw,int quesizezz){

string mystr3[3] = {"11223344","22334455","33445566"};
string mytwo[3] = {"","",""};
for(int z=0;z<3;z++){
    mytwo[z] = stringtotwo(mystr3[z]);
}
bitset<64>bitkey11(mytwo[0]);
bitset<64>bitkey22(mytwo[1]);
bitset<64>bitkey33(mytwo[2]);
mingw = xorxor(mingw);
bitset<64>one(encrypt(bitkey33,decrypt(bitkey22,encrypt(bitkey11,mingw))));
return one.to_string();

}
string Widget::process2(string mew,int quesizezz){

string mystr3[3] = {"11223344","22334455","33445566"};
string mytwo[3] = {"","",""};
for(int z=0;z<3;z++){
    mytwo[z] = stringtotwo(mystr3[z]);
}
bitset<64>bitkey11(mytwo[0]);
bitset<64>bitkey22(mytwo[1]);
bitset<64>bitkey33(mytwo[2]);
mew = xorxor(mew);
bitset<64>one(decrypt(bitkey11,encrypt(bitkey22,decrypt(bitkey33,mew))));
return one.to_string();

}

void Widget::start(){
TLE;
QString str;
string returnmew;string returnmingw;

QFile out1("E:\\QT\\QTCode\\1129\\ciphertext.txt");
QFile out2("E:\\QT\\QTCode\\1129\\later.txt");
QTextStream txtOutput1(&out1);
QTextStream txtOutput2(&out2);


QFile aFile("E:\\QT\\QTCode\\1129\\former.txt");

if (!aFile.exists()) {
    cout<<"error"<<endl;
}

if (!aFile.open(QIODevice::ReadOnly | QIODevice::Text)){
    cout<<"error"<<endl;
}

QTextStream aStream(&aFile); //用文本流读取文件
while(!aStream.atEnd()){   //进不来getline(in,str)
    str = aStream.readLine();
    char ch;
    string mingw = string((const char *)str.toLocal8Bit());;
    mingw = stringtotwo(mingw);
    int quesize = 64-(mingw.size()%64);
    int i=0;
    if(quesize==64){
         quesize = 0;
    }else{
        while(i < quesize){
            mingw += '0';
            i++;
        }
    }
    for(i=0;i<mingw.size();i=i+64){
        string s64 = mingw.substr(i,64);
        if((i == (mingw.size()-64)) && (quesize!=0)){
           returnmew = process1(s64,quesize);
            if (out1.open(QIODevice::WriteOnly)) {
                //out1<<returnmew;
                txtOutput1 << QString(QString::fromLocal8Bit(returnmew.c_str()));
            }
           //txtOutput1<<returnmew;
           //txtOutput1 << QString(QString::fromLocal8Bit(returnmew.c_str()));
           returnmingw = process2(returnmew,quesize);
           returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
           if (out2.open(QIODevice::WriteOnly)) {
                txtOutput2<< QString(QString::fromLocal8Bit(returnmingw.c_str()));
           }
           //txtOutput2<< QString(QString::fromLocal8Bit(returnmingw.c_str()));
        }else{
            returnmew = process1(s64,0);
            if (out1.open(QIODevice::WriteOnly)) {
               // out1<<returnmew;
                txtOutput1<<QString(QString::fromLocal8Bit(returnmingw.c_str()));
            }
            txtOutput1<<QString(QString::fromLocal8Bit(returnmingw.c_str()));
           returnmingw = process2(returnmew,0);
           returnmingw = totwostring(returnmingw.substr(0,32)) + totwostring(returnmingw.substr(32,32));
           if (out2.open(QIODevice::WriteOnly)) {
               txtOutput2<<QString(QString::fromLocal8Bit(returnmingw.c_str()));
           }
           //txtOutput2<<QString(QString::fromLocal8Bit(returnmingw.c_str()));
        }
    }
   txtOutput2<<endl;
}
out1.close();
out2.close();

}

'''

#include "widget.h"
#include <QApplication>
#include <QPushButton>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    Widget w;//去执行构造函数
    w.setWindowTitle(QString("3DES加解密"));
    w.resize(600,600);
    w.show();
    return a.exec();
}

posted @ 2020-11-10 11:49  像走了一光年  阅读(190)  评论(0编辑  收藏  举报