In C gibt es einen Unterschied zwischen Integer Division a/b und Boden (a/b) wo beide a und b sind ganze Zahlen? Genauer gesagt, was passiert bei beiden Prozessen?C Integer Division und Floor
Antwort
a/b
ist ganzzahlige Division. Wenn entweder a
oder b
negativ ist, hängt das Ergebnis vom Compiler ab (die Rundung kann in pre-C99 gegen Null oder gegen die negative Unendlichkeit gehen; in C99 + geht die Rundung gegen 0). Das Ergebnis hat den Typ int
. floor(a/b)
führt die gleiche Division durch, konvertiert das Ergebnis in double, verwirft den (nicht vorhandenen) Bruchteil und gibt das Ergebnis als double zurück.
floor
Gibt eine double
a/b
während denen beide a
und b
ganze Zahlen einen ganzzahligen Wert ergibt.
Mit der richtigen Besetzung ist der Wert der gleiche.
Wenn typeof
Operator in C existiert (es nicht) würden wir haben:
(typeof (a /b)) floor(a/b) == a/b
EDIT: Wenn nun die Frage: gibt es einen Unterschied zwischen:
(double) (a/b)
und
floor(a/(double) b)
die Antwort ist ja. Die Ergebnisse unterscheiden sich in Bezug auf negative Werte.
Es ist möglich, Informationen zu verlieren, die von Integer zu Gleitkomma konvertieren. Nicht sehr wahrscheinlich mit int und double, aber mit einer leichten Änderung:
#include <stdio.h>
#include <math.h>
int main(void)
{
unsigned long long a = 9000000000000000003;
unsigned long long b = 3;
printf("a/b = %llu\n", a/b);
printf("floor(a/b) = %f\n", floor(a/b));
return 0;
}
Ergebnis:
a/b = 3000000000000000001
floor(a/b) = 3000000000000000000.000000
Ein Double kann alle 32bit Integer Werte genau speichern. Sie können immer double anstelle von int verwenden. Es ist nicht nur unwahrscheinlich, die Präzision zu verlieren, es ist unmöglich. Ihr Beispiel ist korrekt, aber irreführende Personen, die das Problem noch nicht verstehen. – maxy
Im Allgemeinen davon aus, dass die ganzen Zahlen sind darstellbare sowohl in der ganzen Zahl und die Gleitkommatypen, dort isn Es ist ein Unterschied, aber der Beweis ist nicht offensichtlich. Das Problem ist, dass im Fließkomma eine Rundung in der Division a/b erfolgt, so dass die floor-Funktion nicht auf den exakten rationalen Wert, sondern auf einen ungefähren Wert angewendet wird. Ich hatte ein Papier über das Thema geschrieben: https://www.vinc17.net/research/publi.html#Lef2005b
Kurz gesagt, das Ergebnis, das ich erhalten habe, ist, wenn a - b genau im Floating-Point-System darstellbar ist, dann Boden (a/b), wo a und b sind Fließkommazahlen (mit ganzzahligen Werten), ergibt das gleiche Ergebnis wie die ganzzahlige Division a/b.
In C Integer-Division führt Abschneiden gegen Null. Dies gilt seit C99, bevor es implementiert wurde. – ouah
Ah, verpasste das 'C'-Tag. Dennoch ist klar, dass meine Antwort C++ ist. '' –
@Mysticial der Punkt ist, dass 'floor' in diesem Fall nichts rundet, weil' a/b' eine ganzzahlige Division durchführt und * dann * es an 'floor' weiterleitet. – oldrinb