信息加密之Transposition Cipher(变位密码)

本文介绍了一种简单的对称加密方法——变位密码,并通过示例代码详细展示了加密与解密的过程。该方法通过重新排列明文字符的位置来实现加密。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

变位密码是一种简单的对称加密方法,
加密原理:

   (1)确定密钥(加密、解密使用同一密钥)。
   (2)对密钥中的字符进行排序。
   (3)将明文放到一个行宽为strlen(密钥)的矩阵中,补足则用a、b、c、d...补足生成明文矩阵。
   (4)根据密钥中字符的次序(Ascii码)依次以列的形式将明文矩阵的内容读到一数组中,生成密文。

解密原理:

   (1)确定密钥(加密、解密使用同一密钥)。
   (2)对密钥中的字符进行排序。
   (3)将密文存放到一个列长为strlen(密钥)的矩阵中,生成密文矩阵。
   (4)根据密钥中字符的次序(Ascii码)依次以行的形式将密文矩阵的内容读到一个数组中,生成解密后的明文。

 

运行结果:

代码:

// TranspositionCipher.cpp : 定义控制台应用程序的入口点。
//

#include 
"stdafx.h"
#include 
<stdio.h>
#include 
<string.h>

//密钥长度
int keyLength;
//密钥
char* key = "Hello World";
//明文用'|'来代表结束符
char* Plaintext = "Hello, my name is lauvenman|";
//在矩阵不能排满时用temptext补足
char* temptext = "abcdefghijklmn";

