C++Talk.NET Forum Index C++Talk.NET
C++ language newsgroups
 
Archives   FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

C++ verrechnet sich

 
Post new topic   Reply to topic    C++Talk.NET Forum Index -> C++ (German)
View previous topic :: View next topic  
Author Message
Michael Wielsch
Guest





PostPosted: Mon Sep 15, 2003 11:35 pm    Post subject: C++ verrechnet sich Reply with quote



Hallo,
Bei der Logarithmus funktion von <cmath> sind Dinge im Spiel die ich nicht
verstehe.

int dez=128;
int bit=(int)(log((double)dez) / log((double)2));

Ergibt 6, obwohl mein Taschenrechner eine 7 prophezeit. Auch mit einem
static_cast<int> ist das Ergebnis falsch. Wenn man für "dez" etwa 256 oder
512 oder sonst irgenteine Zahl über 128 einsetzt stimmt das ergebnis
wieder.
Und diese Version...

double bit=(log((double)dez) / log((double)2));

....ergibt nun eine schöne, glatte 7. Das spielchen lässt sich auch mit
log10(double) statt log(double) wiederhohlen.

Könnte es sein das mein GCC diesen Fehler produziert?
Leider fehlen mir die vergleichsmöglichkeiten.

Gruß
Michael

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de
Back to top
Stefan Ring
Guest





PostPosted: Tue Sep 16, 2003 8:55 am    Post subject: Re: C++ verrechnet sich Reply with quote



Irgendwie schade, dass durch all diese komplizierten Varianten der
Compiler nie die Möglichkeit hat, die wunderbaren i386 Bit Scan
Instruktionen zu benutzen. Die tun nämlich genau das.


--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de
Back to top
Dirk Clemens
Guest





PostPosted: Tue Sep 16, 2003 3:35 pm    Post subject: Re: C++ verrechnet sich Reply with quote



Michael Wielsch wrote:
Quote:
Hallo,
Bei der Logarithmus funktion von <cmath> sind Dinge im Spiel die ich nicht
verstehe.

int dez=128;
int bit=(int)(log((double)dez) / log((double)2));


Wie wärs mit Rundung:
in bit = floor ( log(dez) / log(2) + 0.5 );


Lemmi

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Markus Schaaf
Guest





PostPosted: Tue Sep 16, 2003 4:30 pm    Post subject: Re: C++ verrechnet sich Reply with quote

"Stefan Ring" <e9725446 (AT) stud3 (DOT) tuwien.ac.at> schrieb:

Quote:
Irgendwie schade, dass durch all diese komplizierten Varianten der
Compiler nie die Möglichkeit hat, die wunderbaren i386 Bit Scan
Instruktionen zu benutzen. Die tun nämlich genau das.

Und, Vorschläge? Am nähesten dran wäre wohl ein »ilogb« (welches
es in C99 gibt, aber nur für Gleitkommazahlen), das man in C++
für Ganzzahltypen überladen könnte. In C++98 verspricht »frexp«
wohl den meisten Erfolg, wenngleich ich mir nicht vorstellen kann,
daß es wirklich einen Compiler gibt, der das so optimiert (falls
man den Rückgabewert von »frexp« ignoriert, selbstverständlich).

Allerdings sollte selbst das normale »frexp« für modernere
Prozessoren mit FPU effizienter sein, als alle bisher geposteten
Varianten.

MfG

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Michael Wielsch
Guest





PostPosted: Wed Sep 17, 2003 12:22 pm    Post subject: Re: C++ verrechnet sich Reply with quote

Stefan Ram wrote:

Quote:
int main(){ ::std::cout
( ::std::log( 128. )
/
::std::log( 2. ))
- 7. << 'n'; }

Sehr interessant.
Das erklährt das Ergebnis des Taschenrechners und auch der
(int)(log()/log()) Version.
Aber an was liegt es das in manchen Fällen eine 7 das Ergebnis ist.
Kann std::cout nicht richtig mit double Zahlen umgehen? Zumindest ab der
15.ten Stelle.

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Karl Heinz Buchegger
Guest





PostPosted: Wed Sep 17, 2003 1:56 pm    Post subject: Re: C++ verrechnet sich Reply with quote



Michael Wielsch wrote:
Quote:

Stefan Ram wrote:

int main(){ ::std::cout
( ::std::log( 128. )
/
::std::log( 2. ))
- 7. << 'n'; }

Sehr interessant.
Das erklährt das Ergebnis des Taschenrechners und auch der
(int)(log()/log()) Version.
Aber an was liegt es das in manchen Fällen eine 7 das Ergebnis ist.

Das liegt daran, das Gleitkommazahlen in einem Computer and Kommezahlen wie
Du sie aus der Mathematik kennst, nun mal sehr wenig miteinander zu tun haben.
Auch wenn es fuer viele schwer zu akzeptieren ist: Ein Computer kann in den
meisten Faellen nun mal mit Gleitkommazahlen nicht exakt rechnen (zumindest
nicht so wie Du es aus der Mathematik erwarten wuerdest)

Quote:
Kann std::cout nicht richtig mit double Zahlen umgehen? Zumindest ab der
15.ten Stelle.

Das hat nichts mit cout zu tun. Es ist vielmehr eine grundaetzliche Eigenschaft
einer Gleitkommaimplementierung. Der Mathematiker Cantor hat bewiesen, dass
es nun mal unendlich viele Zahlen zwischen 0.0 und 1.0 gibt. Wie soll man
aber unendlich viele Zahlen in nur 8 Byte (oder was auch immer) unterbringen?
Es geht nicht. Also muss man mit Naeherungen operieren. Dein Rechenergebniss
ist nun halt nicht exact 7.0, sondern in manchen Faellen vielleicht 6.9999999999998
oder 7.00000000000001. Also eine Zahl die sehr nahe an 7 liegt aber eben nicht
genau 7 ist. Dein Taschenrechner weiss das auch und berechnet seine Ergebnisse
mit mehr Kommastellen als er dir anzeigt. Bevor er Dir das Ergebnis praesentiert,
*rundet* er es auf die anzuzeigenden Kommastellen. cout (genauer der operator<<
fuer double) tut das auch, und so wird aus 6.999999999999998 bei 6 anzuzeigenden
Nachkommastellen wieder 7. Nur wenn Du explizit sagst: schneide die Nachkommastellen
ab, dann wird aus 6.99999999999999998 eben 6.

--
Karl Heinz Buchegger
[email]kbuchegg (AT) gascad (DOT) at[/email]

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Uwe Schnitker
Guest





PostPosted: Thu Sep 18, 2003 6:08 am    Post subject: Re: C++ verrechnet sich Reply with quote

Karl Heinz Buchegger <kbuchegg (AT) gascad (DOT) at> wrote

Quote:
Michael Wielsch wrote:

Stefan Ram wrote:

int main(){ ::std::cout
( ::std::log( 128. )
/
::std::log( 2. ))
- 7. << 'n'; }

Sehr interessant.
Das erklährt das Ergebnis des Taschenrechners und auch der
(int)(log()/log()) Version.
Aber an was liegt es das in manchen Fällen eine 7 das Ergebnis ist.

Das liegt daran, das Gleitkommazahlen in einem Computer and Kommezahlen wie
Du sie aus der Mathematik kennst, nun mal sehr wenig miteinander zu tun haben.
Auch wenn es fuer viele schwer zu akzeptieren ist: Ein Computer kann in den
meisten Faellen nun mal mit Gleitkommazahlen nicht exakt rechnen (zumindest
nicht so wie Du es aus der Mathematik erwarten wuerdest)

Kann std::cout nicht richtig mit double Zahlen umgehen? Zumindest ab der
15.ten Stelle.

Das hat nichts mit cout zu tun. Es ist vielmehr eine grundaetzliche
Eigenschaft
einer Gleitkommaimplementierung. Der Mathematiker Cantor hat bewiesen, dass
es nun mal unendlich viele Zahlen zwischen 0.0 und 1.0 gibt.

Sorry, aber das wusste man schon sehr viel eher. Was Cantor bewiesen hat,
ist dass es überabzählbar viele relle Zahlen zwischen 0 und 1 gibt. Der
Unterschied zwischen abzählbar unendlich und überabzählbar unendlich ist
aber für die Implementierung von Gleitkommaarithmetik irrelevant.

Quote:
Wie soll man
aber unendlich viele Zahlen in nur 8 Byte (oder was auch immer) unterbringen?

In der Praxis wird ein Programm immer nur endlich viele Variablen verwenden.
Es reicht also, wenn man es schafft, eine beliebige endliche Auswahl aus den
überabzählbar vielen Möglichen darzustellen.

Hmm - nachdenk, grübel - könnte man nicht die Basis der Exponentialdarstellung
variabel machen? Ein "suprafloat" besteht aus Mantisse, Exponent und Basis?
Und bei jeder Berechnung wird, wenn nötig, versucht, die Basis anzupassen?
Wär mal lustig, sowas auszuprobieren.

Quote:
Es geht nicht. Also muss man mit Naeherungen operieren.

Wer sagt das?

Wenn es unmöglich ist "unendlich viele Zahlen in nur 8 Byte unterbringen".
muss man sich auf endlich viele Zahlen beschränken. Oder? Oder man muss
unendlich viele Bytes zulassen.

