356 Stimmen

Konvertierung der Dateigröße in Bytes in eine für Menschen lesbare Zeichenfolge

Ich verwende diese Funktion, um eine Dateigröße in Bytes in eine für Menschen lesbare Dateigröße zu konvertieren:

function getReadableFileSizeString(fileSizeInBytes) {
  var i = -1;
  var byteUnits = [' kB', ' MB', ' GB', ' TB', 'PB', 'EB', 'ZB', 'YB'];
  do {
    fileSizeInBytes /= 1024;
    i++;
  } while (fileSizeInBytes > 1024);

  return Math.max(fileSizeInBytes, 0.1).toFixed(1) + byteUnits[i];
}

console.log(getReadableFileSizeString(1551859712)); // output is "1.4 GB"

Es scheint jedoch, dass dies nicht zu 100 % richtig ist. Zum Beispiel:

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

Sollte das nicht sein "1.5 GB" ? Es scheint, als würde die Division durch 1024 an Präzision verlieren. Verstehe ich etwas völlig falsch oder gibt es einen besseren Weg, dies zu tun?

8voto

James Mudd Punkte 1317

Hier gibt es viele gute Antworten. Aber wenn Sie nach einem wirklich einfachen Weg suchen und Ihnen eine populäre Bibliothek nichts ausmacht, ist eine großartige Lösung filesize https://www.npmjs.com/package/filesize

Es hat viele Optionen und die Benutzung ist einfach, z.B.

filesize(265318); // "259.1 KB"

Aus ihren hervorragenden Beispielen entnommen

7voto

mpen Punkte 253762

Hier ist eine weitere Implementierung, internationalisiert, geschrieben in TypeScript:

const UNITS = ['byte', 'kilobyte', 'megabyte', 'gigabyte', 'terabyte', 'petabyte']
const BYTES_PER_KB = 1000

/**
 * Format bytes as human-readable text.
 *
 * @param sizeBytes Number of bytes.
 *
 * @return Formatted string.
 */
export function humanFileSize(sizeBytes: number | bigint): string {
    let size = Math.abs(Number(sizeBytes))

    let u = 0
    while(size >= BYTES_PER_KB && u < UNITS.length-1) {
        size /= BYTES_PER_KB
        ++u
    }

    return new Intl.NumberFormat([], {
        style: 'unit',
        unit: UNITS[u],
        unitDisplay: 'short',
        maximumFractionDigits: 1,
    }).format(size)
}

Ersetzen Sie [] mit einem Sprachcode wie fr um eine vom Standard abweichende Lokalisierung zu erzwingen.

console.log(humanFileSize(0))
console.log(humanFileSize(9))
console.log(humanFileSize(99))
console.log(humanFileSize(999))
console.log(humanFileSize(1000))
console.log(humanFileSize(1001))
console.log(humanFileSize(1023))
console.log(humanFileSize(1024))
console.log(humanFileSize(1025))
console.log(humanFileSize(100_000))
console.log(humanFileSize(1_000_000))
console.log(humanFileSize(1_000_000_000))
console.log(humanFileSize(1_000_000_000_000))
console.log(humanFileSize(1_000_000_000_000_000))
console.log(humanFileSize(1_000_000_000_000_000_000))

// fr
0o
9o
99o
999o
1ko
1ko
1ko
1ko
1ko
100ko
1Mo
1Go
1To
1Po
1000Po

// en-US
0 byte
9 byte
99 byte
999 byte
1 kB
1 kB
1 kB
1 kB
1 kB
100 kB
1 MB
1 GB
1 TB
1 PB
1,000 PB

Sie können sich Intl.NumberFormat um die Einheitenumrechnung automatisch vorzunehmen. z.B.

const sizeFormatter = new Intl.NumberFormat([], {
    style: 'unit',
    unit: 'byte',
    notation: "compact",
    unitDisplay: "narrow",
})

console.log(sizeFormatter.format(0))
console.log(sizeFormatter.format(1))
console.log(sizeFormatter.format(999))
console.log(sizeFormatter.format(1000))
console.log(sizeFormatter.format(1023))
console.log(sizeFormatter.format(1024))
console.log(sizeFormatter.format(1024**2))
console.log(sizeFormatter.format(1024**3))
console.log(sizeFormatter.format(1024**4))
console.log(sizeFormatter.format(1024**5))
console.log(sizeFormatter.format(1024**6))

...aber die Einheiten sind irgendwie komisch. z.B. 1024**4 es 1.1BB was wohl "Milliarden Bytes" bedeutet; ich glaube nicht, dass das jemals jemand verwendet, auch wenn es technisch korrekt ist.

6voto

Kerkouch Punkte 1406

