• Java base64加密解密


    参考:

    https://www.cnblogs.com/luguo3000/p/3940197.html

    https://blog.csdn.net/jiahao1186/article/details/83661862

    https://www.cnblogs.com/alter888/p/9140732.html

    从原理上搞定编码-- Base64编码

    开发者对Base64编码肯定很熟悉,是否对它有很清晰的认识就不一定了。实际上Base64已经简单到不能再简单了,如果对它的理解还是模棱两可实在不应该。大概介绍一下Base64的相关内容,花几分钟时间就可以彻底理解它。文章下边贴了一个Base64的编解码器,方便阅读文章的同时来实验。

      一. Base64编码由来

      为什么会有Base64编码呢?因为有些网络传送渠道并不支持所有的字节,例如传统的邮件只支持可见字符的传送,像ASCII码的控制字符就不能通过邮件传送。这样用途就受到了很大的限制,比如图片二进制流的每个字节不可能全部是可见字符,所以就传送不了。最好的方法就是在不改变传统协议的情况下,做一种扩展方案来支持二进制文件的传送。把不可打印的字符也能用可打印字符来表示,问题就解决了。Base64编码应运而生,Base64就是一种基于64个可打印字符来表示二进制数据的表示方法。

      二. Base64编码原理

      看一下Base64的索引表,字符选用了"A-Z、a-z、0-9、+、/" 64个可打印字符。数值代表字符的索引,这个是标准Base64协议规定的,不能更改。64个字符用6个bit位就可以全部表示,一个字节有8个bit位,剩下两个bit就浪费掉了,这样就不得不牺牲一部分空间了。这里需要弄明白的就是一个Base64字符是8个bit,但是有效部分只有右边的6个bit,左边两个永远是0。

      那么怎么用6个有效bit来表示传统字符的8个bit呢?8和6的最小公倍数是24,也就是说3个传统字节可以由4个Base64字符来表示,保证有效位数是一样的,这样就多了1/3的字节数来弥补Base64只有6个有效bit的不足。你也可以说用两个Base64字符也能表示一个传统字符,但是采用最小公倍数的方案其实是最减少浪费的。结合下边的图比较容易理解。Man是三个字符,一共24个有效bit,只好用4个Base64字符来凑齐24个有效位。红框表示的是对应的Base64,6个有效位转化成相应的索引值再对应Base64字符表,查出"Man"对应的Base64字符是"TWFU"。说到这里有个原则不知道你发现了没有,要转换成Base64的最小单位就是三个字节,对一个字符串来说每次都是三个字节三个字节的转换,对应的是Base64的四个字节。这个搞清楚了其实就差不多了。

             

      但是转换到最后你发现不够三个字节了怎么办呢?愿望终于实现了,我们可以用两个Base64来表示一个字符或用三个Base64表示两个字符,像下图的A对应的第二个Base64的二进制位只有两个,把后边的四个补0就是了。所以A对应的Base64字符就是QQ。上边已经说过了,原则是Base64字符的最小单位是四个字符一组,那这才两个字符,后边补两个"="吧。其实不用"="也不耽误解码,之所以用"=",可能是考虑到多段编码后的Base64字符串拼起来也不会引起混淆。由此可见Base64字符串只可能最后出现一个或两个"=",中间是不可能出现"="的。下图中字符"BC"的编码过程也是一样的。

      三. 总结  

      说起Base64编码可能有些奇怪,因为大多数的编码都是由字符转化成二进制的过程,而从二进制转成字符的过程称为解码。而Base64的概念就恰好反了,由二进制转到字符称为编码,由字符到二进制称为解码

      Base64编码主要用在传输、存储、表示二进制等领域,还可以用来加密,但是这种加密比较简单,只是一眼看上去不知道什么内容罢了,当然也可以对Base64的字符序列进行定制来进行加密。

      Base64编码是从二进制到字符的过程,像一些中文字符用不同的编码转为二进制时,产生的二进制是不一样的,所以最终产生的Base64字符也不一样。例如"上网"对应utf-8格式的Base64编码是"5LiK572R",对应GB2312格式的Base64编码是"yc/N+A=="。

    文章参考自 "维基百科-Base64"

     

    Java base64加密解密 两种实现方式

    1、为什么要使用Base 64

        Base 64主要用途不是加密,而是把一些二进制数转成普通字符,方便在网络上传输。 由于一些二进制字符在传输协议中属于

    控制字符,不能直接传送,所以需要转换一下才可以。由于某些系统中只能使用ASCII字符,Base64就是用来将非ASCII字符的数

    据转换成ASCII字符的一种方法,Base64特别适合在http,mime协议下快速传输数据。比如网络中图片的传输。

         Base64,并非安全领域下的加密解密算法。虽然经常遇到所谓的base64的加密解密。但base64只能算是一个编码算法,对数

    据内容进行编码来适合传输。虽然base64编码过后原文也变成不能看到的字符格式,但是方式初级又简单。

    2、Base 64 原理

            Base64编码方法,要求把每三个8Bit的字节转换为四个6Bit的字节,其中,转换之后的这四个字节中每6个有效bit为是有效

    数据,空余的那两个 bit用0补上成为一个字节。因此Base64所造成数据冗余不是很严重,Base64是当今比较流行的编码方法,

    因为它编起来速度快而且简单。


     举个例子,有三个字节的原始数据:aaaaaabb bbbbccccc ccdddddd(这里每个字母表示一个bit位)
     那么编码之后会变成:      00aaaaaa 00bbbbbb 00cccccc 00dddddd

    所以可以看出base64编码简单,虽然编码后不是明文,看不出原文,但是解码也很简单

    2、Base64加密解密的实现方式:两种

    package com.liuxd;
     
    import sun.misc.BASE64Decoder;
    import sun.misc.BASE64Encoder;
     
    import java.util.Base64;
     
    /**
     * Created by Liuxd on 2018-11-02.
     */
    public class TestString {
     
     
        public static void main(String[] args) throws Exception {
            String str = "青锋剑,偃月刀";
     
            base64(str);
     
            enAndDeCode(str);
     
        }
     
     
        /**
         * Base64
         *
         */
        public static void base64(String str) {
            byte[] bytes = str.getBytes();
     
            //Base64 加密
            String encoded = Base64.getEncoder().encodeToString(bytes);
            System.out.println("Base 64 加密后:" + encoded);
     
            //Base64 解密
            byte[] decoded = Base64.getDecoder().decode(encoded);
     
            String decodeStr = new String(decoded);
            System.out.println("Base 64 解密后:" + decodeStr);
     
            System.out.println();
     
     
        }
     
        /**
         * BASE64加密解密
         */
        public static void enAndDeCode(String str) throws Exception {
            String data = encryptBASE64(str.getBytes());
            System.out.println("sun.misc.BASE64 加密后:" + data);
     
            byte[] byteArray = decryptBASE64(data);
            System.out.println("sun.misc.BASE64 解密后:" + new String(byteArray));
        }
     
        /**
         * BASE64解密
         * @throws Exception
         */
        public static byte[] decryptBASE64(String key) throws Exception {
            return (new BASE64Decoder()).decodeBuffer(key);
        }
     
        /**
         * BASE64加密
         */
        public static String encryptBASE64(byte[] key) throws Exception {
            return (new BASE64Encoder()).encodeBuffer(key);
        }
    }

    输出结果:

    Base 64 加密后:6Z2S6ZSL5YmR77yM5YGD5pyI5YiA
    Base 64 解密后:青锋剑,偃月刀

    sun.misc.BASE64 加密后:6Z2S6ZSL5YmR77yM5YGD5pyI5YiA

    sun.misc.BASE64 解密后:青锋剑,偃月刀

    Java如何进行Base64的编码(Encode)与解码(Decode)

    Base64是一种能将任意Binary资料用64种字元组合成字串的方法,而这个Binary资料和字串资料彼此之间是可以互相转换的,十分方便。在实际应用上,Base64除了能将Binary资料可视化之外,也常用来表示字串加密过后的内容。如果要使用Java 程式语言来实作Base64的编码与解码功能,可以参考本篇文章的作法。

    早期作法

    早期在Java上做Base64的编码与解码,会使用到JDK里sun.misc套件下的BASE64Encoder和BASE64Decoder这两个类别,用法如下:

    复制代码
    final BASE64Encoder encoder = new BASE64Encoder();
    final BASE64Decoder decoder = new BASE64Decoder();
    final String text = "字串文字";
    final byte[] textByte = text.getBytes("UTF-8");
    //编码
    final String encodedText = encoder.encode(textByte);
    System.out.println(encodedText);
    //解码
    System.out.println(new String(decoder.decodeBuffer(encodedText), "UTF-8"));
    
    final BASE64Encoder encoder = new BASE64Encoder();
    final BASE64Decoder decoder = new BASE64Decoder();
    final String text = "字串文字";
    final byte[] textByte = text.getBytes("UTF-8");
    //编码
    final String encodedText = encoder.encode(textByte);
    System.out.println(encodedText);
    
    //解码
    System.out.println(new String(decoder.decodeBuffer(encodedText), "UTF-8"));
    复制代码
     

    从以上程式可以发现,在Java用Base64一点都不难,不用几行程式码就解决了!只是这个sun.mis c套件所提供的Base64功能,编码和解码的效率并不太好,而且在以后的Java版本可能就不被支援了,完全不建议使用。

    Apache Commons Codec作法

    Apache Commons Codec有提供Base64的编码与解码功能,会使用到org.apache.commons.codec.binary套件下的Base64类别,用法如下:

    复制代码
    final Base64 base64 = new Base64();
    final String text = "字串文字";
    final byte[] textByte = text.getBytes("UTF-8");
    //编码
    final String encodedText = base64.encodeToString(textByte);
    System.out.println(encodedText);
    //解码
    System.out.println(new String(base64.decode(encodedText), "UTF-8"));
    
    final Base64 base64 = new Base64();
    final String text = "字串文字";
    final byte[] textByte = text.getBytes("UTF-8");
    //编码
    final String encodedText = base64.encodeToString(textByte);
    System.out.println(encodedText);
    //解码
    System.out.println(new String(base64.decode(encodedText), "UTF-8"));
    复制代码

    以上的程式码看起来又比早期用sun.mis c套件还要更精简,效能实际执行起来也快了不少。缺点是需要引用Apache Commons Codec,很麻烦。

    Java 8之后的作法

    Java 8的java.util套件中,新增了Base64的类别,可以用来处理Base64的编码与解码,用法如下:

    复制代码
    final Base64.Decoder decoder = Base64.getDecoder();
    final Base64.Encoder encoder = Base64.getEncoder();
    final String text = "字串文字";
    final byte[] textByte = text.getBytes("UTF-8");
    //编码
    final String encodedText = encoder.encodeToString(textByte);
    System.out.println(encodedText);
    //解码
    System.out.println(new String(decoder.decode(encodedText), "UTF-8"));
    
    final Base64.Decoder decoder = Base64.getDecoder();
    final Base64.Encoder encoder = Base64.getEncoder();
    final String text = "字串文字";
    final byte[] textByte = text.getBytes("UTF-8");
    //编码
    final String encodedText = encoder.encodeToString(textByte);
    System.out.println(encodedText);
    //解码
    System.out.println(new String(decoder.decode(encodedText), "UTF-8"));
    复制代码

    与sun.mis c套件和Apache Commons Codec所提供的Base64编解码器来比较的话,Java 8提供的Base64拥有更好的效能。实际测试编码与解码速度的话,Java 8提供的Base64,要比sun.mis c套件提供的还要快至少11倍,比Apache Commons Codec提供的还要快至少3倍。因此在Java上若要使用Base64,这个Java 8底下的java .util套件所提供的Base64类别绝对是首选!

     
  • 相关阅读:
    2015-05-27 用正则把oracle时间转化到mysql时间
    linux版idea14界面美观和windows,mac基本一致
    ubuntu 下自定义快捷键,,用着舒服
    ubuntu 方便好用的截图软件
    Integer 包装器类 大小比较
    win7、ubuntu双系统,遇到分区不可用问题,和卸载ubuntu后win7开不了机
    巧妙小思想
    读取16进制文件和校验图片格式的问题。 文件名后缀
    旧电脑变废为宝!
    Win10打开Autodesk软件时提示“管理员已阻止你运行此应用”
  • 原文地址:https://www.cnblogs.com/xuwc/p/14058183.html
Copyright © 2020-2023  润新知