LINUX.ORG.RU

Занимательная математика с плавающей точкой

 , ,


1

0

Узнал для себя следующее:

$ perl -e '(0.1 + 0.2 == 0.3) ? print "ok" : print "false"';

Ответ: false

Взято по мотивам http://learn.javascript.ru/number#неточные-вычисления

Также сказано и такое утверждение:

Ради справедливости заметим, что в точности то же самое происходит в любом другом языке, где используется формат IEEE 754, включая Java, C, PHP, Ruby, Perl.

Вопрос в том, как это можно отловить в перле? Т.е наглядно показать аналогично JS, что все именно так?

Updated. Дока с мат. объяснением: http://docs.oracle.com/cd/E19957-01/806-3568/ncg_goldberg.html

Это интересно: В фильме «Офисное пространнство» был использован похожий баг. В фильме идет отсылка к «Супермену», где была также использована данная «особенность» и якобы имело место быть в 70-х годах в Америке в действительности. Суть: ребята хотели украсть таким образом деньги у компании :)

Вопрос в том, как это можно отловить в перле?

что отловить? работает так же как в js 0.1 + 0.2 != 0.3, все верно.

hizel ★★★★★ ()

Как-то так

perl -e '(0 < 0.1+0.2-0.3) & (0.1+0.2-0.3 < 1e-15) ? print "ok\n" : print "false\n"';

Xenesz ★★★★ ()
> python2 -c 'print (0.1+0.2)'
0.3
> python3 -c 'print (0.1+0.2)'
0.30000000000000004
init_6 ★★★★★ ()

Нашел:

$ perl -e 'printf("%.20f", 0.1 + 0.2);'
0.30000000000000004441
gh0stwizard ★★★★★ ()
Последнее исправление: gh0stwizard (всего исправлений: 1)

Есть ещё такое:

$ cat ./perltest 
#!/usr/bin/perl

$x = NaN;
($x == $x) ? print "true" : print "false";



$ ./perltest 
false
=)

Deleted ()
Последнее исправление: Deleted (всего исправлений: 1)
Ответ на: комментарий от Deleted

дык это NaN, он по определению сам себе не равен. Что тебя удивляет?

anonymous ()
Ответ на: комментарий от anonymous

дык это NaN, он по определению сам себе не равен. Что тебя удивляет?

Меня? Ничего. Просто на случай, если некоторые не в курсе, что значения, одинаковые бит-в-бит, могут быть не равны друг другу. Обратное тоже случается.

Deleted ()
Ответ на: комментарий от Deleted

Забавно, учитывая следующее:

#/usr/bin/perl

use strict;
use warnings;

my $x = "abc";
($x == $x) ? print "true" : print "false";
Argument "abc" isn't numeric in numeric eq (==) at abc.pl line 8.
true%
#/usr/bin/perl

use strict;
use warnings;

my $x = "NaN";
($x == $x) ? print "true" : print "false";
false%
gh0stwizard ★★★★★ ()
Ответ на: комментарий от gh0stwizard

print +($x == $x) ? «true» : «false»;

Не важно, но «не в силах выдержать».

anonymous ()
Ответ на: комментарий от gh0stwizard

#/usr/bin/perl

#!/usr/bin/perl

my $x = «NaN»;

Не пытайся на*бать perl — он знает что ты имеешь ввиду!

helios ★★★★★ ()
Ответ на: комментарий от helios

Ну если честно, то это работает только если сделать:

$ chmod +x script.pl
$ ./script.pl

Т.к. особенность выполнения «экзешников». Я всегда пускаю через perl myscript.pl, поэтому и не заметил опечатку.

gh0stwizard ★★★★★ ()
Ответ на: комментарий от gh0stwizard

Ну если честно, то это работает только если сделать:

Да я понимаю. Можно ещё вспомнить, что в Windows это не работает. Но уж коли писать, то правильно.

helios ★★★★★ ()

см «What Every Computer Scientist Should Know About Floating-Point Arithmetic»

true_admin ★★★★★ ()

дык, очень старую особенность ты узнал...

paranormal ★★ ()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.