NOVINKA - Online rekvalifikační kurz Java programátor. Oblíbená a studenty ověřená rekvalifikace - nyní i online.
NOVINKA – Víkendový online kurz Software tester, který tě posune dál. Zjisti, jak na to!

Diskuze: Dělení a násobení velkých čísel

V předchozím kvízu, Online test znalostí Java, jsme si ověřili nabyté zkušenosti z kurzu.

Aktivity
Avatar
Neaktivní uživatel:13.8.2017 9:39

Ahoj,
ve svém programu pro převod čísla mezi číselnými soustavami vždy převedu číslo do soustavy desítkové a následně do soustavy, jež byla zadána pro výstup. Běžný postup. Problémem je, pokud má číslo moc velkou hodnotu (v decimální soustavě), protože s ním pak nemůžu pracovat ve formátu int, někdy ani v long. A u větších soustav (třicítková) stačí napsat pár cifer a hodnota čísla hned přesahuje tyto datové typy.
Zatím jsem to vyřešil tím, že mám číslo uložené jako String. Jenže k převodu potřebuji operace jako násobení, dělení, sčítání..
Algoritmus sám o sobě je jasný - dělit a násobit umí každý od druhého ročníku základní školy. Jen se mi zatím nepodařilo zapsat je do kódu. Jak by vypadala tedy metoda dělení, násobení, či sčítání v javě?

Odpovědět
13.8.2017 9:39
Neaktivní uživatelský účet
Avatar
Honza Bittner
Tvůrce
Avatar
Odpovídá na Neaktivní uživatel
Honza Bittner:13.8.2017 10:17

Musíš si uvědomit, že primitivní typy javy mají omezenou hodnotu. Long například má pravděpodobně rozsah -9,223,372,036­,854,775,808 do +9,223,372,03­6,854,775,807, což je hodně, ale jak říkáš, ve vyšších soustavách čísla rostou velmi rychle.

Jedna z optimalizací může být nepřevádět číslo do desítkové soustavy, což se ti hodí převážně pokud převádíš z vyšší než desítkové do vyšší než desítkové, tj. čísla budou zřejmě menší než v desítkové.

Reprezentace Stringem je úplně v pohodě. Musíš si uvědomit, že číslo jako takové nemá žádnou podobu a jeho zápis do čísla či řetězce je jen pomoc pro nás lidi.

Sčítání, odčítání je na implementaci se Stringy jednoduché. Násobení a dělení ne až tolik, ale také se s tím dá pracovat – vygoogli. Viz například https://stackoverflow.com/…-string-by-3, což není nejlepší zdroj, ale máš tam nějaké poznámky k této tématice.

Sčítání, odčítání – jedeš čísla zprava a postupně aplikuješ operaci a předáváš zbytek do vyšší pozice.

Násobení – pravděpodobně hloupá implementace by bylo to dělat tak, jak to dělají lidé, tj. zprava vynásobíš všechno prvním číslem (tím kterým násobíš) zprava, pak znova druhým číslem (tím kterým násobíš) zprava a postupně aplikovat již vytvořené sčítání atp. aby ses dočkal požadovaného výsledku.

Dělení už není tak jednoduché, ale jakmile si uvědomíš že dělení je operace, který ti řekne "kolikrát se něco vejde" a "jaký je zbytek", na nějakou implementaci přijdeš taky.

Nahoru Odpovědět
13.8.2017 10:17
FIT ČVUT alumnus :-) Sleduj mě na https://twitter.com/tenhobi a ptej se na cokoli na https://github.com/tenhobi/ama.
Avatar
Atrament
Člen IT Redactor Gang
Avatar
Odpovídá na Neaktivní uživatel
Atrament:13.8.2017 10:26

Použil bych <a href='http://­docs.oracle.com/ja­vase/8/docs/a­pi/java/math/Big­Decimal.html'>Big­Decimal</a>

 
Nahoru Odpovědět
13.8.2017 10:26
Avatar
Odpovídá na Atrament
Neaktivní uživatel:13.8.2017 10:59

Jak se dá v tomto případě BigDecimal použít?

Nahoru Odpovědět
13.8.2017 10:59
Neaktivní uživatelský účet
Avatar
Odpovídá na Atrament
Neaktivní uživatel:13.8.2017 11:24

Nevím, jak převést např. "12A" do BigDecimal

Nahoru Odpovědět
13.8.2017 11:24
Neaktivní uživatelský účet
Avatar
Atrament
Člen IT Redactor Gang
Avatar
Odpovídá na Neaktivní uživatel
Atrament:13.8.2017 11:46

Aha tak na tohle konkrétně bych teda použil BigInteger. BigDecimal je pro velká čísla s desetinnou čárkou, BigInteger je pro velká celá čísla, lze mezi nimi jednoduše převádět. BigInteger umí rovnou načíst hexadecimální číslo jako string, stačí mu udat v jaké soustavě to je:

String cislo = "12A";
BigInteger c = new BigInteger(cislo, 16);
//v 'c' teďka máš číslo 12A, protože jsi BigIntegeru řekl, že je to v 16kové soustavě, tak si to interně převedl a uložil podle svého
//takže mužeš pro 'převod' do jiné soustavy udělat:
System.out.println("hexadecimální číslo: " + c.toString(16) + " v decimální soustavě: " + c.toString(10));
Akceptované řešení
+20 Zkušeností
+2,50 Kč
Řešení problému
 
Nahoru Odpovědět
13.8.2017 11:46
Avatar
Honza Bittner
Tvůrce
Avatar
Odpovídá na Neaktivní uživatel
Honza Bittner:13.8.2017 11:49

Vypadá to, že ten BigDecimal opravdu umožňuje pojmout ohromné číslo. Hustý.

Podle tohoto https://stackoverflow.com/…6661/3281252 by to mělo jít pouhým napsáním soustavy jako druhý parametr. Je to příklad pro BigInteger, ale pro BigDecimal to půjde určo obdoběně.

Nahoru Odpovědět
13.8.2017 11:49
FIT ČVUT alumnus :-) Sleduj mě na https://twitter.com/tenhobi a ptej se na cokoli na https://github.com/tenhobi/ama.
Avatar
Neaktivní uživatel:13.8.2017 15:01

Děkuji za pomoc při řešení. Funguje skvěle :)

Nahoru Odpovědět
13.8.2017 15:01
Neaktivní uživatelský účet
Děláme co je v našich silách, aby byly zdejší diskuze co nejkvalitnější. Proto do nich také mohou přispívat pouze registrovaní členové. Pro zapojení do diskuze se přihlas. Pokud ještě nemáš účet, zaregistruj se, je to zdarma.

Zobrazeno 8 zpráv z 8.