短链接是什么
短链接就是当我们想把一个URL分享给别人的时候,由于这个URL可能很长,那么我们可以把这个URL转换为短链接
实现代码
public static String[] shortUrl(String url) throws NoSuchAlgorithmException {
// 可以自定义生成 MD5 加密字符传前的混合 KEY
String key = "abcde";
// 要使用生成 URL 的字符
String[] chars = new String[]{"a", "b", "c", "d", "e", "f", "g", "h",
"i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t",
"u", "v", "w", "x", "y", "z", "0", "1", "2", "3", "4", "5",
"6", "7", "8", "9", "A", "B", "C", "D", "E", "F", "G", "H",
"I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T",
"U", "V", "W", "X", "Y", "Z"
};
// 对传入网址进行 MD5 加密
MessageDigest md5 = MessageDigest.getInstance("MD5");
String sMD5EncryptResult = DatatypeConverter.printHexBinary(md5.digest((key + url).getBytes()));
String hex = sMD5EncryptResult;
String[] resUrl = new String[4];
for (int i = 0; i < 4; i++) {
// 把加密字符按照 8 位一组 16 进制与 0x3FFFFFFF 进行位与运算
String sTempSubString = hex.substring(i * 8, i * 8 + 8);
// 这里需要使用 long 型来转换,因为 Inteper .parseInt() 只能处理 31 位 , 首位为符号位 , 如果不用 long ,则会越界
long lHexLong = 0x3FFFFFFF & Long.parseLong(sTempSubString, 16);
String outChars = "";
for (int j = 0; j < 6; j++) {
// 把得到的值与 0x0000003D 进行位与运算,取得字符数组 chars 索引
long index = 0x0000003D & lHexLong;
// 把取得的字符相加
outChars += chars[(int) index];
// 每次循环按位右移 5 位
lHexLong = lHexLong >> 5;
}
// 把字符串存入对应索引的输出数组
resUrl[i] = outChars;
}
return resUrl;
}
原理讲解
我们的长链接经过短链接算法之后会生成四个只由大小写英文字母和数字组成的长度为6的4个短链接,他们只由62中字母组成,我们只需要取其中一段用就行
- 我们先需要准备一个长度为62的字母数组,里面存放着大小写英文字母和0~9数字
- 将原网址进行md5加密,生成32位签名串 ,然后我们把这32位分成四段 , 每段8个字节即这个算法最后会生成四个短链接,我们对每一段循环处理,但是我们只需要随机取一段使用就可以了
- 那么每一段八个字节,我们利用与运算取出低位的30位 , 我们把这三十位与61进行与操作与出来的结果就对应着数组的坐标,然后数组的坐标最大也是刚好61位,这样就可以找到一位字符了,然后右移五位,上面的操作刚好30位能重复六次,就得到了六个字符了,这样就生成了一个短链接,但是短链接的最后一个字符不会超过ascii码大于4的字符,因为61要用6位表示,但是我们拿三十位每次右移5位,最后一次的和61与出来的坐标不会超过字符4的坐标