Meine Antwort kommt vielleicht zu spät, aber ich denke, sie wird jemandem helfen.

Metrische Vorsilbe:

/**
 * Format file size in metric prefix
 * @param fileSize
 * @returns {string}
 */
const formatFileSizeMetric = (fileSize) => {
  let size = Math.abs(fileSize);

  if (Number.isNaN(size)) {
    return 'Invalid file size';
  }

  if (size === 0) {
    return '0 bytes';
  }

  const units = ['bytes', 'kB', 'MB', 'GB', 'TB'];
  let quotient = Math.floor(Math.log10(size) / 3);
  quotient = quotient < units.length ? quotient : units.length - 1;
  size /= (1000 ** quotient);

  return `${+size.toFixed(2)} ${units[quotient]}`;
};

Binäres Präfix:

/**
 * Format file size in binary prefix
 * @param fileSize
 * @returns {string}
 */
const formatFileSizeBinary = (fileSize) => {
  let size = Math.abs(fileSize);

  if (Number.isNaN(size)) {
    return 'Invalid file size';
  }

  if (size === 0) {
    return '0 bytes';
  }

  const units = ['bytes', 'kiB', 'MiB', 'GiB', 'TiB'];
  let quotient = Math.floor(Math.log2(size) / 10);
  quotient = quotient < units.length ? quotient : units.length - 1;
  size /= (1024 ** quotient);

  return `${+size.toFixed(2)} ${units[quotient]}`;
};

Beispiele:

// Metrics prefix
formatFileSizeMetric(0)      // 0 bytes
formatFileSizeMetric(-1)     // 1 bytes
formatFileSizeMetric(100)    // 100 bytes
formatFileSizeMetric(1000)   // 1 kB
formatFileSizeMetric(10**5)  // 10 kB
formatFileSizeMetric(10**6)  // 1 MB
formatFileSizeMetric(10**9)  // 1GB
formatFileSizeMetric(10**12) // 1 TB
formatFileSizeMetric(10**15) // 1000 TB

// Binary prefix
formatFileSizeBinary(0)     // 0 bytes
formatFileSizeBinary(-1)    // 1 bytes
formatFileSizeBinary(1024)  // 1 kiB
formatFileSizeBinary(2048)  // 2 kiB
formatFileSizeBinary(2**20) // 1 MiB
formatFileSizeBinary(2**30) // 1 GiB
formatFileSizeBinary(2**40) // 1 TiB
formatFileSizeBinary(2**50) // 1024 TiB

5voto

Mohsen Alyafei Punkte 3573

Eine einfache und kurze "Pretty Bytes"-Funktion für das SI-System ohne unnötige Rundung der Nachkommastellen.

Da die Zahlengröße für den Menschen lesbar sein soll, ist eine Anzeige "1 von tausend" nicht mehr menschlich.

Die Anzahl der Dezimalstellen ist auf 2 voreingestellt, kann aber beim Aufruf der Funktion auf andere Werte geändert werden. Die gängigste Anzeige ist die Standardanzeige mit 2 Dezimalstellen.

Der Code ist kurz und verwendet die Methode der Number String Triplets.

// Simple Pretty Bytes with SI system
// Without fraction rounding

function numberPrettyBytesSI(Num=0, dec=2){
if (Num<1000) return Num+" Bytes";
Num =("0".repeat((Num+="").length*2%3)+Num).match(/.{3}/g);
return Number(Num[0])+"."+Num[1].substring(0,dec)+" "+"  kMGTPEZY"[Num.length]+"B";
}

console.log(numberPrettyBytesSI(0));
console.log(numberPrettyBytesSI(500));
console.log(numberPrettyBytesSI(1000));
console.log(numberPrettyBytesSI(15000));
console.log(numberPrettyBytesSI(12345));
console.log(numberPrettyBytesSI(123456));
console.log(numberPrettyBytesSI(1234567));
console.log(numberPrettyBytesSI(12345678));

4voto

Ebrahim Byagowi Punkte 8964

Basierend auf Coccos Antwort aber leicht desugeriert (ehrlich gesagt, diejenigen, mit denen ich zufrieden war, sind geblieben/hinzugefügt) und zeigt keine abschließenden Nullen an, unterstützt aber immer noch 0, ich hoffe, dass es für andere nützlich ist:

function fileSizeSI(size) {
    var e = (Math.log(size) / Math.log(1e3)) | 0;
    return +(size / Math.pow(1e3, e)).toFixed(2) + ' ' + ('kMGTPEZY'[e - 1] || '') + 'B';
}

// test:
document.write([0, 23, 4322, 324232132, 22e9, 64.22e12, 76.22e15, 64.66e18, 77.11e21, 22e24].map(fileSizeSI).join('<br>'));

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X