How would I round the result from two divided numbers, e.g.
3/2As when I do
testOne=$((3/2))$testOne contains "1" when it should have rounded up to "2" as the answer from 3/2=1.5
310 Answers
To do rounding up in truncating arithmetic, simply add (denom-1) to the numerator.
Example, rounding down:
N/2
M/5
K/16Example, rounding up:
(N+1)/2
(M+4)/5
(K+15)/16To do round-to-nearest, add (denom/2) to the numerator (halves will round up):
(N+1)/2
(M+2)/5
(K+8)/16 5 Good Solution is to get Nearest Round Number is
var=2.5
echo $var | awk '{print int($1+0.5)}'Logic is simple if the var decimal value is less then .5 then closest value taken is integer value. Well if decimal value is more than .5 then next integer value gets added and since awk then takes only integer part. Issue solved
1bash will not give you correct result of 3/2 since it doesn't do floating pt maths. you can use tools like awk
$ awk 'BEGIN { rounded = sprintf("%.0f", 3/2); print rounded }'
2or bc
$ printf "%.0f" $(echo "scale=2;3/2" | bc)
2 4 If you have integer division of positive numbers which rounds toward zero, then you can add one less than the divisor to the dividend to make it round up.
That is to say, replace X / Y with (X + Y - 1) / Y.
Proof:
Case 1:
X = k * Y(X is integer multiple of Y): In this case, we have(k * Y + Y - 1) / Y, which splits into(k * Y) / Y + (Y - 1) / Y. The(Y - 1)/Ypart rounds to zero, and we are left with a quotient ofk. This is exactly what we want: when the inputs are divisible, we want the adjusted calculation to still produce the correct exact quotient.Case 2:
X = k * Y + mwhere0 < m < Y(X is not a multiple of Y). In this case we have a numerator ofk * Y + m + Y - 1, ork * Y + Y + m - 1, and we can write the division out as(k * Y)/Y + Y/Y + (m - 1)/Y. Since0 < m < Y,0 <= m - 1 < Y - 1, and so the last term(m - 1)/Ygoes to zero. We are left with(k * Y)/Y + Y/Ywhich work out tok + 1. This shows that the behavior rounds up. If we have anXwhich is akmultiple ofY, if we add just 1 to it, the division rounds up tok + 1.
But this rounding is extremely opposite; all inexact divisions go away from zero. How about something in between?
That can be achieved by "priming" the numerator with Y/2. Instead of X/Y, calculate (X+Y/2)/Y. Instead of proof, let's go empirical on this one:
$ round()
> {
> echo $((($1 + $2/2) / $2))
> }
$ round 4 10
0
$ round 5 10
1
$ round 6 10
1
$ round 9 10
1
$ round 10 10
1
$ round 14 10
1
$ round 15 10
2Whenever the divisor is an even, positive number, if the numerator is congruent to half that number, it rounds up, and rounds down if it is one less than that.
For instance, round 6 12 goes to 1, as do all values which are equal to 6, modulo 12, like 18 (which goes to 2) and so on. round 5 12 goes down to 0.
For odd numbers, the behavior is correct. None of the exact rational numbers are midway between two consecutive multiples. For instance, with a denominator of 11 we have 5/11 < 5.5/11 (exact middle) < 6/11; and round 5 11 rounds down, whereas round 6 11 rounds up.
Given a floating point value, we can round it trivially with printf:
# round $1 to $2 decimal places
round() { printf "%.${2:-0}f" "$1"
}Then,
# do some math, bc style
math() { echo "$*" | bc -l
}
$ echo "Pi, to five decimal places, is $(round $(math "4*a(1)") 5)"
Pi, to five decimal places, is 3.14159Or, to use the original request:
$ echo "3/2, rounded to the nearest integer, is $(round $(math "3/2") 0)"
3/2, rounded to the nearest integer, is 2 3 To round up you can use modulus.
The second part of the equation will add to True if there's a remainder. (True = 1; False = 0)
ex: 3/2
answer=$(((3 / 2) + (3 % 2 > 0)))
echo $answer
2ex: 100 / 2
answer=$(((100 / 2) + (100 % 2 > 0)))
echo $answer
50ex: 100 / 3
answer=$(((100 / 3) + (100 % 3 > 0)))
echo $answer
34 If the decimal separator is comma (eg : LC_NUMERIC=fr_FR.UTF-8, see here):
$ printf "%.0f" $(echo "scale=2;3/2" | bc)
bash: printf: 1.50: nombre non valable
0Substitution is needed for ghostdog74 solution :
$ printf "%.0f" $(echo "scale=2;3/2" | bc | sed 's/[.]/,/')
2or
$ printf "%.0f" $(echo "scale=2;3/2" | bc | tr '.' ',')
2 Another solution is to do the division within a python command. For example:
$ numerator=90
$ denominator=7
$ python -c "print (round(${numerator}.0 / ${denominator}.0))"Seems less archaic to me than using awk.
2I think this should be enough.
$ echo "3/2" | bc 1 Following worked for me.
#!/bin/bash
function float() {
bc << EOF
num = $1;
base = num / 1;
if (((num - base) * 10) > 1 ) base += 1;
print base;
EOF
echo ""
}
float 3.2