Genauigkeit in Perl

Genauigkeit in Perl

am 01.03.2006 17:15:40 von Stefan Kristukat

Hallo zusammen,

hier mein Code. Am Ende sollte fuer $sum 1.0 rauskommen, tut es aber
nicht. Es kommt mehr raus - abhängig von der Genauigkeit. Jetzt rechnet
Perl aber schon per default mit doppelter Genauigkeit. Wie kann ich das
Problem vermeiden?
Grüsse

Stefan
------------------------------------------------------------ -------
use warnings;
use strict;


my $nr=250000;
my $step=1/$nr;
print "$step \t";
my $sum=0;
for (1..$nr){$sum=$sum+$step};
print "$sum \n";

Re: Genauigkeit in Perl

am 01.03.2006 17:28:46 von Karlheinz Weindl

Stefan Kristukat schrieb:

> Hallo zusammen,
>
> hier mein Code. Am Ende sollte fuer $sum 1.0 rauskommen, tut es aber
> nicht. Es kommt mehr raus - abhängig von der Genauigkeit. Jetzt rechnet
> Perl aber schon per default mit doppelter Genauigkeit. Wie kann ich das
> Problem vermeiden?
> Grüsse
>
> Stefan
> ------------------------------------------------------------ -------
> use warnings;
> use strict;
>
>
> my $nr=250000;
> my $step=1/$nr;
> print "$step \t";
> my $sum=0;
> for (1..$nr){$sum=$sum+$step};
> print "$sum \n";

Denk drüber nach und post wieder, wenn du auf der Welt irgendeine
Programmiersprache gefunden hast, die bei dieser Vorgehensweise 1.0 als
Ergebnis liefert.

Gruß
Karlheinz

Re: Genauigkeit in Perl

am 01.03.2006 18:36:31 von Frank Seitz

Karlheinz Weindl wrote:
> Stefan Kristukat schrieb:
>>
>>my $nr=250000;
>>my $step=1/$nr;
>>print "$step \t";
>>my $sum=0;
>>for (1..$nr){$sum=$sum+$step};
>>print "$sum \n";
>
> Denk drüber nach und post wieder, wenn du auf der Welt irgendeine
> Programmiersprache gefunden hast, die bei dieser Vorgehensweise 1.0 als
> Ergebnis liefert.

Dafür kommen alle Programmiersprachen infrage, die 1/250000
exakt als 0.000004 darstellen können. Perl kann das mit
ein bisschen Unterstützung auch:

use Math::BigFloat;

my $nr=250000;
my $step=Math::BigFloat->new(1);
$step->bdiv($nr);
print "$step \t";
my $sum=0;
for (1..$nr){$sum=$sum+$step};
print "$sum \n";

Davon, das die Berechung schnell gehen soll,
war ja nicht die Rede :)

Grüße
Frank
--
Dipl.-Inform. Frank Seitz; http://www.fseitz.de/
Tel: 04103/180301; Fax: -02; Industriestr. 31, 22880 Wedel

Re: Genauigkeit in Perl

am 01.03.2006 18:42:03 von Wolf Behrenhoff

Karlheinz Weindl schrieb:
> Stefan Kristukat schrieb:
>> my $nr=250000;
>> my $step=1/$nr;
>> print "$step \t";
>> my $sum=0;
>> for (1..$nr){$sum=$sum+$step};
>> print "$sum \n";
>
> Denk drüber nach und post wieder, wenn du auf der Welt irgendeine
> Programmiersprache gefunden hast, die bei dieser Vorgehensweise 1.0 als
> Ergebnis liefert.

Zählt Mathematica als Programmiersprache?
nr = 250000;
step = 1/nr;
Print[step];
sum = 0;
For[i = 1, i <= nr, i++, sum = sum + step];
Print[sum];

liefert
1/250000
1

Geht also! ;-)

Wenn man das so in Perl machen möchte (aus was für einem Grund auch
immer), dann muss eben ein wenig Bruchrechnen und Zähler und Nenner
verarbeiten.

Hier kann man einfach von $i von 1 bis 250000 laufen lassen und jeweils
als Teilsumme $sum=$i/250000 schreiben.

Wolf

Re: Genauigkeit in Perl

