- log69 blogja
- A hozzászóláshoz be kell jelentkezni
Hozzászólások
Repl.it ruby-ban (1.8.7) kerek 0.2 jön ki, ellenben jruby 1.7.3-ban (tudom nem ez a legfrissebb, de ez van kéznél) szintén 0.19999999999999998.
Repl.it pythonban és luában viszont 0.20000000000000004. :)
- A hozzászóláshoz be kell jelentkezni
$ lua -v
Lua 5.2.2 Copyright (C) 1994-2013 Lua.org, PUC-Rio
$ lua -e "print(0.3 - 0.1)"
0.2
$ perl -v
This is perl 5, version 18, subversion 2 (v5.18.2) built for x86_64-linux-thread-multi
$ perl -e "print 0.3 - 0.1"
0.2
Valszeg csak kerekítenek egy adott hiba % alatt.
Egyébként egy alternatíva repl.it helyett:
https://eval.in/186228
- A hozzászóláshoz be kell jelentkezni
Akkor már ideone.com, az több nyelvet ismer (igaz a coffeescriptet, io-t, slasht nem).
- A hozzászóláshoz be kell jelentkezni
Érdekesség:
> 0.3.to_r
=> (5404319552844595/18014398509481984)
> 0.3.to_s
=> "0.3"
> 0.3.to_s.to_r
=> (3/10)
Tehát érdemes string-be konvertálni Rational előtt. Érthető, mivel a kiírt lebegőpontos 0.3 érték a memóriában nem ábrázolható pontosan binárisan, de megcsinálták ezek szerint a Rational osztályban hogy tudjon string-ből konvertálni pontosan.
> Benchmark.realtime{ 1000000.times{ 0.3.to_s.to_r } }
=> 2.922457332
- A hozzászóláshoz be kell jelentkezni
Bináris formában a decimális 0.1 végtelen kettedes tört, így nem igazán meglepő ez. Persze a kiíratásnál akár kerekíthetne is. Például néhány számjeggyel pontosabban számoljon, mint amit megjelenít.
tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE
- A hozzászóláshoz be kell jelentkezni
Igen, ez nyelvfüggetlen probléma. Ruby-nál még használható BigDecimal is.
http://ruby-doc.org/stdlib/libdoc/bigdecimal/rdoc/BigDecimal.html
> require "bigdecimal"
=> true
> (BigDecimal("0.3") - BigDecimal("0.1")).to_f
=> 0.2
Hasonló Rational sebességéhez:
> Benchmark.realtime{ 1000000.times{ BigDecimal("0.3") - BigDecimal("0.1") } }
=> 2.900123281
- A hozzászóláshoz be kell jelentkezni
Ez is érdekes, kisebb pontosságot ad BigDecimal hatványozásnál mint a sima Float:
> (0.3 ** 0.1) ** 10
=> 0.29999999999999993
> ((BigDecimal("0.3") ** BigDecimal("0.1")) ** BigDecimal("10")).to_f
=> 0.29999999808741157
- A hozzászóláshoz be kell jelentkezni
Illetve az sem jó megoldás hogy valamennyivel pontosabban számoljon mint ahogy megjelenít, mivel hatványnál már hatványozottan csökken a pontos tizedes jegyek száma.
Felül szerkesztettem és kiírtam egyébként hogy ez a probléma, hogy egyértelmű legyen a blog-om célja.
- A hozzászóláshoz be kell jelentkezni
> a = "5.3".to_r / "6.7".to_r * "4.3".to_r
=> (2279/670)
> a.to_f
=> 3.401492537313433
Rational-ban még jó, hogy kihasználja Ruby arbitrary prec. integer-ét, tehát bármilyen hosszú véges lebegőpontost feltud írni törtként:
a = "3.14159".to_r ** 10
p a
p a.to_f
(9364725646787226922299505202262723704312737441654490401 / 100000000000000000000000000000000000000000000000000)
93647.25646787226
- A hozzászóláshoz be kell jelentkezni