当前位置: 首页 > 工具软件 > Java Base64 > 使用案例 >

java中base64的使用

壤驷经国
2023-12-01

Base64

是一种用64个字符来表示任意二进制数据的方法,完成了数据在HTTP协议上的传输
它是一种编码方式,而非加密方式
数据编码之后,数据量会变大,变大1/3左右

base64参考:https://www.zhihu.com/question/36306744

使用场景

简单说,因为某些场合并不能传输或者储存二进制流。
比如,如果一个传输协议是基于ASCII文本的,那么它就不能传输二进制流,那你要将二进制流传输就得编码。常见的诸如 http 协议的 url 就是纯文本的,不能直接放二进制流。
特别的,大多数现代语言的 String 类型,都不能直接储存二进制流,但可以储存BASE64编码的字符串。如果你希望用 String 类型操作一切数据,那就没法直接用二进制流。
当然,另外还有一个原因,就是某些协议会对二进制流中的特定字符进行特殊处理(比如ASCII的0~32编码的字符在某些传输介质中,是会被当作特殊含义处理的),这种时候就需要通过编码来避开这些特定字符了。

为什么图片要用base64

所以一般图片小于10kb的时候,才用base64图片

  • 提升性能: 网页上的每一个图片,都是需要消耗一个 http 请求下载而来的, 图片的下载始终都要向服务器发出请求,要是图片的下载不用向服务器发出请求,base64可以随着 HTML 的下载同时下载到本地.减少https请求。
  • 加密: 让用户一眼看不出图片内容 , 只能看到编码。
  • 方便引用: 在多个文件同时使用某些图片时, 可以把图片转为base64格式的文件, 把样式放在全局中, 比如common.css, 以后在用的时候就可以直接加类名, 二不需要多层找文件路径, 会提升效率。

base64图片缺点:

(1)base64格式的文本内容较多,存储在数据库中增大了数据库服务器的压力;
(2)网页加载图片虽然不用访问服务器了,但因为base64格式的内容太多,所以加载网页的速度会降低,可能会影响用户的体验。
(3)base64无法缓存,要缓存只能缓存包含base64的文件,比如js或者css,这比直接缓存图片要差很多,而且一般HTML改动比较频繁,所以等同于得不到缓存效益。

a-z A-Z 0-9 和 + / 组成base64

编码规则

首先将待编码的内容转换成8位二进制,每3个字符为一组

如果编码前的长度是
3n+1,编码后的内容最后面补上2个 =,如果编码前的长度是3n+2,内容最后面补上1个 =。3的倍数则不用
再将每一组的二进制内容拆分成
6位的二进制,不足6位的后面补足0
每个6进制的数字前面补足
0,保证变成8位二进制
将补足后的内容根据base64编码表转换成base64内容输出

(不足四个字符的时候会用 =来补足,下面会说明)
编码前 “hb”
1.根据ascii码转换成8位二进制,3个为一组:
01101000,01100010
2.编码前长度是3n+2,所以后面补1个 ‘=’:
01101000,01100010,=
3.拆分成6位二进制,不足6位的在后面补足0,0010补足变成001000:
011010,000110,001000,=
4.每个6进制的数字前面补足0:
0011010,00000110,00000010,=
5.根据base64编码表输出:
aGI=

base64的使用

import java.nio.charset.StandardCharsets;
import java.util.Base64;

import org.springframework.util.Base64Utils;

public class Base64Test {
​
    public static void main(String[] args) {
        
        byte[] encode = Base64Utils.encode("abc".getBytes(StandardCharsets.UTF_8));
        System.out.println(new String(encode));
        
        byte[] decode = Base64Utils.decode(encode);
        System.out.println(new String(decode));
        
        // 获取编码器
        Base64.Encoder encoder = Base64.getEncoder();
        byte[] encode = encoder.encode("abc".getBytes());
        System.out.println(new String(encode));
​
        // 获取解码器
        Base64.Decoder decoder = Base64.getDecoder();
        byte[] decode = decoder.decode(encode);
        System.out.println(new String(decode));
        
        // 或者使用
        byte[] encode2 = Base64Utils.encode("abc".getBytes());
    }
}