am 01.03.2006 18:59:10 von Karlheinz Weindl

Frank Seitz schrieb:

> Karlheinz Weindl wrote:
>
>>Stefan Kristukat schrieb:
>>
>>>my $nr=250000;
>>>my $step=1/$nr;
>>>print "$step \t";
>>>my $sum=0;
>>>for (1..$nr){$sum=$sum+$step};
>>>print "$sum \n";
>>
>>Denk drüber nach und post wieder, wenn du auf der Welt irgendeine
>>Programmiersprache gefunden hast, die bei dieser Vorgehensweise 1.0 als
>>Ergebnis liefert.
>
>
> Dafür kommen alle Programmiersprachen infrage, die 1/250000
> exakt als 0.000004 darstellen können. Perl kann das mit
> ein bisschen Unterstützung auch:
>
> use Math::BigFloat;
>
> my $nr=250000;
> my $step=Math::BigFloat->new(1);
> $step->bdiv($nr);
> print "$step \t";
> my $sum=0;
> for (1..$nr){$sum=$sum+$step};
> print "$sum \n";
>
> Davon, das die Berechung schnell gehen soll,
> war ja nicht die Rede :)

Ja, ja Frank, echt guter Vorschlag!

Und dann geht der Stefan her, packt an den Divisor noch ein paar Nullen
mehr ran, kommt an Ostern wieder und sagt: Perl rechnet nicht nur
ungenau, es dauert auch noch eine Ewigkeit, bis das falsche Ergebnis kommt!

Schönen Aschermittwoch
Karlheinz

(nix für ungut Stefan, ist natürlich eine bösartige Unterstellung)

Re: Genauigkeit in Perl

am 01.03.2006 19:38:22 von Frank Seitz

Karlheinz Weindl wrote:
> Frank Seitz schrieb:

[Rechnen mit beliebig großen Gleitkommazahlen]

> Ja, ja Frank, echt guter Vorschlag!
>
> Und dann geht der Stefan her, packt an den Divisor noch ein paar Nullen
> mehr ran, kommt an Ostern wieder und sagt: Perl rechnet nicht nur
> ungenau, es dauert auch noch eine Ewigkeit, bis das falsche Ergebnis kommt!

Das sehe ich nicht. Weder, dass er im Fall einer großen Zahl nochmal
wiederkommt, noch dass er ein falsches Ergebnis erhält.

my $nr=Math::BigFloat->new(250000000000000000000000000000000000 00000000000000);
my $step=Math::BigFloat->new(1);
$step->bdiv($nr);
print "$nr\n$step\n";
__END__
25000000000000000000000000000000000000000000000000
0.00000000000000000000000000000000000000000000000004

Grüße
Frank
--
Dipl.-Inform. Frank Seitz; http://www.fseitz.de/
Tel: 04103/180301; Fax: -02; Industriestr. 31, 22880 Wedel

Re: Genauigkeit in Perl

am 11.03.2006 17:22:45 von unknown

On Wed, 01 Mar 2006 17:15:40 +0100, Stefan Kristukat
wrote:

>Hallo zusammen,
>
>hier mein Code. Am Ende sollte fuer $sum 1.0 rauskommen, tut es aber
>nicht. Es kommt mehr raus - abhängig von der Genauigkeit. Jetzt rechnet
>Perl aber schon per default mit doppelter Genauigkeit. Wie kann ich das
>Problem vermeiden?
(
Alles in ints verwandeln, ggf Bigint verwenden.
Dann mit modulo-Arithmetik zurückrechnen.

Alternativ: Mit Strings arbeiten und die Rechenoperationen auf
Stringoperationen zurückführen.

Oder mit Brüchen rechnen: Math::Fraction

Oder
use const eps => Wähle eine zahl genügende klein
definiere eine Zahl $a als $a=($a-eps,$a+eps).
)
Und Wolfbook p 472 und TPJ No 8 "unreal Numbers " von T.Phoenix lesen.



----== Posted via Newsfeeds.Com - Unlimited-Unrestricted-Secure Usenet News==----
http://www.newsfeeds.com The #1 Newsgroup Service in the World! >100,000 Newsgroups
---= East/West-Coast Server Farms - Total Privacy via Encryption =---