一、实验目的
-
帮助学生掌握置换密码的加密解密过程,能够利用所学过的编程语言,熟悉加密算法流程与编程实现加密算法。使学生掌握编程实现实际问题中的方法,提高专业技能和专业素养。
-
要求学生掌握算法的程序实现的方法,能应用密码算法的特点,设计合适的交互界面,并能正确实现应用编程。
-
分析算法程序的质量。
-
要求学生掌握用规范的方法书写实验报告。
二、实验仪器设备/实验环境
-
PC Windows环境
-
使用Java编程语言开发环境,或者Maple语言。或者C#开发环境开发环境。
三、实验原理
置换密码加密解密过程:
设明文为:4D 61 65 53 2D 4F 69 20 4E。密钥为8,1,6,3,5,7,4,9,2。 求加密后的16进制密文。
解: 先思考和描述算法,也就是对明文4D 61 65 53 2D 4F 69 20 4E实现置换8,1,6,3,5,7,4,9,2。通过对数组赋值实现:
m(i)={4D 61 65 53 2D 4F 69 20 4E},i=1,2,3,…,9。
k(i)={8,1,6,3,5,7,4,9,2},i=1,2,3,…,9。
c(i)=m(k(i)), i=1,2,3,…,9。
c(1),c(2),…,c(9)为密文。
所以密文序列为:20 4D 4F 65 2D 69 53 4E 61。
幻方密码加密解密过程:
…
注意:密钥通过生成的2n+1阶幻方得到
import java.io.*;
public class Experiment2 {
public static void main(String[] args) throws IOException {
//获取3阶幻方对应的置换
int[] key = getMagicTrans(createMagicSquare(3));
//读取本地txt文件中转置加密的明文,进行转置加密
File transFile = new File("C:/Users/CD4356/Desktop/transposition.txt");
transposition(transFile, key);
//读取本地txt文件幻方加密的明文,进行幻方加密
File magicFile = new File("C:/Users/CD4356/Desktop/magic_square.txt");
magicSquare(magicFile, key);
}
//置换加密
public static void transposition(File transFile, int[] key) throws IOException{
String[] plainText = readTxt(transFile);
System.out.println("\n\n置换加密的明文: ");
for (int i = 0; i < plainText.length; i++) {
System.out.print(plainText[i] + " ");
}
//将加密后的密文保存到.txt文件中,并以空格隔开
FileWriter writer = new FileWriter(new File("C:/Users/CD4356/Desktop/trans.txt"));
System.out.println("\n置换加密的密文: ");
for (int i = 0; i < key.length; i++) {
System.out.print(plainText[key[i]-1] + " ");
if(i == key.length - 1){
writer.write(plainText[key[i]-1]);
} else {
writer.write(plainText[key[i]-1] + " ");
}
}
//释放资源
writer.close();
}
//幻方加密
private static void magicSquare(File magicFile, int[] key) throws IOException{
//获取明文字符串数组
String[] plainText = readTxt(magicFile);
System.out.println("\n\n幻方加密的明文: ");
for (int i = 0; i < plainText.length; i++) {
System.out.print(plainText[i] + " ");
}
//将加密后的密文保存到.txt文件中
FileWriter writer = new FileWriter(new File("C:/Users/CD4356/Desktop/Magic.txt"));
//对明文进行加密,并保存到strArr字符数组中
String[] strArr = new String[plainText.length];
for (int i = 0; i < key.length; i++) {
strArr[key[i]-1] = plainText[i];
}
System.out.println("\n幻方加密的密文: ");
for (int i = 0; i < key.length; i++) {
System.out.print(strArr[i] + " ");
if(i == key.length - 1){ //字符间以空格隔开,末尾不能留有空格
writer.write(strArr[i]);
} else {
writer.write(strArr[i] + " ");
}
}
System.out.println("");
//释放资源
writer.close();
}
//生成奇数阶幻方,可以是3、5、7、... 、2n+1阶
public static int[][] createMagicSquare(int k){
int[][] magicArr = new int[k][k];
int x = 0;
int y = k/2;
int total = k*k;
for (int i = 1; i <= total; i++) {
magicArr[x][y] = i;
int m = (x-1+k)%k;
int n = (y+1)%k;
if (magicArr[m][n]>0) {
x = (x+1)%k;
}else{
x= m;
y= n;
}
}
System.out.println("生成的3阶幻方:");
for (int i = 0; i < magicArr.length; i++) {
for (int j = 0; j < magicArr.length; j++) {
System.out.print(magicArr[i][j] + " ");
}
System.out.println("");
}
return magicArr;
}
//幻方对应的置换
public static int[] getMagicTrans(int[][] arr){
int[] res = new int[(int) Math.pow(arr.length, 2)];
int index = 0;
for (int i = 0; i < arr.length; i++) {
for (int j = 0; j < arr.length; j++) {
res[index++] = arr[i][j];
}
}
System.out.println("\n密钥:");
for (int i = 0; i < res.length; i++) {
System.out.print(res[i] + " ");
}
return res;
}
//读取.txt文件中的明文
public static String[] readTxt(File file) throws IOException{
//通过字符流读取.txt
BufferedReader br = new BufferedReader(new FileReader(file));
//将读取到的明文以空格进行分割,并保存到字符串数组中
String[] plainText = br.readLine().split(" ");
//释放资源
br.close();
return plainText;
}
}