Ist dies der richtige Weg, um eine Float-in-Integer-Konvertierung in Bash durchzuführen? Gibt es eine andere Methode?
flotToint() {
printf "%.0f\n" "$@"
}
bash
floating-point
Rahul Patil
quelle
quelle
%.0f
wird auf- oder abrunden. Ist es das was du willst? Mit können Sieprintf "%d\n" "$@" 2>/dev/null
den Bruch hacken.Antworten:
Bash
In
bash
, die wahrscheinlich so gut wie es nur geht. Das nutzt eine eingebaute Shell. Wenn Sie das Ergebnis in einer Variablen benötigen, können Sie die Befehlssubstitution oder diebash
spezifische Funktion (die jetzt auch von unterstützt wirdzsh
) verwenden:Du könntest es tun:
Aber das würde den Bruchteil entfernen, anstatt Ihnen die nächste Ganzzahl zu geben, und das würde nicht für Werte
$float
wie1.2e9
oder.12
zum Beispiel funktionieren .Beachten Sie auch die möglichen Einschränkungen aufgrund der internen Darstellung von Floats:
Sie erhalten eine Ganzzahl, aber es besteht die Möglichkeit, dass Sie diese Ganzzahl nirgendwo verwenden können.
Wie von @BinaryZebra bemerkt, wird es in verschiedenen
printf
Implementierungen (bash, ksh93, yash, nicht GNU, zsh, dash) vom Gebietsschema (dem Dezimaltrennzeichen, das.
oder sein kann,
) beeinflusst.Wenn Ihre Gleitkommazahlen immer mit dem Punkt als Dezimaltrennzeichen angegeben werden und Sie möchten, dass sie
printf
unabhängig vom Gebietsschema des Benutzers, der Ihr Skript aufruft, als solches behandelt werden , müssen Sie das Gebietsschema auf C festlegen:Mit
yash
können Sie auch Folgendes tun:(siehe unten).
POSIX
ist nicht POSIX, da
%f
es nicht von POSIX unterstützt werden muss.POSIXly können Sie tun:
Dieses ist vom Gebietsschema nicht betroffen (das Komma darf kein Dezimaltrennzeichen sein,
awk
da es dort bereits ein Sonderzeichen in der Syntax ist (print 1,2
dasselbe gilt fürprint 1, 2
die Übergabe von zwei Argumenten anprint
).zsh
In
zsh
(das Gleitkomma-Arithmetik unterstützt (Dezimaltrennzeichen ist immer der Punkt)) haben Sie dierint()
mathematische Funktion, um die nächste Ganzzahl als Gleitkomma (wie inC
) undint()
eine Ganzzahl aus einem Gleitkomma (wie inawk
) anzugeben . Sie können also Folgendes tun:Oder:
Beachten Sie jedoch, dass
double
s zwar sehr große Zahlen darstellen kann, Ganzzahlen jedoch wesentlich eingeschränkter sind.ksh93
ksh93 war die erste Bourne-ähnliche Shell, die Gleitkomma-Arithmetik unterstützt. ksh93 optimiert die Befehlsersetzung, indem keine Pipe verwendet oder gegabelt wird, wenn die Befehle nur eingebaute Befehle sind. Damit
gabelt nicht. Oder noch besser:
Das gibt auch nicht nach, macht aber auch nicht die ganze Mühe, eine gefälschte Subshell-Umgebung zu erstellen.
Sie können auch tun:
Aber hüte dich vor:
Sie könnten auch tun:
Aber wie für
zsh
:Beachten Sie, dass
ksh93
Gleitkomma-Arithmetik die Dezimaltrennzeichen-Einstellung im Gebietsschema berücksichtigt (auch wenn,
es sich ansonsten um einen mathematischen Operator handelt ($((1,2))
wäre 6/5 in einem französisch / deutschen Gebietsschema und dasselbe wie$((1, 2))
2 in einem englischen Gebietsschema). .yash
yash unterstützt auch Gleitpunktarithmetik aber keine mathematische Funktionen wie haben
ksh93
/zsh
‚srint()
. Sie können eine Zahl in eine Ganzzahl umwandeln, indem Sie beispielsweise die Binärzahl oder den Operator verwenden (funktioniert auch in,zsh
aber nicht inksh93
). Beachten Sie jedoch, dass der Dezimalteil abgeschnitten wird und nicht die nächste Ganzzahl angezeigt wird:yash
Berücksichtigt das Dezimaltrennzeichen des Gebietsschemas bei der Ausgabe, jedoch nicht die Gleitkomma-Literalkonstanten in den arithmetischen Ausdrücken, was zu Überraschungen führen kann:Es ist in gewisser Weise gut, dass Sie Gleitkommakonstanten in Ihren Skripten verwenden können, die den Punkt verwenden, und sich nicht sorgen müssen, dass er in anderen Gebietsschemata nicht mehr funktioniert, aber dennoch in der Lage ist, die vom Benutzer ausgedrückten Zahlen so lange zu verarbeiten wie du dich erinnerst zu tun:
quelle
int=${float%.*}
funktionierte sehr gut in meinem bash (version 3.2.57 (1) -release) script auf einem mac (version 10.13.4 (17E199)).,
den Dezimalpunkt. Siehe den Abschnitt überLC_ALL=C
bc
- Eine beliebige Präzisionsrechnerspracheint (float) sollte so aussehen:
Um besser abzurunden, benutze dies:
Beispiel:
quelle
float=-2; echo "($float+0.5)/1" | bc
gibt-1
.Die vorige Antwort war fast richtig: "Sie konnten tun:
Aber das würde den Bruchteil entfernen, anstatt Ihnen die nächste Ganzzahl zu geben, und das würde nicht für Werte von $ float wie zum Beispiel 1.2e9 oder .12 funktionieren .... "
Verwenden Sie einfach
${float%%.*}
.quelle
Eine sehr einfache Hacky ist
Beispielausgabe
quelle
sed
, aber diecut
Lösung ist einfacher. Ich bevorzugesed
odercut
da sie meiner Meinung nach mehr auf eingebetteten Zielen verfügbar sind alsawk
(was immer noch recht häufig überbusybox
als istbc
).Verbunden:
Ergänzen @ Stéphane Chazelas
awk
Antwort:quelle
printf
oder ob es einen anderen Grund gibt, awk dem eingebauten vorzuziehenprintf
.