我使用这个函数将文件大小(以字节为单位)转换为人类可读的文件大小:

零二线函数 var i = -1; var byteUnits =[英国‘计划生育’‘兆’,‘和合’,‘PB’‘EB”、“ZB’,‘YB]; do { fileSizeInBytes /= 1024; 我+; while (fileSizeInBytes > 1024) 数学归来。max(fileSizeInBytes, 0.1)。toFixed(1) + byteUnits[i]; 的 控制台日志(getReadableFileSizeString (1551859712);//输出是“1.4 GB”

然而,这似乎不是百分之百准确的。例如:

getReadableFileSizeString(1551859712); // output is "1.4 GB"

不应该是“1.5 GB”吗?除以1024似乎失去了精度。是我完全误解了什么,还是有更好的办法?


当前回答

这取决于你是想使用二进制还是十进制约定。

例如,RAM总是用二进制来度量,因此将1551859712表示为~1.4GiB是正确的。

另一方面,硬盘制造商喜欢使用十进制,所以他们称它为~1.6GB。

只是让人迷惑的是,软盘混合使用了这两种系统——它们的1MB实际上是1024000字节。

其他回答

1551859712 / 1024 = 1515488
1515488 / 1024 = 1479.96875
1479.96875 / 1024 = 1.44528198242188

你的解决方法是正确的。要认识到的重要一点是,为了从1551859712到1.5,必须除以1000,但是字节是以二进制到十进制的1024块计算的,这就是为什么gb的值更小。

Let bytes = 1024 * 10 * 10 * 10;

控制台日志(getReadableFileSizeString(字节)。

将返回1000.0Кб而不是1MB

基于cocco的想法,这里有一个不太紧凑但希望更全面的示例。

<!DOCTYPE html>
<html>
<head>
<title>File info</title>

<script>
<!--
function fileSize(bytes) {
    var exp = Math.log(bytes) / Math.log(1024) | 0;
    var result = (bytes / Math.pow(1024, exp)).toFixed(2);

    return result + ' ' + (exp == 0 ? 'bytes': 'KMGTPEZY'[exp - 1] + 'B');
}

function info(input) {
    input.nextElementSibling.textContent = fileSize(input.files[0].size);
} 
-->
</script>
</head>

<body>
<label for="upload-file"> File: </label>
<input id="upload-file" type="file" onchange="info(this)">
<div></div>
</body>
</html> 

解决方案作为ReactJS组件

Bytes = React.createClass({
    formatBytes() {
        var i = Math.floor(Math.log(this.props.bytes) / Math.log(1024));
        return !this.props.bytes && '0 Bytes' || (this.props.bytes / Math.pow(1024, i)).toFixed(2) + " " + ['Bytes', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'][i]
    },
    render () {
        return (
            <span>{ this.formatBytes() }</span>
        );
    }
});

更新 对于那些使用es6的人来说,这里是同一个组件的无状态版本

const sufixes = ['Bytes', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];
const getBytes = (bytes) => {
  const i = Math.floor(Math.log(bytes) / Math.log(1024));
  return !bytes && '0 Bytes' || (bytes / Math.pow(1024, i)).toFixed(2) + " " + sufixes[i];
};

const Bytes = ({ bytes }) => (<span>{ getBytes(bytes) }</span>);

Bytes.propTypes = {
  bytes: React.PropTypes.number,
};

这是笔答题尺寸的改进

function humanFileSize(bytes, si=false) {
  let u, b=bytes, t= si ? 1000 : 1024;     
  ['', si?'k':'K', ...'MGTPEZY'].find(x=> (u=x, b/=t, b**2<1));
  return `${u ? (t*b).toFixed(1) : bytes} ${u}${!si && u ? 'i':''}B`;    
}

函数humanFileSize(bytes, si=false) { 设u, b=bytes, t= si ?1000: 1024; [",如果?“k”:“k”,…' MGTPEZY ']。Find (x=> (u=x, b/=t, b**2<1)); 返回' ${u ?(t*b).toFixed(1): bytes} ${u}${!Si && u ?“我”:“B} '; } / /测试 console.log (humanFileSize (5000));// 4.9 KiB . console.log (humanFileSize(5000,真的));// 5.0 kB