int main()
{
     
//初始化密钥长度
     keyLength = strlen(key);
     
//定义密钥中字母的排列顺序的数组rank
     int* rank = new int[keyLength];
     
//flag用于在对密钥的字母进行排序时判断该字母是否已经被确定位置
     int* flag = new int[keyLength];

     
for(int i = 0 ; i < keyLength; i++)
         flag[i] 
= 0;
         
    
//将key中的字母进行排序
     for(int i = 0 ; i < keyLength; i++)
        {
            
int temp_rank_flag1;
            
int rank_flag;
            
char min_char;
            
            
for(int k = 0 ; k < keyLength ; k++)
                {
                    
//找一个还没被确定位置的字母
                    if(flag[k] == 0)
                        {
                            min_char 
= key[k];
                            rank_flag 
= k;
                            temp_rank_flag1 
= k;
                            
break;
                        }
                }
                
            
for(int j = 0 ; j < keyLength; j++)
                {
                     
//如果找到一个比现在的min_char小,并且它还没被选中过的密钥中的字母时
                     if(min_char > key[j] && flag[j] == 0)
                        {
                              
//重新赋值min_char更小的字母
                              min_char = key[j];
                              
//记录此时最小字母的下标
                              rank_flag = j;
                              temp_rank_flag1 
= j;
                        }
                }
           
           
//得到其在密钥中字母排序后的位置
           rank[rank_flag] = i+1;
           
//将其flag设成1
           flag[temp_rank_flag1] = 1;
        }
      
        
//声明矩阵的空间
        int col = keyLength;
        
int row = strlen(Plaintext) / keyLength;
        
if(strlen(Plaintext) % keyLength != 0)
            row
++;
        
        
//定义用于存放明文的矩阵temp_string(动态生成),长=row, 宽=col
        char** temp_string = new char*[row];
        
for(int i=0;i<row;i++)
            temp_string[i] 
= new char[col];
        
        
//定义密文
        char* Ciphertext = new char[row*col];

        
//将明文信息转换到矩阵当中
        int temptext_flag = 0;
        
for(int i = 0; i < row; i++)
            {
                
for(int j = 0; j < col; j++)
                    {
                        
if( i*keyLength+< (strlen(Plaintext)) )
                            temp_string[i][j] 
= Plaintext[i*(keyLength)+j];
                        
else
                            {
                                 temp_string[i][j] 
= temptext[temptext_flag];
                                 temptext_flag
++;
                            }
                    }
            }


       printf(
" 明文是长度: %d",strlen(Plaintext)-1);
       printf(
" 明文是: ");
       
for(int i = 0 ; i < strlen(Plaintext) ; i++)
            {
                 printf(
"%c",Plaintext[i]);
            }

       printf(
" 密钥是: ");
       
for(int i = 0; i < keyLength; i++)
           {
               printf(
"%c",key[i]);
           }
           
       printf(
" 密钥排序 ");
       
for(int i = 0 ; i < keyLength ; i++)
            printf(
"%c ",key[i]);
            printf(
" ");
       
for(int i = 0 ; i < keyLength ; i++)
            printf(
"%d ",rank[i]);
       printf(
" ");

       printf(
" 明文矩阵(row = %d , col = %d) ",row,col);
       
for(int i = 0; i < row; i++)
           {
                
for(int j = 0; j < col; j++)
                     {
                         printf(
"%c ",temp_string[i][j]);
                     }
                 printf(
" ");
           }

       
/*加密*/
       printf(
" 密文是:  ");
       
int full = 0;
       
for(int i = 0 ; i < keyLength ; i++)
            {
                 
for(int j = 0 ; j < keyLength ; j ++)
                    {    
                        
//按密钥字母排序的顺序将明文矩阵转换成密文
                        if(rank[j] == i+1)
                            {
                                
for(int k = 0 ; k < row; k++)
                                    {
                                        Ciphertext[full] 
= temp_string[k][j];
                                        printf(
"%c",Ciphertext[full]);
                                        full
++;
                                    }
                            }
                    }
            }
        printf(
" ");

        printf(
" 密文矩阵(row = %d , col = %d) ",col,row);
        
for(int j = 0; j < row*col; j++)
            {
                printf(
"%c ",Ciphertext[j]);
                
if(j%row == row-1  )
                    printf(
" ");
            }

        
        
//定义解密后的明文(动态生成),长度是row*col
        char** dec = new char*[row];
        
for(int i = 0 ; i < row ; i ++)
            dec[i] 
= new char[col];
        
        
/*解密*/
        
//此处由于只是用于演示所以就没有重新对密钥进行排序
        
//直接使用上面的排序结果
        for(int i = 0 ; i < keyLength ; i++)
            {
                
//将密文以行的形式放到解密后明文的行中
                for(int j = 0 ; j < row ; j++)
                    {
                        dec[j][i] 
= Ciphertext[(rank[i]-1* row + j];
                    }
            }
        

        printf(
" 解密后的明文 ");
        
for(int i = 0 ; i < row ; i++)
            {
                
for(int j = 0 ; j < col ; j++)
                    {
                       
if(dec[i][j] == '|')
                           
goto endPrint;
                       printf(
"%c",dec[i][j]) ;

                    }
            }
        endPrint:
            printf(
" ");

    getchar();
   
return 0;
}

### 使用矩阵变位加密方法对明文进行加密 对于给定的明文 "OneWorldOneDream" ,可以采用矩阵变位加密的方法来生成密文。此方法涉及创建一个基于特定密钥或规则的矩阵,并通过该矩阵重新排列输入的信息。 #### 创建矩阵结构 假设使用简单的矩形网格作为变换的基础,其中行数由指定的密钥决定。为了简化说明,假设定下述例子中使用的密钥长度决定了矩阵的列数而非行数。如果密钥为字符串形式,则可以根据字母表的位置或其他预定义方案将其转换成数值表示法[^1]。 #### 准备阶段 首先计算所需的空间大小以容纳整个消息。由于目标短语包含14个字符(包括大写字母),可以选择构建具有适当宽度和高度组合的表格以便填充所有这些符号而不留空白位置。考虑到本案例中的特殊需求,选取能被14整除的小于等于其平方根的最大正整数作为边长可能是合理的做法;然而,在实际应用时通常会根据具体情况调整尺寸。 在此基础上建立了一个4×4的方阵(因为\( \sqrt{14}≈3.74\) 并向上取最接近的偶数)。但是请注意,当原始文本无法完美填满所选框架时,可能需要补充额外的占位符(如Xs)直到完全占据每一格为止: | O | n | e | W | |---|---|---|---| | o | r | l | d | | O | n | e | D | | r | e | a | m | #### 应用置换函数f 接下来执行具体的重排操作。这一步骤依赖于事先确定好的映射关系——即所谓的“置换函数”。在这个实例里,简单起见,选择按照行优先级顺序读取出新的序列,而不是遵循任何复杂的模式。因此,最终得到的结果将是沿着水平方向连续提取各元素形成的一维数组。 于是乎,“OneWorldOneDream”的编码版本变成了:“OnewOrldOnedream”。 显然上述方式并没有真正意义上打乱原有次序,所以更常见的情形是利用某种随机化机制或是依据其他参数指导下的非线性路径遍历整个二维空间内的单元格内容。例如,可以通过逆向书写、蛇形路线等方式增加混淆度。 #### 实际示例展示 现在考虑一种稍微复杂一点的情况:先将原句分割成固定长度的部分再交错放置到多行之中,之后沿垂直轴逐列收集字符构成输出串。设每组含三个成员,则可得如下布局及其对应的转化成果: | O | n | e | |---|---|---| | W | o | r | | l | d | O | | n | e | D | | r | e | a | | m | X | X | 注意最后两处空缺已被人为填补上虚拟标记以防越界错误发生。据此产生的秘密讯息应为:"WlneoreoDmnaerXX"。 ```python def matrix_transposition_cipher(plaintext, cols=3): padded_text = plaintext.ljust((len(plaintext) + (cols - 1)) // cols * cols, 'X') rows = len(padded_text) // cols cipher_matrix = [[''] * cols for _ in range(rows)] index = 0 for i in range(rows): for j in range(cols): cipher_matrix[i][j] = padded_text[index] index += 1 ciphertext = ''.join([cipher_matrix[row][col] for col in range(cols) for row in range(rows)]) return ciphertext print(matrix_transposition_cipher('OneWorldOneDream')) ```
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值