Kann man in einer Shell auch Kommazahlen zwischen grösse unterscheiden?
Also quasi so:
Code: Alles auswählen
if [ $KOMMAZAHLA -gt $KOMMAZAHLB ]; then ...
Aber ich muss es schon mit Kommazahlen lösen.
Aber wie stellt man so etwas bitte an?
Code: Alles auswählen
if [ $KOMMAZAHLA -gt $KOMMAZAHLB ]; then ...
NUMBERS
The most basic element in bc is the number. Numbers are arbitrary precision numbers. This precision is both in the integer part and the fractional part. All numbers are represented internally in decimal and all computation is done in decimal. (This version truncates results from divide and multiply operations.) There are two attributes of numbers, the length and the scale. The length is the total number of decimal digits used by bc to represent a number and the scale is the total number of decimal digits after the decimal point. For example:
.000001 has a length of 6 and scale of 6.
1935.000 has a length of 7 and a scale of 3.
Code: Alles auswählen
$ bc -l <<< "2.3 + 7.8"
10.1
$ bc -l <<< "2.3 > 7.8"
0
$ bc -l <<< "2.3 < 7.8"
1
Code: Alles auswählen
if (( $(echo "$KOMMAZAHLA > $KOMMAZAHLB" |bc -l) )); then
…
fi
Code: Alles auswählen
AAA="128.2800"
BBB="128.2900"
if [ x"$(echo "scale=4; $AAA < $BBB" | bc -l)" = x1 ]; then
echo "ok"
fi
Nein. bc rechnet mit Festkommazahlen. Das ist das dicke Feature von bc gegenüber fast allen anderen tools. Defakto ist das in 99% eher nicht das was du haben willst. Es ist aber eben deutlich einfacher vorhersehbar, was passiert. Du kannst explizit angeben wieviele Nachkommastellen (im 10er System) du haben willst. Ich würde eher calc aus apcalc bevorzugen. Schwerer zu beschreiben, was es macht, aber im Normalfall das was du willst. (Fließkommazahlen)Um bc mit Fließkommazahlen rechnen zu lassen, musst Du die Option -l verwenden:
Code: Alles auswählen
128.2800
Code: Alles auswählen
bc -l
Code: Alles auswählen
scale=4
Code: Alles auswählen
AAA="128.2800"
BBB="128.2900"
if [ $(echo "$BBB > $AAA" | bc) -eq 1 ]; then
echo "ok"
fi
Code: Alles auswählen
AAA="128.28"
BBB="128.29"
if [ $(echo "scale=4; $BBB > $AAA" | bc) -eq 1 ]; then
echo "ok"
fi
Code: Alles auswählen
AAA="128.28"
BBB="128.29"
if [ $(echo "$BBB > $AAA" | bc) -eq 1 ]; then
echo "ok"
fi
Code: Alles auswählen
$ a=120.123
$ b=120.456
$ if [ ${a%\.*} -eq ${b%\.*} ]; then n=$((${a#*\.}-${b#*\.})); if [ $n -gt 0 ]; then echo "0.$n"; else echo "-0.${n#-}"; fi; else echo $((${a%\.*}-${b%\.*})); fi
-0.333
Code: Alles auswählen
$ echo ${a%\.*} ${a#*\.} ${b%\.*} ${b#*\.}
120 123 120 456
Code: Alles auswählen
$ a=120.0123
$ b=120.00456
$ if [ ${a%\.*} -eq ${b%\.*} ]; then n=$((${a#*\.}-${b#*\.})); if [ $n -gt 0 ]; then echo "0.$n"; else echo "-0.${n#-}"; fi; else echo $((${a%\.*}-${b%\.*})); fi
-0.219
Code: Alles auswählen
AAA="128.2800"
BBB="128.2900" # BBB ist größer als AAA
echo "$BBB > $AAA" | bc # aber Ausgabe ist 1, also Fehler und angeblich falsch
1
BBB="128.2799" # BBB ist kleiner als AAA
echo "$BBB > $AAA" | bc # aber Ausgabe ist 0, also richtig und angeblich kein Fehler
0
Code: Alles auswählen
$ while ((0)); do echo hallo; done
$ while ((1)); do echo hallo; done
hallo
hallo
hallo
hallo
hallo
hallo
[…]
bc gibt bei korrekter Syntax immer den Rückgabewert 0. Das Ergebnis schreibt es nach stdout. Das ist aber kein Rückgabewert.bc gibt mir den Rückgabewert, nur eben falsch herum aus meiner Sicht...
Code: Alles auswählen
$ [ 5 -le 3 ] > /dev/null ; echo $?
> 1
$ [ 3 -le 5 ] > /dev/null ; echo $?
> 0
Code: Alles auswählen
$ echo "5 > 3" | bc > /dev/null ; echo $?
> 0
$ echo "0 > 5" | bc > /dev/null ; echo $?
> 0
Wie du siehst sieht man bei test bzw [ ] nichts. bc sagt aber 0.$ [ 5 > 3 ]
$ echo "3 > 5" | bc
> 0
nur warum muss bei wannes Post noch auf Gleichheit „-eq 1” geprüft werden?
Code: Alles auswählen
test ... -eq 1