Gleitpunktzahl - Test ob negativ/positiv
-
Hallo Community,
stehe gerade vor dem Problem eine Funktion zu erstellen, die testen soll, ob ein double-Wert positiv oder negativ ist. Im neuen C99-Standard ist ja die Funktion signbit() vorgesehen, allerdings ist der noch nicht vollständig in der GCC (hab Version 4.2.1) implementiert.
Jetzt dachte ich an die interne Darstellung nach IEEE-754. Ist das 1. Bit ne 1, handelt es sich um eine negative, ansonsten um eine positive Zahl.
Aber hier komm ich nicht weiter. Beispiel für -13.5
1 10000010 10110000000000000000000
Wie fragt man hier am effektivsten das erste Bit ab? Hatte einen Ansatz die 1 als Maske zu verwenden und über UND zu vergleichen. Allerdings gibts da Haue vom Compiler, wenn die Maske vom Typ int ist, die Zahl jedoch vom Typ double.
Hat jemand einen Hinweis?
Hier ein Funktion die zwar funktioniert, aber meinen Horizon übersteigt
(irgendwo im Internet gefunden)
long long endianness_test = 1; #define MSW (*(int*)&endianness_test) int test( double* a ){ __extension__ union { double d; int i[2]; } u = { d: *a }; return u.i[MSW] < 0; }
-
teste doch einfach auf < 0, dann sollte das vorzeichenbit doch gesetzt sein, oder hab' ich was übersehen?
-
~fricky schrieb:
teste doch einfach auf < 0, dann sollte das vorzeichenbit doch gesetzt sein, oder hab' ich was übersehen?
Auch eine Möglichkeit. Aber irgendwie scheint mir das nicht so "professionell" zu sein
Trotzdem erstmal danke für den Ansatz
-
Wieso nicht professionell?
-
Weil das zu trivial erscheint. Es funktioniert ohne Probleme. Da ist wohl wieder der Wald mit den ganzen Bäumen
-
hando schrieb:
Weil das zu trivial erscheint. Es funktioniert ohne Probleme. Da ist wohl wieder der Wald mit den ganzen Bäumen
Für dich sind also nur nicht triviale Lösungen professionelle? Dann ist es gut das in den meisten Softwarehäusern keine Profis arbeiten...
-
teste doch einfach auf < 0, dann sollte das vorzeichenbit doch gesetzt sein, oder hab' ich was übersehen?
Minus 0 ist nicht kleiner 0, hat aber das Bit gesetzt.
Wozu das gut ist? Keine Ahnung.
-
hando schrieb:
Weil das zu trivial erscheint.
'trivial' scheint für viele ein schimpfwort zu sein. aber aus irgendeinem grund muss es die signbit()-funktion ja geben. vielleicht aus geschwindigkeitsgründen, weil vergleiche von fliesskommawerten mehr cpu-cycles verbraten, wenn's emuliert wird?
-
Mag sein, aber die Frage ist doch ob man das wirklich braucht... Naja, wie auch immer, hier is noch eine Version:
#define SIGNBIT( x ) \ ((*( const unsigned long* )(&x))>>31)
-
David_pb schrieb:
Naja, wie auch immer, hier is noch eine Version:
die ist aber für 'long', vielleicht auch noch für 'float', aber bei double geht sie bestimmt nicht mehr.
-
Dann eben long long.
-
David_pb schrieb:
Für dich sind also nur nicht triviale Lösungen professionelle? Dann ist es gut das in den meisten Softwarehäusern keine Profis arbeiten...
So war das nicht gemeint. Ich habe nichts gegen triviale Lösungen, außer, dass man auf genau diese meist selbst nicht kommt
-
bgdnoy schrieb:
Minus 0 ist nicht kleiner 0, hat aber das Bit gesetzt.
es gibt keine -0. jedenfalls nicht, wenn man float/double als computerisierte form der reellen zahlen betrachtet. falls float/double zwei nullen mit verschiedenen vorzeichen zulassen, wird's wohl ein fehler im system sein. zumindest kann mein einfacher verstand erstmal keinen sinn in einer unterscheidung von +0 und -0 sehen.
-
~fricky schrieb:
zumindest kann mein einfacher verstand erstmal keinen sinn in einer unterscheidung von +0 und -0 sehen.
du hast gerade selber +0 und -0 gesagt. und -0 ist nicht kleiner als +0, gell?
-
volkard schrieb:
du hast gerade selber +0 und -0 gesagt.
hab' ich, das gibts aber trotzdem nicht.
volkard schrieb:
...und -0 ist nicht kleiner als +0, gell?
nee, kann ja nicht, weil's nur eine 0 gibt, die weder positiv noch negativ ist.
-
~fricky schrieb:
falls float/double zwei nullen mit verschiedenen vorzeichen zulassen, wird's wohl ein fehler im system sein.
Kann auch sein, dass sich da irgendjemand was bei gedacht hat...
zumindest kann mein einfacher verstand erstmal keinen sinn in einer unterscheidung von +0 und -0 sehen.
Einfache Verstände werden bei sowas normalerweise nicht gefragt :p
-
Bashar schrieb:
~fricky schrieb:
falls float/double zwei nullen mit verschiedenen vorzeichen zulassen, wird's wohl ein fehler im system sein.
Kann auch sein, dass sich da irgendjemand was bei gedacht hat...
kann sein, aber was?
-
Ich habe dieses Problem dem Programm brain.exe uebergeben und das hat auch als optimale Loesung x < 0 fuer float/double ausgegeben, hat aber ganz schoen lange gedauert.
-
~fricky schrieb:
kann sein, aber was?
David Goldberg, What Every Computer Scientist Should Know About Floating-Point Arithmetic:
2.2.2 Signed Zero
[...]
If zero did not have a
sign, the relation 1/(1 /x) = x would fail
to hold when x = +-oo. The reason is
that 1/–oo and 1/+oo both result in O,
and 1/0 results in +oo, the sign information
having been lost. One way to restore
the identity 1/(1 /x) = x is to have
only one kind of infinity; however,
that would result in the disastrous
consequence of losing the sign of an
overflowed quantity.Wenn du nicht wusstest, dass es überhaupt +0 und -0 gibt, könnte es sich vielleicht lohnen, das ganze Paper zu lesen.
-
Bashar schrieb:
Wenn du nicht wusstest, dass es überhaupt +0 und -0 gibt, könnte es sich vielleicht lohnen, das ganze Paper zu lesen.
ich wusste schon dass es die gibt, nur nicht warum. aber danke für den tip.