4 多表代替密码之Hill 密码_1 矩阵工具类
在说明Hill加密之前要先复习线性代数的知识,主要是关于矩阵的一些运算和概念。
一、矩阵的逆:
定义方阵M的逆矩阵应该满足M*M^-1==I,其中I是单位矩阵,比如:
但是这个地方是对英文字母进行加密,所以矩阵中的数字都是模26的值,比如:
* =
这个地方结果就应该mod26, 最后结果就是:
那么上面两个相乘的矩阵就互为逆矩阵。
这个地方要多说一下密码学中的mod运算,数学中-5%26结果肯定是-5,但是这个地方我们取值只能在0-25之间,所以-5%26的结果应该是21。
求解一个方阵的逆矩阵的公式是: (det A)-1*(-1)i+j(Dji),其中:
1.det A 是矩阵A 的行列式,当然最后结果也要是mod26,(det A)-1的意思是取矩阵A的行列式的逆,比如:
的行列式是5*3-8*17=-121mod26=9
那么(det A)-1 = 3,因为3*8mod26=1,符合矩阵逆的定义。
2.Dji 是将A去掉第j行和dii行的子行列式的值,比如:
是个2*2的方阵,那么i和j就有4种组合:0,0:0,1:1,0:1,1, 那么分别去掉对应的列和行后,就成了4个1*1的方阵,再分别计算这四个方阵的行列式,结果就是:
Dji =
3. (-1)i+j
这个与Dji相乘的结果就是:
mod26 =
最后得到A的逆矩阵为:
mod26=
二、Java中关于矩阵计算的工具包
其中最常用的就是jama了, http://math.nist.gov/javanumerics/jama/
但是要用到我们这个对应26个英文字母的加密算法中还需要进行改造,‘主要是以下几点:
1. jama是针对double类型的,要切换到int或者short
2. jama结果不会取模, 比如手动实现取模
三、我的实现
还是直接来个工具类吧,使用jama:
package com.owner.util.matrix; import Jama.Matrix; import java.text.NumberFormat; /**
* Created by wellmax on 2015/10/8.
*/
public class MatrixUtil {
private Matrix matrix; public MatrixUtil(Matrix matrix) {
this.matrix = matrix;
} public MatrixUtil() {
} public int dimension() {
return this.getMatrix().getArray().length;
} private int mod(int number) {
int mod = number % 26;
return mod < 0 ? mod + 26 : mod;//+26 避免取模结果为负
} private int convertDouble2Int(Double d) {
return d.intValue();
} /**
* 计算构成Dji 矩阵的子矩阵矩阵
*/
private Matrix excludeRowAndColumn(int row, int column) {
double[][] subArr = new double[dimension() - 1][dimension() - 1];
double[][] arr = this.getMatrix().getArray();
int rowFlag = 0;
int columnFlag = 0;
for (int i = 0; i < arr.length; i++) {
if (i == row) {
continue;
}
for (int j = 0; j < arr.length; j++) {
if (j == column) {
continue;
}
subArr[rowFlag][columnFlag] = arr[i][j];
columnFlag++;
}
rowFlag++;
columnFlag = 0;
}
return new Matrix(subArr);
} /**
* 计算行列式
*/
public int determinant(Matrix matrix) {
double doubleDeterminant = matrix.det();
return this.mod(this.convertDouble2Int(doubleDeterminant));
} /**
* 计算行列式的逆,这个方法有点坑。。。
*/
public int negativeDeterminant(int determinant) {
int i = 1;
while (true) {
if ((determinant * i) % 26 == 1) {
return i;
}
if (i == Integer.MAX_VALUE >> 1) {
break;
}
i++;
}
throw new RuntimeException("Could not find the negative determinant");
} /**
* 计算D矩阵
*/
public Matrix getD() {
double[][] arr = this.getMatrix().getArray();
if (arr == null || arr.length == 0) {
return null;
}
double[][] arrD = new double[arr.length][arr.length];
for (int i = 0; i < arr.length; i++) {
for (int j = 0; j < arr[i].length; j++) {
arrD[i][j] = this.determinant(this.excludeRowAndColumn(j, i));
}
}
return new Matrix(arrD);
} /**
* 计算(-1)i+j 乘上 D矩阵
*/
public Matrix negative(Matrix matrix) {
double[][] arr = matrix.getArray();
for (int i = 0; i < arr.length; i++) {
for (int j = 0; j < arr.length; j++) {
if ((i + j) % 2 == 1) {
arr[i][j] = mod(-1 * new Double(arr[i][j]).intValue());
}
}
}
return new Matrix(arr);
} /**
* 最后一个求矩阵的逆矩阵
*/
public Matrix inverse() {
int negativeDeterminant = negativeDeterminant(determinant(this.getMatrix()));
Matrix D = this.negative(this.getD());
double[][] arr = D.getArray();
double[][] inverseArr = new double[arr.length][arr.length];
for (int i = 0; i < arr.length; i++) {
for (int j = 0; j < arr.length; j++) {
inverseArr[i][j] = mod(new Double(arr[i][j]).intValue() * negativeDeterminant);
}
}
return new Matrix(inverseArr);
} private int rowMultiplyEqualLengthMatrix(int[] row, double[] matrix) {
double result = 0;
for (int i = 0; i < row.length; i++) {
result += row[i] * matrix[i];
}
return this.mod(this.convertDouble2Int(result));
} public int[] rowMultiplyMatrix(int[] row, Matrix matrix) {
int length = row.length;
int matrixDimension = matrix.getColumnDimension();
int mod = length % matrixDimension;
int cycleTime = length / matrixDimension;
int[] result = new int[length];
double[] matrixArr = matrix.getColumnPackedCopy();
int element = 0;
double[] cycleMatrixArr = new double[matrixDimension];
int[] cycleRowArr = new int[matrixDimension];
for (int i = 0; i < cycleTime; i++) {
System.arraycopy(row, i * matrixDimension, cycleRowArr, 0, matrixDimension);
for (int j = 0; j < matrixDimension; j++) {
System.arraycopy(matrixArr, j * matrixDimension, cycleMatrixArr, 0, matrixDimension);
element = this.rowMultiplyEqualLengthMatrix(cycleRowArr, cycleMatrixArr);
result[i * matrixDimension + j] = element;
}
}
if (mod != 0) {
for(int i = 0 ; i < matrixDimension ; i ++){
cycleMatrixArr[i] = 0;
}
System.arraycopy(row, cycleTime * matrixDimension, cycleRowArr, 0, length - cycleTime * matrixDimension);
for (int j = 0; j < length - cycleTime * matrixDimension; j++) {
System.arraycopy(matrixArr, j * matrixDimension, cycleMatrixArr, 0, matrixDimension);
element = this.rowMultiplyEqualLengthMatrix(cycleRowArr, cycleMatrixArr);
result[cycleTime * matrixDimension + j] = element;
} }
return result;
} public Matrix getMatrix() {
return matrix;
} public void setMatrix(Matrix matrix) {
this.matrix = matrix;
} public static void main(String[] args) {
double[][] arr = new double[][]{{5, 8}, {17, 3}};
Matrix m = new Matrix(arr, 2, 2);
MatrixUtil util = new MatrixUtil(new Matrix(arr));
// System.out.println(util.determinant());
Matrix D = util.getD();
// m.print(NumberFormat.getInstance(),3);
// util.negative(D).print(NumberFormat.getInstance(), 3);
util.inverse().print(NumberFormat.getInstance(), 3);
int[] row = new int[]{1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11};
int[] result = util.rowMultiplyMatrix(row, m);
for (int i : result) {
System.out.println(i);
} // double[][] det = new double[][]{{9}};
// Matrix detMatrix = new Matrix(det);
// detMatrix.inverse().print(NumberFormat.getInstance(),3);
}
}
-wellmaxwang
4 多表代替密码之Hill 密码_1 矩阵工具类的更多相关文章
- 4 多表代替密码之Hill 密码 2实现
该解密方法的KEY 不是一个数或者一段字符串,而是一个矩阵, 比如有个3*3的KEY: 那么如果我们要加密一个长度为N的字符串, 那么把N除以3,分成M个3个字母组成的小段, 对每个小段尽心加密: 1 ...
- javascript实现playfair和hill密码算法
时至期末,补习信息安全概论作业.恰巧遇古典密码学算法中的playfair算法和hill算法,用javascript语言实现起来是在有趣,边查百度边编码,顺便好好补习一下javascript基础. pl ...
- Hill密码解密过程(Java)
Hill密码是一种传统的密码体系.加密原理:选择一个二阶可逆整数矩阵A称为密码的加密矩阵,也就是这个加密体系的密钥.加密过程: 明文字母依次逐对分组,例如加密矩阵为二阶矩阵,明文就两个字母一组,如果最 ...
- 信息安全-2:python之hill密码算法[原创]
转发注明出处:http://www.cnblogs.com/0zcl/p/6106513.html 前言: hill密码算法我打算简要介绍就好,加密矩阵我用教材上的3*3矩阵,只做了加密,解密没有做, ...
- Hill密码
希尔密码(Hill Password)是运用基本矩阵论原理的替换密码,由Lester S. Hill在1929年发明.每个字母当作26进制数字:A=, B=, C=... 一串字母当成n维向量,跟一个 ...
- Oracle创建表空间、用户名、密码步骤教程
第一步,以最高级别 SYSDBA 身份登录数据库 cmd 进入命令行 登录方式一: C:\Documents and Settings\Administrator>sqlplus sys/sys ...
- ubuntu系统下mysql重置密码和修改密码操作
一.忘记密码后想重置密码 在介绍修改密码之前,先介绍一个文件/etc/mysql/debian.cnf.其主要内容如下图: 里面有一个debian-sys-maint用户,这个用户只有Debian或U ...
- ssm中通过ajax或jquer的validate验证原密码与修改密码的正确性
一.ajax 1. <script type="text/javascript"> //验证原密码1.ajax,正则 var ok1=false,ok2=false,o ...
- C#--用户密码处理------混淆密码加密
近期刚好做新框架的用户数据安全这块 密码的保护措施:混淆加密--------------------------------拙见----------贴上代码--请指教 1:生成混淆数据,---存入数据 ...
随机推荐
- 网页边框样式与style样式部分总结
1).border边框样式:border-style:solid 边框样式值如下: none : 无边框.与任何指定的border-width值无关 hidden : 隐藏边框.IE不支持 dotte ...
- openxml(二) 添加页眉,页脚
openxml 中 word 文档的结构是如下图: 其中,页眉是 header,属于headerpart 部件,页脚是footer,属于footerpart 部件,图上还有其他的东西,之后会一一介绍. ...
- iPhone5停留在语音的界面,提示按三次home键,无法继续下去
不知道之前用户是怎么操作的,可能是刷机或恢复出厂设置.穷人,没用玩过iPhone. 根据提示关键词,网上搜索,发现只需要按三次home,三次锁屏,三次锁屏,最后再三次home就可以了. 试了两次,还真 ...
- div跟随页面滚动
$(document).ready(function(){ var timer; $(window).scroll(function (){ clearInterval(timer); var top ...
- 20169212《Linux内核原理与分析》 第十周作业
云课堂回顾学习 1. 进程调度的时机 中断处理过程(包括时钟中断.I/O中断.系统调用和异常)中,直接调用schedule(),或者返回用户态时根据need_resched标记调用schedule() ...
- TranslateAnimation 运行动画后实际位置不正确问题
最近在调试android 动画时候发现一个很奇怪问题,网上搜索都说TranslateAnimation 动画运行后,实际位置要在动画结束的监听里面重新设置才会正确,不然物体位置还是在原位. 我根据网上 ...
- continue用法
之前,一直没搞懂continue的用法,现在知道其中一个了: continue语句用于终止本轮循环,返回循环头部,开始下一轮循环 var i = 0; while (i < 10){ i++; ...
- Android开发--Android Studio配置
1.常见问题 emulator: You might want to adjust your AVD RAM size and/or HAXM configuration to run in fast ...
- MVC5+EF6 入门完整教程十一:细说MVC中仓储模式的应用
摘要: 第一阶段1~10篇已经覆盖了MVC开发必要的基本知识. 第二阶段11-20篇将会侧重于专题的讲解,一篇文章解决一个实际问题. 根据园友的反馈, 本篇文章将会先对呼声最高的仓储模式进行讲解. 文 ...
- Mongodb 副本集分片(二)---mongodb副本集部署脚本详解
分享下,最近做的一主一从一仲裁的示例,如有需要,大家可以扩展成一主两从一仲裁. 大家可以看到 我的集群名字沿用了默认的neunnm,如果是其他的话 大家注意修改. 需要辅助文件hosts.con ...