Autor Zpráva
martinK
Profil
Dobrý den,

ve světe Flash jsem laikem, rád bych věděl, jak nejjednodušeji (kde, program) a jakým způsbem lze vytvořit kalkulačku na libovolné vzorce, obzvlášť z finanční matematiky. Ocením nasměrování na vhodný článek či tutoriál.

Mockrát děkuji
Martin2
Profil *
Chceš použít technologii, kterou neznáš a jejíž vývoj byl v podstatě ukončen a už není obecně vhodné ji používat. Proč? Obyčejný JavaScript výpočty zvládne také.
Tomáš2
Profil *
"Obyčejný javascript" tyhle výpočty rozhodně nezvládne a na finanční matematiku je potřeba trochu lepší kanón, kámen úrazu je jednak v 53bitové velikosti čísla, přesnosti floatu a doublu a v rozdílech v implementaci mezi prohlížeči. Doporučil bych ti se podívat na mathjs.org .


jen pro doplnění, nejedná se o žádnou okrajovou záležitost, přesnost výpočtu v JS spadne i na banální věci jako console.log(0.1 + 0.2) a pro finanční výpočty to je pohroma.
Martin2
Profil *
Omezená přesnost desetinných čísel je vlastní prakticky všem programovacím jazykům (Když z toho vyloučíme ty matematicky dedikované, jako Matlab nebo Mathematica). Plyne to ze způsobu převodu čísel z dekadické do binární soustavy. V tomto se implementace JavaScriptu v prohlížečích neliší nijak.

Obyčejným JavaScriptem je myšlen JS bez pluginů, nějaký objekt pro přesnou matematiku by to asi sneslo (ne nezbytně, i s omezenou přesností se dá pracovat tak, aby se chyby nekumulovaly a zůstaly v řádech, kde nejsou důležité). Mimochodem ActionScript ve Flashi, jako nevlastní bratr JavaScriptu, má práci s číselnými typy úplně stejnou.
Tomáš2
Profil *
ano, o tom žádná, pracuji s čísly, jazyky znám. Nemůžeš ale počítat finanční kalkulace s tím, že výpočty mohou obsahovat chybu a ty si při výpočtu budeš dávat pozor, aby byla dostatečně malá, aby výsledek neovlivnila, to je moc špatně. Vždyť výpočet 0.2 + 0.1 nejde správně exportovat do jsonu nebo třeba zobrazit na stránce aniž bys ho dodatečně upravil.

Stačí přitom maličkost, vzít si data z eurostatu o HDP a převádět je na lokální měny. Oponoval jsem několik dp. prací, kde autoři na výpočty použili excel a prezentovali už špatné výsledky.

Co je prosímtě plugin do JS? A proč bys měl znovuvynalézat kolo a nepoužívat již odladěná a dokumentovaná řešení? To nedává smysl.

PS: JS má sníženou přesnost double na 53 bitů, narozdíl od většiny dalších jazyků, i tohle je pro mě dostatečný důvod, abych to řešil obecně a ne až v implementaci.
Martin2
Profil *
Tomáš2:
Co je prosímtě plugin do JS?
Plugin do prohlížeče, ne JS.

Nemůžeš ale počítat finanční kalkulace s tím, že výpočty mohou obsahovat chybu
Proč ne? Výraz 0.2 + 0.1 obsahuje chybu až na 17. desetinném místě. Nedovedu si představit situaci, kdy by to byl problém. (s výjimkou již zmiňované kumulace chyby u nevhodně zvolených cyklů). Výpočty budou vždy obsahovat chyby, nebo jak bys chtěl vyčíslit 1/3?

A proč bys měl znovuvynalézat kolo a nepoužívat již odladěná a dokumentovaná řešení? To nedává smysl.
Třeba proto, abys zaručil kompatibilitu v co nejširší možné míře a nenutil zbytečně uživatele instalovat pluginy a běhová prostředí kvůli věci, která jde bez problémů řešit i bez nich.
_es
Profil
Tomáš2:
JS má sníženou přesnost double na 53 bitů, narozdíl od většiny dalších jazyků
Dátový typ „číslo“ v JS je presne ten istý typ ako „double“ v C či iných programovacích jazykoch.

A proč bys měl znovuvynalézat kolo a nepoužívat již odladěná a dokumentovaná řešení?
To odladené riešenie môže zase vyvolať iné problémy. Napríklad výpočty s takými „dorobenými typmi“ trvajú oveľa dlhšie. Nemusí to vadiť pri jednoduchom výpočte, no ak ide o nejaké náročnejšie cykly... Je veľa spôsobov ako to riešiť - napríklad pracovať s najmenšou jednotkou meny. Presne sa dá v JS pracovať s celými číslami od - 9 007 199 254 740 992 do 9 007 199 254 740 992 čo by snáď mohlo stačiť.
Chamurappi
Profil
Reaguji na Tomáše2:
JS má sníženou přesnost double na 53 bitů
Ne, doublez definice přesnost 53 bitů všude. Samozřejmě i v ActionScriptu ve flashi.

a v rozdílech v implementaci mezi prohlížeči
Jaké jsou rozdíly? Já o žádných při práci s čísly nevím.

přesnost výpočtu v JS spadne i na banální věci jako console.log(0.1 + 0.2)
To není zase tak banální věc, problém je hlavně v tom, že ani samotné 0.1 není přesně 0.1, ale 0.1000000000000000055511151231257827021181583404541015625 (což se běžně při výpisu zaokrouhluje). Stejně se chová double ve všech jazycích.
Jednoduše se tomu dá vyhnout tím, že se hodnoty posunou do celých čísel, nebo rozloží do více proměnných.

