只加密不解密的哈希算法(超详细版)

一、哈希算法的简述

  • 概念

哈希算法(Hash Algorithm)是一种将任意长度的消息压缩到一个固定长度的摘要(digest)的函数。

  • 主要应用

 哈希算法的最主要的应用是对于一段数据,通过一定的算法,生成一个固定长度的哈希值,这个哈希值通常用于数据校验、数据完整性验证等领域。

  • 常见算法

  1. MD5---Message Digest Algorithm 5
  2. SHA-1---Secure Hash Algorithm 1
  3. SHA-256---Secure Hash Algorithm 256
  4. SHA-512---Secure Hash Algorithm 512
  5. RipeMD160
  •  特点

  1.  相同的输入一定会得到相同的输出
  2.  不同的输入大概率得到不同的输出。
  3.  给定的哈希值无法反向推出原始输入内容

 二、哈希碰撞

  • 概念

不同的输入得到了相同的输出称为哈希碰撞。这种情况是避免不了的,因为输出的哈希数据长度是固定的(最多只有4294967296种输出)但是输入的数据长度确实不固定的,有无数种输入。

  • 安全的哈希算法需要满足

  1. 抗碰撞性:相同的输入应该得到相同的输出,不同的输入应该尽可能得到不同的输出,即使输入之间只有微小的差异
  2. 无法逆推性:不应该能够通过哈希输出结果推导出输入。
  3. 抗修改性:输入的任何改动都应该导致输出的改动,且无法通过修改输出来推导出修改后的输入。

三、哈希算法的常见算法代码实现 

  • MD5---Message Digest Algorithm 5

  1. 中文加密
    //创建基于MD5的消息摘要对象
    MessageDigest md5 = MessageDigest.getInstance("MD5");
    //更新原始数据
    md5.update("何事西风悲画扇".getBytes());
    //获得加密数据
    byte[] digestBytes = md5.digest();
    System.out.println("加密后的结果:"+Arrays.toString(digestBytes));
    System.out.println("加密后的结果(16进制):"+Hashtools.BytestoHex(digestBytes));
    System.out.println("加密结果长度:"+digestBytes.length);
    		
    //1、何事西
    //2、风悲画扇
    //分两次更新数据只要顺序相同获得的加密结果也是一样的
    
  2.  图片加密 
//获取图片信息
byte[] bs = Files.readAllBytes(Paths.get("D:\\3yue\\vv.jpg"));
//创建基于MD5的基本摘要信息
MessageDigest digest = MessageDigest.getInstance("MD5");
//更新数据
digest.update(bs);
//获得加密数组结果并输出
byte[] digestBytes = digest.digest();
System.out.println("加密后的结果:"+Arrays.toString(digestBytes));
//此处为一个Hashtools类写有BytestoHex
//是一个将数据转换为16进制的方法
System.out.println("加密后的结果(16进制):"+Hashtools.BytestoHex(digestBytes));
System.out.println("加密结果长度:"+digestBytes.length);
  •  SHA---Secure Hash Algorithm

  1. SHA-1---Secure Hash Algorithm 1
  2. SHA-256---Secure Hash Algorithm 256
  3. SHA-512---Secure Hash Algorithm 512

因为这些常见算法的实现操作都基本大差不差,为了方便我们进行快速操作, 所以创建了一个Hashtools类,详细代码如下:

//创建私有类方便操作避免代码冗余
private static MessageDigest digest;
//无参构造方法
private Hashtools() {}
//通过消息摘要对象,处理加密内容
private static String hanler(String source) {
		digest.update(source.getBytes());
		byte[] bytes = digest.digest();
		String hash = BytestoHex(bytes);
		return hash;
	}
//字节数组转换16进制字符串
public static String BytestoHex(byte[] b) {
		StringBuilder builder = new StringBuilder();
		for (byte c : b) {
			//将字节值转换为2位十六进制字符串
			builder.append(String.format("%02x", c));
		}
		return builder.toString();
	}
	
//按照sha-1加密
public static String DigestBySha1(String source) throws NoSuchAlgorithmException {
		digest = MessageDigest.getInstance("sha-1");
		return hanler(source);
	}
//按照sha-256加密
public static String DigestBySha256(String source) throws NoSuchAlgorithmException {
		digest = MessageDigest.getInstance("sha-256");
		return hanler(source);
	}
//按照sha-512加密
public static String DigestBySha512(String source) throws NoSuchAlgorithmException {
		digest = MessageDigest.getInstance("sha-512");
		return hanler(source);
	}
	
//按照md5加密
public static String DigestByMd5(String source) throws NoSuchAlgorithmException {
    	digest = MessageDigest.getInstance("md5");
		return hanler(source);
		
	}

有了这个Hashtools事半功倍,算法实现代码就变得简洁明了。算法输出结果如下:

String str = "edefrev";
String md5 = Hashtools.DigestByMd5(str);
String sha-1 = Hashtools.DigestBySha1(str);
String sha-256 = Hashtools.DigestBySha256(str);
String sha-512 = Hashtools.DigestBySha512(str);
		
System.out.println("md5="+md5);
System.out.println("sha-1="+sha-1);
System.out.println("sha-256="+sha-256);
System.out.println("sha-512="+sha5-12);
  •  RipeMD160算法

      Java标准库提供了一系列常用的哈希算法,但是没有RipeMD160算法,所以为了实现它我们需要找到一个现成的第三方库bouncycastle去使用这个方法。在使用前我们需要去官方网站bouncycastle.org下载我们要使用jar包,然后Build Path>>>add....。

      Java标准库的java.security包提供了一种标准机制,允许第三方提供商无缝接入。我们要使用BouncyCastle提供的RipeMD160算法,需要先把BouncyCastle注册一下:

//注册BouncyCastle BouncyCastleProvider通知类
//将提供的消息摘要算法注册至Security
Security.addProvider(new BouncyCastleProvider());

 然后就可以实现算法啦~

//获取RipeMd160算法的信息摘要对象
MessageDigest digest = MessageDigest.getInstance("ripemd160");
//更新数据
digest.update("dddd".getBytes());
//获取信息加密
byte[] result = digest.digest();
//信息摘要字节长度玉内容
System.out.println("加密结果字节长度"+result.length);
System.out.println("加密结果字节内容"+Arrays.toString(result));
//16进制内容字符串
String hex = new BigInteger(1,result).toString(16);
System.out.println("加密结果字符串长度"+hex.length());
System.out.println("加密结果字符串内容"+hex);

 四、小总结

哈希算法具有以下优点:

  1. 不可逆:无法从摘要中推算出原始数据。

  2. 唯一性:不同的输入会得到不同的摘要。

  3. 敏感性:原始数据的微小变化也会导致摘要的大幅变化。

  4. 固定长度:输出的摘要长度是固定的。

哈希算法也有以下缺点:

  1. 取决于输入长度:输入长度不同,输出长度也不同。

  2. 可能存在碰撞:不同的输入可能会产生相同的摘要。

  3. 不能解密:无法通过摘要找到原始数据。

  • 3
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

猿究院懒羊羊

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值