Und da ein Programm immer nur endlich viele Werte tatsächlich benötigt,
kann man sowas machen. Das nennt man wohl "Arbitrary Precision Numbers"
oder so ähnlich, und Gerüchten zufolge sollen Banken und ähnliche
Institutionen, welche auf hohe Genauigkeit angewiesen sind, so was
ja auch machen. (Anderen Gerüchten zufolge sollen es aber gewisse
institutionen bei der Berechnung von Finanzdaten nicht immer so
ganz genau nehmen. Hmm. Man weiss es nicht, man steckt nicht drin.)

Sowas braucht natürlich in der Regel mehr Speicher und mehr Rechenzeit
als Gleitkommaarithmetik, die deshalb - trotz des Risikos - nicht
totzukriegen sein wird.


Quote:
--
Karl Heinz Buchegger
[email]kbuchegg (AT) gascad (DOT) at[/email]

Uwe

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Karl Heinz Buchegger
Guest





PostPosted: Thu Sep 18, 2003 12:19 pm    Post subject: Re: C++ verrechnet sich Reply with quote



Uwe Schnitker wrote:
Quote:

Karl Heinz Buchegger <kbuchegg (AT) gascad (DOT) at> wrote


Das hat nichts mit cout zu tun. Es ist vielmehr eine grundaetzliche
Eigenschaft
einer Gleitkommaimplementierung. Der Mathematiker Cantor hat bewiesen, dass
es nun mal unendlich viele Zahlen zwischen 0.0 und 1.0 gibt.

Sorry, aber das wusste man schon sehr viel eher.

Aehm. Glaub ich Dir mal. Ich habe mich nie naeher mit der Geschichte befasst.

Quote:
Was Cantor bewiesen hat,
ist dass es überabzählbar viele relle Zahlen zwischen 0 und 1 gibt.

Richtig das wars. Cantor's Diagonalargument.

Quote:
Der
Unterschied zwischen abzählbar unendlich und überabzählbar unendlich ist
aber für die Implementierung von Gleitkommaarithmetik irrelevant.

Eben.

Quote:

Wie soll man
aber unendlich viele Zahlen in nur 8 Byte (oder was auch immer) unterbringen?

In der Praxis wird ein Programm immer nur endlich viele Variablen verwenden.
Es reicht also, wenn man es schafft, eine beliebige endliche Auswahl aus den
überabzählbar vielen Möglichen darzustellen.

Hmm - nachdenk, grübel - könnte man nicht die Basis der Exponentialdarstellung
variabel machen? Ein "suprafloat" besteht aus Mantisse, Exponent und Basis?
Und bei jeder Berechnung wird, wenn nötig, versucht, die Basis anzupassen?
Wär mal lustig, sowas auszuprobieren.

An die Performance wage ich nicht mal zu denken :-)

Quote:

Es geht nicht. Also muss man mit Naeherungen operieren.

Wer sagt das?

Wenn es unmöglich ist "unendlich viele Zahlen in nur 8 Byte unterbringen".
muss man sich auf endlich viele Zahlen beschränken. Oder?

Ich sehe hier nicht worauf Du hinaus willst. Wenn man sich auf endlich vielen
Zahlen einschraenken muss, muss zwangslauefig irgend etwas mit den Zahlen
geschehen, die nicht in dieser Menge enthalten sind. Die beste Loesung ist
dann ziemlich sicher eine Naehrung, obwohl das natuerlich nicht zwingend ist.

Quote:
Oder man muss
unendlich viele Bytes zulassen.

Und da ein Programm immer nur endlich viele Werte tatsächlich benötigt,
kann man sowas machen. Das nennt man wohl "Arbitrary Precision Numbers"
oder so ähnlich, und Gerüchten zufolge sollen Banken und ähnliche
Institutionen, welche auf hohe Genauigkeit angewiesen sind, so was
ja auch machen. (Anderen Gerüchten zufolge sollen es aber gewisse
institutionen bei der Berechnung von Finanzdaten nicht immer so
ganz genau nehmen. Hmm. Man weiss es nicht, man steckt nicht drin.)

Ich bin zwar nicht aus der Bankbranche. Ich erinnere mich aber an
einen Ausspruch eines meiner Praktikumsleiter: "Wer fuer Geldwerte
Gleitkommaarithmetik nimmt, gehoert sowieso sofort an die Wand gestellt." :-)

--
Karl Heinz Buchegger
[email]kbuchegg (AT) gascad (DOT) at[/email]

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Display posts from previous:   
Post new topic   Reply to topic    C++Talk.NET Forum Index -> C++ (German) All times are GMT
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2006 phpBB Group
SEO toolkit © 2004-2006 webmedic.