正确的方法使用FileReader()读取文件以从图像文件生成md5哈希字符串? [英] Proper way to read a file using FileReader() to generate an md5 hash string from image files?

查看:454
本文介绍了正确的方法使用FileReader()读取文件以从图像文件生成md5哈希字符串?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我目前正在执行此操作(请参见下面的代码段),以获取要上传的图像文件的md5哈希字符串(我将哈希用作fileNames):

I'm currently doing this (see snippet below) to get an md5 hash string for the image files I'm uploading (I'm using the hash as fileNames):

注意::我正在使用md5包来生成哈希(已将其加载到摘要中).

NOTE: I'm using the md5 package to generate the hash (it's loaded into the snippet).

FileReader()上有4种可用的方法来读取文件.它们似乎都产生了良好的效果.

There are 4 available methods on FileReader() to read the files. They all seem to produce good results.

  • readAsText(文件)
  • readAsBinaryString(file);
  • readAsArrayBuffer(file);
  • readAsDataURL(file);

在这种情况下,我应该使用哪个?为什么?您还可以解释它们之间的区别吗?

Which is should I be using in this case and why? Can you also explain the difference between them?

function onFileSelect(e) {
  const file = e.target.files[0];
  const reader1 = new FileReader();
  const reader2 = new FileReader();
  const reader3 = new FileReader();
  const reader4 = new FileReader();
  
  reader1.onload = (event) => {
    const fileContent = event.target.result;
    console.log('Hash from "readAsText()": ');
    console.log(md5(fileContent));
  }
  
  reader2.onload = (event) => {
    const fileContent = event.target.result;
    console.log('Hash from "readAsBinaryString()": ');
    console.log(md5(fileContent));
  }
  
  reader3.onload = (event) => {
    const fileContent = event.target.result;
    console.log('Hash from "readAsArrayBuffer()": ');
    console.log(md5(fileContent));
  }
  
  reader4.onload = (event) => {
    const fileContent = event.target.result;
    console.log('Hash from "readAsDataURL()": ');
    console.log(md5(fileContent));
  }
  
  reader1.readAsText(file);
  reader2.readAsBinaryString(file);
  reader3.readAsArrayBuffer(file);
  reader4.readAsDataURL(file);
  
}

.myDiv {
  margin-bottom: 10px;
}

<script src="https://cdn.jsdelivr.net/npm/js-md5@0.7.3/src/md5.min.js"></script>
<div class="myDiv">Pick an image file to see the 4 hash results on console.log()</div>
<input type='file' onChange="onFileSelect(event)" accept='.jpg,.jpeg,.png,.gif' />

推荐答案

使用readAsArrayBuffer.

readAsBinaryString()readAsDataURL()将使您的计算机执行比需要完成的工作更多的工作:

Use readAsArrayBuffer.

readAsBinaryString() and readAsDataURL() will make your computer do a lot more work than what needs to be done:

  1. 将blob读取为二进制流
  2. 转换为UTF-16/base64字符串(记住在js中字符串不是可变的,您对其执行的任何操作实际上都会在内存中创建一个副本)
  3. [传递给您的lib]
  4. 转换为二进制字符串
  5. 处理数据

另外,看来您的库无法处理数据URL,并且无法处理UTF-16字符串.

Also, it seems your library doesn't handle data URLs and fails on UTF-16 strings.

readAsText()默认情况下会尝试将二进制数据解释为UTF-8文本序列,这对于二进制数据(如光栅图像)非常不利:

readAsText() by default will try to interpret you binary data as an UTF-8 text sequence, which is pretty bad for binary data like raster image:

// generate some binary data
document.createElement('canvas').toBlob(blob => {
  const utf8_reader = new FileReader();
  const bin_reader = new FileReader();
  let done = 0;
  utf8_reader.onload = bin_reader.onload = e => {
    if(++done===2) {
      console.log('same results: ', bin_reader.result === utf8_reader.result);
      console.log("utf8\n", utf8_reader.result);
      console.log("utf16\n", bin_reader.result);
    }
  }
  utf8_reader.readAsText(blob);
  bin_reader.readAsBinaryString(blob);
});

readAsArrayBuffer只会像分配内存中那样分配二进制数据.简单的I/O,无需处理.
为了处理这些数据,我们可以在此二进制数据上使用TypedArrays视图,这些视图仅仅是视图,也不会产生任何开销.

readAsArrayBuffer on the other hand will just allocate the binary data as is in memory. Simple I/O, no processing.
To manipulate this data, we can use TypedArrays views over this binary data, which being only views, won't create any overhead either.

如果您查看该库,您就是使用,他们无论如何都会将您的输入传递给这样的Uint8Array进行进一步处理.但是请注意,它们显然需要您传递此ArrayBuffer的Uint8Array视图,而不是直接传递裸ArrayBuffer.

And if you look at the library you are using, they will anyway pass your input to such an Uint8Array to further process it. However beware they apparently need you to pass an Uint8Array view of this ArrayBuffer instead of the nude ArrayBuffer directly.

这篇关于正确的方法使用FileReader()读取文件以从图像文件生成md5哈希字符串?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