
Brenda Lang
Ich bin kürzlich auf ein Problem gestoßen, das leicht mit der Moduldivision gelöst werden konnte, aber die Eingabe war ein Float:
Bei einer periodischen Funktion (z sin
) und eine Computerfunktion, die es nur innerhalb des Periodenbereichs berechnen kann (z [-π, π]), erstellen Sie eine Funktion, die jede Eingabe verarbeiten kann.
Die “offensichtliche” Lösung ist so etwas wie:
#include <cmath>
float sin(float x){
return limited_sin((x + M_PI) % (2 *M_PI) - M_PI);
}
Warum funktioniert das nicht? Ich bekomme diesen Fehler:
error: invalid operands of types double and double to binary operator %
Interessanterweise funktioniert es in Python:
def sin(x):
return limited_sin((x + math.pi) % (2 * math.pi) - math.pi)

Ameise
Weil der normale mathematische Begriff „Rest“ nur auf die ganzzahlige Division anwendbar ist. dh Division, die erforderlich ist, um einen ganzzahligen Quotienten zu erzeugen.
Um das Konzept des “Rests” auf reelle Zahlen auszudehnen, müssen Sie eine neue Art von “Hybrid”-Operation einführen, die erzeugen würde ganze Zahl Quotient für Real Operanden. Die Core-C-Sprache unterstützt eine solche Operation nicht, wird aber als Standardbibliothek bereitgestellt fmod
Funktion sowie remainder
Funktion in C99. (Beachten Sie, dass diese Funktionen nicht identisch sind und einige Besonderheiten aufweisen. Insbesondere folgen sie nicht den Rundungsregeln der ganzzahligen Division.)

Doug Stephen
Du schaust nach fmod().
Ich denke, um Ihre Frage genauer zu beantworten, in älteren Sprachen die %
Operator wurde nur als ganzzahlige modulare Division definiert und in neueren Sprachen haben sie beschlossen, die Definition des Operators zu erweitern.
BEARBEITEN: Wenn ich raten müsste, warum, würde ich sagen, weil die Idee der modularen Arithmetik aus der Zahlentheorie stammt und sich speziell mit ganzen Zahlen befasst.
Ich kann es nicht wirklich sagen sicher, aber ich denke, es ist hauptsächlich historisch. Nicht wenige frühe C-Compiler unterstützten Gleitkommazahlen überhaupt nicht. Es wurde später hinzugefügt, und selbst dann nicht so vollständig – hauptsächlich wurde der Datentyp hinzugefügt, und die die meisten Primitive Operationen werden in der Sprache unterstützt, aber alles andere bleibt der Standardbibliothek überlassen.
Der Modulo-Operator %
in C und C++ ist für zwei ganze Zahlen definiert, es gibt jedoch eine fmod()
Funktion für die Verwendung mit Doubles verfügbar.

Yu Hao
Die Einschränkungen sind in den Standards:
C11 (ISO/IEC 9899:201x) §6.5.5 Multiplikative Operatoren
Jeder der Operanden muss vom arithmetischen Typ sein. Die Operanden des %-Operators müssen vom Typ Integer sein.
C++11 (ISO/IEC 14882:2011) §5.6 Multiplikative Operatoren
Die Operanden von * und / müssen vom arithmetischen oder Aufzählungstyp sein; die Operanden von % müssen vom Typ Ganzzahl oder Aufzählung sein. Die üblichen arithmetischen Konvertierungen werden an den Operanden durchgeführt und bestimmen die Art des Ergebnisses.
Die Lösung ist zu verwenden fmod
weshalb die Operanden von %
sind in erster Linie auf Integer-Typen beschränkt, gemäß C99 Begründung §6.5.5 Multiplikative Operatoren:
Das C89-Komitee lehnte die Ausweitung des %-Operators auf die Arbeit mit schwimmenden Typen ab, da eine solche Verwendung die von fmod bereitgestellte Einrichtung duplizieren würde

Oliver Charlesworth

Andreas
Der %-Operator gibt Ihnen einen REST (ein anderer Name für Modulus) einer Zahl. Für C/C++ ist dies nur für Integer-Operationen definiert. Python ist etwas breiter und ermöglicht es Ihnen, den Rest einer Gleitkommazahl für den Rest zu erhalten, wie oft die Zahl darin geteilt werden kann:
>>> 4 % math.pi
0.85840734641020688
>>> 4 - math.pi
0.85840734641020688
>>>
9926000cookie-checkWarum funktioniert die Moduldivision (%) nur mit ganzen Zahlen?yes
π ist nicht gleich 3,14 und kann tatsächlich nicht als Fließkommatyp dargestellt werden. Rechnen
sin(x)
für große Werte vonx
erfordert tatsächlich einen sehr schwierigen transzendentalen Argumentreduktionsprozess, der mit keiner endlichen Annäherung an pi auskommt.– R.. GitHub HÖR AUF, EIS ZU HELFEN
23. Mai 2011 um 21:03 Uhr
Dies ist mit ziemlicher Sicherheit eine Hausaufgabe, sodass Fließkommafehler entweder außerhalb des Aufgabenbereichs liegen oder zu einer Diskussion über eine strengere numerische Analyse führen sollen. So oder so,
fmod
ist wahrscheinlich das, wonach der Ausbilder sucht.– Dennis Zickefoose
23. Mai 2011 um 21:16 Uhr
Es ist keine Hausaufgabe, es ist nur etwas, das beim Lesen einer anderen SO-Frage aufgetaucht ist (stackoverflow.com/questions/6091837/…)
– Brendan Lange
23. Mai 2011 um 22:10 Uhr
OK, ich hätte meine Aussage präziser machen sollen. Mein Punkt war, dass, wenn das Argument unbegrenzt groß werden kann (nicht nur die Exponentengröße mit doppelter Genauigkeit), keine endliche Annäherung an pi ausreicht. Für Double, ja, wird eine sehr, sehr lange Annäherung an Pi ausreichen.
– R.. GitHub HÖR AUF, EIS ZU HELFEN
15. Juli 2012 um 0:21 Uhr
@aschepler: Ich glaube nicht, dass du das Problem verstanden hast.
– R.. GitHub HÖR AUF, EIS ZU HELFEN
10. Juli 2013 um 1:30 Uhr