Jakou navrhuješ alternativu k JS? Flash, i kdyby byl na práci s čísly lepší, je prakticky mrtvý, v současné době funguje bez potíží už jen cca třetině českých brouzdalů. Upozornění na možnou ztrátu přesnosti je na místě, ale pro webové použití vypadá momentálně JavaScript jako jediná možnost.
Nedivil bych se, kdyby martinK vyráběl nějaký kalkulačkový reklamní banner, jako bývají na portálech s auty nebo s nemovitostmi, kde si návštěvník může zadat, kolik měsíců chce splácet a ono mu to propočítá sumu – tam asi nehrozí, že by se přehoupl do triliard.
Tomáš2
Profil *
Měl jsem se vyjádřit konkrétněji.

JS ukládá integer jako double, i celá čísla jsou tedy jen 53 bitová (v tomhle případě ale asi i tak dostačuje).

Rozdíl mezi prohlížeči není ani tak v aritmetických operacích, ale nekonzistence je v JSON.parse a JSON.stringify v případě velkých čísel. Do aplikace často data nějak musíš dostat a také je často nějak poslat dál. Nemám to teď chuť zkoušet na aktuálních verzích, podporujeme vše 5 let zpátky.

Banální věc to je z hlediska finančníka, který s čísly pracuje, ne programátora, který to musí řešit. Pokud beru v potaz pouze násobení a vstup mám normovaný na 3 desetinná místa, nečekám, že mi výsledek vrátí jinou přesnost. Je tedy nutné dodatečně zkorigovat přesnost výsledku, aby odpovídala vstupu. Aneb řečeno, pokud sečtu 0.1 a 0.2, čekám, že dostanu "0.3" a ne číslo s mnoha desetinnými místy, ikdyž matematicky je výsledek velice přesný, pokud to vytisknu na fakturu, do reportu, do stránky, je to velká chyba, o tom mluvím.

Nenavrhuji alternativu k JS, pro velká čísla jsou specializované jazyky/programy a pro běžné použití jsou zbytečné. Navrhuji použít knihovnu, která se postará o korekci chyb, které plynou z IEEE 754. Nikdy není vhodné v implementaci řešit technická omezení, ale je potřeba ho separovat do mezivrstvy.

Pokud se ale jedná o další kalkulačku čehokoliv, je tohle úplně lhostejný, v tom máte pravdu :).
_es
Profil
Tomáš2:
JS ukládá integer jako double, i celá čísla jsou tedy jen 53 bitová
JS nemá rozdielne dátové typy na čísla, len jeden typ, v iných jazykoch obvykle nazvaný double.

nekonzistence je v JSON.parse a JSON.stringify v případě velkých čísel.
Nejaká konkrétna ukážka pre konkrétne prehliadače?

Použitím tej knižnice sa zmení len to, že namiesto ukladania čísel v tvare a*2^b, sa budú ukladať v tvare c*10^d, kde a b c d sú celé čísla. Problémy pri násobení a delení zostanú a aj tak bude treba vhodne zaokrúľovať, alebo zaokrúľovať dole alebo hore. Alebo sa snáď dá zaplatiť DPH presne 21 % z trebárs 100.3 korún? Problémy s reprezentáciou financií v pamäti sa dajú vyriešiť oveľa jednoduchšie ich ukladaním v najmenšej jednotke meny. Knižnica nijako zázračne nevyrieši bezrozmyslové kopírovanie čísel z nejakého kalkulátora.
Chamurappi
Profil
Reaguji na _es:
Použitím tej knižnice sa zmení len to, že namiesto ukladania čísel v tvare a*2^b, sa budú ukladať v tvare c*10^d, kde a b c d sú celé čísla.
Řekl bych, že knihovna math.js je trochu chytřejší a že umí správně pracovat se zlomky. Samozřejmě, že ztráty přesnosti stále půjde najít jinde, třeba v odmocninách atd., ale s racionálními čísly nejspíš pracuje bezchybně.


Reaguji na Tomáše2:
Nikdy není vhodné v implementaci řešit technická omezení, ale je potřeba ho separovat do mezivrstvy.
Zaplatit za to separování čtyřistakilovou knihovnou se nemusí vždy vyplatit. Kdyby opravdu martinK dělal banner, musí se vejít do limitů.
Ať dělá cokoliv, tak se výpočet děje jen na straně klienta a je otázka, jak moc bude výsledek pro cokoliv závazný. Nepředpokládám, že bude vypočítávat částku na fakturu v prohlížeči, ale kdo ví…
Rozhodně ti ale děkuji, že jsi math.js zmínil, je to zajímavá knihovna, neznal jsem ji.
_es
Profil
Chamurappi:
Keď už sa použije nejaký „vylepšený“ číslený typ, tak pre finančné aplikácie dekadické ukladanie čísel, v prípade tej knižnice tento, čo asi myslel aj Tomáš2. „Čarovanie“ so zlomkami na to nie je vhodné - 2/7 koruny si asi v banke aj tak neuložíš.

Vaše odpověď

Mohlo by se hodit


Prosím používejte diakritiku a interpunkci.

Ochrana proti spamu. Napište prosím číslo dvě-sta čtyřicet-sedm: