看看jdk怎么说
This MessageDigest class provides applications the functionality of a
message digest algorithm, such as SHA-1 or SHA-256.
Message digests are secure one-way hash functions that take arbitrary-sized
data and output a fixed-length hash value.
实话实说,我的英语要是再好点,我就能很少用去看别人写的博客了,因为这段注释已经写的很清楚了,所以,这个英文的注释要常看,希望有一天能很顺畅的都这些注释。
这个类提供了一些消息摘要算法,例如SHA-1,SHA-256.它是一个安全的单向哈希函数,能把不定长度的
数据转化成固定长度的hash值
用法
通过查看注释可以比较清晰的理解该类的核心方法
- update(byte) 通过这个函数来处理数据
- reset() 通过这个函数来重置
- digest 在经过可能多次update后,一定最后要调用这个函数来结束整个运算过程
下面是jdk中给的使用范例
MessageDigest md = MessageDigest.getInstance("SHA-256");
try {
md.update(toChapter1);
MessageDigest tc1 = md.clone();
byte[] toChapter1Digest = tc1.digest();
md.update(toChapter2);
...etc.
} catch (CloneNotSupportedException cnse) {
throw new DigestException("couldn't make digest of partial content");
}
工具类封装
以下工具类来之西北野狼的博客
package com.company;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
public class MD5Tool {
private static ThreadLocal<MD5Tool> md5ToolThreadLocal = new ThreadLocal<>();
private MD5Tool() {
}
/**
* 获取一个MD5工具实例
*/
public static MD5Tool getInstance() {
if (md5ToolThreadLocal.get() == null) {
md5ToolThreadLocal.set(new MD5Tool());
}
return md5ToolThreadLocal.get();
}
/**
* 通过md5进行加密
*
* @param source 要加密的数据
* @return
* @throws NoSuchAlgorithmException
*/
public String getMd5(String source) throws NoSuchAlgorithmException {
//1.获取MessageDigest对象
MessageDigest digest = MessageDigest.getInstance("md5");
//2.执行加密操作
byte[] bytes = source.getBytes();
//在MD5算法这,得到的目标字节数组的特点:长度固定为16
byte[] targetBytes = digest.digest(bytes);
//3.声明字符数组
char[] characters = new char[]{'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};
//4.遍历targetBytes
StringBuilder builder = new StringBuilder();
for (byte b : targetBytes) {
//5.取出b的高四位的值
//先把高四位通过右移操作拽到低四位
int high = (b >> 4) & 15;
//6.取出b的低四位的值
int low = b & 15;
//7.以high为下标从characters中取出对应的十六进制字符
char highChar = characters[high];
//8.以low为下标从characters中取出对应的十六进制字符
char lowChar = characters[low];
builder.append(highChar).append(lowChar);
}
return builder.toString();
}
}
以上代码有两点比较有意思
- 用ThreadLocal来封装实例,避免了线程安全问题
- 对函数运算结果的一个byte数组,通过取高四位和低四位映射字符,生成一字符串