MD5加密算法
MD5算法这一内容还是我从软件工程实习中了解到的一个算法,它可以用来加密用户数据比如密码,用户注册时将用户输入的明文密码通过MD5加密后转换成密文保存到数据库中,这样即使别人拿到了用户数据也找不出密码是什么,用户在登陆时输入明文密码通过MD5加密后与数据库中的密文对照相同就说明密码正确,否则密码错误。这点作用充分体现在了我实习访问数据库信息的过程中,密码一栏出现了乱码的现象,琢磨了一周也不知道如何解决,直到去询问学长之后,才发现是MD5加密算法的原因,在源码中调用这一算法,导致我无法正常访问数据库,而且那并不是乱码的现象,而是在Web页面输入密码后,经过加密解析,呈现在数据库中的是一串你看不懂的数字,这个时候就错误的以为它乱码了,然后便去网站上搜索解决数据库乱码问题,害,明显没有找到根源的地方。
经过我的上述实习导入,接下来我将介绍什么是MD5加密算法:
MD5消息摘要算法(MD5 Message-Digest Algorithm),是一种被广泛使用的密码散列函数,可以产生出一个128位(16字节)的散列值(hash value),用于确保信息传输完整一致。
算法原理:
第一步:处理原文
首先,我们计算出原文长度(bit)对512求余的结果,如果不等于448,就需要填充原文使得原文对512求余的结果等于448。填充的方法是第一位填充1,其余位填充0。填充完后,信息的长度就是512*N+448。
之后,用剩余的位置(512-448=64位)记录原文的真正长度,把长度的二进制值补在最后。这样处理后的信息长度就是512*(N+1)。
第二步:设置初始值
MD5的哈希结果长度为128位,按每32位分成一组共4组。这4组结果是由4个初始值A、B、C、D经过不断演变得到。MD5的官方实现中,A、B、C、D的初始值如下(16进制):
A=0x01234567
B=0x89ABCDEF
C=0xFEDCBA98
D=0x76543210
第三步:循环加工
这一步是最复杂的一步,我们看看下面这张图,此图代表了单次A,B,C,D值演变的流程。
图中,A,B,C,D就是哈希值的四个分组。每一次循环都会让旧的ABCD产生新的ABCD。一共进行多少次循环呢?由处理后的原文长度决定。
假设处理后的原文长度是M
主循环次数 = M / 512
每个主循环中包含 512 / 32 * 4 = 64 次 子循环。
上面这张图所表达的就是单次子循环的流程。
下面是Java中生成的MD5值的代码:
public class MD5Test {
//main测试类
public static void main(String[] args) {
String result = getMD5("aaa");
System.err.println(result);
}
/**
* 生成md5
* @param message
* @return
*/
public static String getMD5(String message) {
String md5str = "";
try{
//1 创建一个提供信息摘要算法的对象,初始化为md5算法对象
MessageDigest md = MessageDigest.getInstance("MD5");
//2 将消息变成byte数组
byte[] input = message.getBytes();
//3 计算后获得字节数组,这就是那128位了
byte[] buff = md.digest(input);
//4 把数组每一字节(一个字节占八位)换成16进制连成md5字符串
md5str = bytesToHex(buff);
} catch(Exception e) {
e.printStackTrace();
}
return md5str;
}
/**
* 二进制转十六进制
* @param bytes
* @return
*/
public static String bytesToHex(byte[] bytes) {
StringBuffer md5str = new StringBuffer();
//把数组每一字节换成16进制连成md5字符串
int digital;
for(int i = 0; i < bytes.length; i++) {
digital = bytes[i];
if(digital < 0) {
digital += 256;
}
if(digital < 16){
md5str.append("0");
}
md5str.append(Integer.toHexString(digital));
}
return md5str.toString().toUpperCase();
}
}