base58

前端显示base64图片

<img src = "data:image/png;base64,base64代码">

文件流和base64文件上传区别

  • base64文件上传,base64编码的图片相对偏大,所以一般都是用来做小图的,比如头像
  • base64 就是传一个超大的字符串,可能会吃掉很大的内存
  • 访问文件流图片需要2次HTTP请求。而BASE64只需要一次,减少http请求
  • 文件流图片在任何浏览器都可以被访问到,而base64某些浏览器不支持
  • base64图片无法缓存(缓存整页另当别论)

用处

  • 文件流用来上传大图,比如一些广告图片啊,商品图片等等
  • base64图片可以用来上传用户头像,或者小的logo,或者小的图标等等
  • base64可以保存到数据库,而不需求上传,

Base58

一般用在比特币里面的一种编码方式,没有数字0,O(大写字母 O)、I(大写字母i)、l(小写字母L),+,/

编码流程
将ascii编码的字符串(256进制),转换成58进制。然后按照58进制的码表转换成相应的字符。
1、将字符串的每个字节换算成ASCII(0-255) (字符串实际上就是256进制的数字组合):
源字符串为:ABD
换算后: 65 66 68
2、将256进制的数字转换成10进制数字:
256进制数:65 66 68
转成10进制:(65 * 256 + 66) * 256 + 68 = 4276804
3、将10进制数字转换成58进制数字:
10进制数:4276804
58进制数: 21 53 20 0
4、将58进制数字的每一位按照表格转换成对应的字符:
58进制数:21 53 20 0
码表:123456789abcdefghijkmnopqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ
转换后的字符:nVm1
【注】任意进制之间的转换,先将数字转10进制再转其它进制
解码流程
按码表把字符转成58进制数字,再转256进制,按ascii把256进制数字转字符。
1、字符串每一位按码表替换成数字(58进制):
源字符: nVm1
58进制数:21 53 20 0
2、58进制转10进制:
58进制数:21 53 20 0
10进制数:4276804
3、10进制转256进制:
10进制数:4276804
256进制: 65 66 68
4、256进制转字符(按ascii转)
256进制: 65 66 68
字符:ABD
【注】任意进制之间的转换,先将数字转10进制再转其它进制

直接返回图片

具体细节可自行添加

    @GetMapping("/getPic")
    public ResponseEntity<byte[]> getPic(HttpServletResponse httpServletResponse) throws Exception {
        FileInputStream fileInputStream = new FileInputStream(new File("D:\\Picture\\Appearance 1.png"));
        final HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.IMAGE_PNG);

        return new ResponseEntity<>(IOUtils.toByteArray(fileInputStream), headers, HttpStatus.OK);

    }

浏览器输入地址,然后浏览器就会显示图片了

返回base64

具体细节可自行添加

    @GetMapping({"/captchaImage"})
    public ResponseMessage<Map<String, Object>> getCaptchaImage() throws Exception {
        HashMap retMap = new HashMap();
            String text = CaptchaHelper.generateVerifyCode(4);
            ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
            // 生成验证码图片, 具体可参考百度
            CaptchaHelper.outputImage(111, 36, outputStream, text);
            retMap.put("img", "data:image/gif;base64," + Base64.getEncoder().encodeToString(outputStream.toByteArray()));
        return ResponseMessage.success("success!", retMap);
    }

资源下载返回值封装

具体细节可自行添加

    @GetMapping("/getPic2")
    public ResponseEntity<Resource> getPic2() throws Exception {
        String contentDisposition = ContentDisposition
                .builder("attachment")
                .filename("pic.png")
                .build().toString();
        return ResponseEntity.ok()
                .header(HttpHeaders.CONTENT_DISPOSITION, contentDisposition)
                .contentType(MediaType.IMAGE_PNG)
                .body(new FileSystemResource("D:\\Picture\\Appearance 1.png"));
    }
 类似资料: