Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

How to calculate the real value in kb,mb,gb,b in Bash script

I want to convert all values with kb,mb,gb,b to the real bytes, for example, "10kb" should be convert to "10240" bytes.

Here is the test function:

#! /bin/bash

get_value_in_bytes()
{
    local value="$1"
    
    local unit_length=0
    local number_length=0
    local number=0
    
    if [[ "$value" == *"gb" ]]
    then
        unit_length=2
        number_length=$((${#value} - $unit_length))
        number=$((${value:0:$number_length})) * 1024 * 1024 * 1024 || -1
    elif [[ "$value" == *"mb" ]]
    then
        unit_length=2
        number_length=$((${#value} - $unit_length))
        number=$((${value:0:$number_length}))*1024*1024 || -1
    elif [[ "$value" == *"kb" ]]
    then
        unit_length=2
        number_length=$((${#value} - $unit_length))
        number=$((${value:0:$number_length}))*1024 || -1
    elif [[ "$value" == *"b" ]]
    then
        unit_length=1
        number_length=$((${#value} - $unit_length))
        number=$((${value:0:$number_length})) || -1
    else
        number=$((${value:0:$number_length})) || -1
    fi
    
    if (( $number < 0 ))
    then
        echo "error : $value"
    else
        echo "$number : $value"
    fi
}

Here is the test:

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

get_value_in_bytes 10kb
get_value_in_bytes 10mb
get_value_in_bytes 10gb
get_value_in_bytes 10b
get_value_in_bytes 10
get_value_in_bytes not_number_mb
get_value_in_bytes not_number_gb

Here is the output:

10*1024 : 10kb
10*1024*1024 : 10mb
./test.sh: line 15: test.sh: command not found
./test.sh: line 15: -1: command not found
0 : 10gb
10 : 10b
0 : 10
0*1024*1024 : not_number_mb
./test.sh: line 15: test.sh: command not found
./test.sh: line 15: -1: command not found
0 : not_number_gb

I want this function can accept any values as input, and if the value is not number string, then convert it to -1. But the above function doesn’t work as expected.

>Solution :

Here’s a solution based on a bash ERE and a case statement:

get_value_in_bytes() {
    local bytes=-1
    if [[ $1 =~ ^([[:digit:]]+)(b|kb|mb|gb)?$ ]]
    then
        bytes=${BASH_REMATCH[1]}
        case ${BASH_REMATCH[2]} in
        kb) bytes=$((bytes * 1024)) ;;
        mb) bytes=$((bytes * 1048576)) ;;
        gb) bytes=$((bytes * 1073741824)) ;;
        esac
    fi
    printf '%s\n' "$bytes"
}
remarks:
  • With shell arithmetic you can only process integers, so for floating point numbers you’ll have to use bc.

  • b means bit, you should use B when you mean byte.

  • To be correct, the units based on 2^10 are KiB MiB GiB, etc…

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading