PHP convert KB MB GB TB etc to Bytes

Viewed 30234


I'm asking how to convert KB MB GB TB & co. into bytes.
For example:

byteconvert("10KB") // => 10240
byteconvert("10.5KB") // => 10752
byteconvert("1GB") // => 1073741824
byteconvert("1TB") // => 1099511627776

and so on...

EDIT: wow. I've asked this question over 4 years ago. Thise kind of things really show you how much you've improved over time!

11 Answers

Based on https://stackoverflow.com/a/17364338/1041470

Improvements:

  • Fixed bug with bytes suffix length,
  • Allowed to use double (float) values but only integers,
  • Reverted array which holds units,
  • Renamed variables,
  • Added comments.
/**
 * Converts human readable file size into bytes.
 *
 * Note: This is 1024 based version which assumes that a 1 KB has 1024 bytes.
 * Based on https://stackoverflow.com/a/17364338/1041470
 *
 * @param string $from
 *   Required. Human readable size (file, memory or traffic).
 *   For example: '5Gb', '533Mb' and etc.
 *   Allowed integer and float values. Eg., 10.64GB.
 *
 * @return int
 *   Returns given size in bytes.
 */
function cm_common_convert_to_bytes(string $from): ?int {
  static $units = ['B', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];
  $from = trim(check_plain($from));
  // Get suffix.
  $suffix = strtoupper(trim(substr($from, -2)));
  // Check one char suffix 'B'.
  if (intval($suffix) !== 0) {
    $suffix = 'B';
  }
  if (!in_array($suffix, $units)) {
    return FALSE;
  }
  $number = trim(substr($from, 0, strlen($from) - strlen($suffix)));
  if (!is_numeric($number)) {
    // Allow only float and integer. Strings produces '0' which is not corect.
    return FALSE;
  }
  return (int) ($number * pow(1024, array_flip($units)[$suffix]));
}

I was just looking for this function and took on the challenge to try to improve in it and got it to TWO lines :) Uses a similar regex to Eugene's to validate/extract values, but avoids the switch statement. Can accept long '10MB','10mb' and short '10M','10m' values, decimal values and always returns an integer. Invalid strings return 0

function to_bytes( $str )
{
    if( ! preg_match('/^([\d.]+)([BKMGTPE]?)(B)?$/i', trim($str), $m) ) return 0;
    return (int) floor($m[1] * ( $m[2] ? (1024**strpos('BKMGTPE', strtoupper($m[2]))) : 1 ));
}

Here is a little more cleaned version according to the standards (Using answer above):

/**
 * Format kb, mb, gb, tb to bytes
 *
 * @param integer $size
 * @return integer
 */
function formatToBytes ($size)
{
    $aUnits = array('bytes' => 0, 'KB' => 1, 'MB' => 2, 'GB' => 3, 'TB' => 4);
    $sUnit = strtoupper(trim(substr($size, -2)));
    if (intval($sUnit) !== 0) {
        $sUnit = 'bytes';
    }
    if (!in_array($sUnit, array_keys($aUnits))) {
        return false;
    }
    $iUnits = trim(substr($size, 0, strlen($size) - 2));
    if (!intval($iUnits) == $iUnits) {
        return false;
    }
    return $iUnits * pow(1024, $aUnits[$sUnit]);
}
Related