Kirjautuminen

Haku

Tehtävät

Keskustelu: Ohjelmointikysymykset: C++: Suurten kokonaislukujen laskin C:llä

käsienkäsi [15.01.2007 10:31:16]

#

Elikkäs tollasta olis tarkoitus väsätä. Luvut ei siis ole mitään miljardeja tms. vaan satoja desimaaleja pitkiä... Aloittelija kun on, niin apua tarvitsee. Mikä olis paras lähestymistapa? Annetut luvut otetaan sisään stringeinä(?), mutta entäpä sitten laskeminen? Bittitasolla? Täytyiskö luvut vaihtaa eri kantaan?

tn [15.01.2007 21:36:37]

#

Yksi vaihtoehto on käyttää valmista kirjastoa: http://www.swox.com/gmp/

Toki itse koodamalla oppii paremmin. Helpointahan tuo olisi varmaankin toteuttaa pitämällä luvut merkkijonoina (/tavujonoina). Esimerkiksi yksi desimaali yhtä merkkiä/tavua kohden. Toisaalta jos haluaa enemmän kikkailla, saa yhteen tavuun toki pakattua kaksikin desimaalia. Tässä lähestymistavassa (1 tai 2 numeroa per tavu) on se hyvä puoli, että lukujen muuntaminen kymmenjärjestelmään ja takaisin lukemista ja tulostamista varten on helppoa.

Tehokkuuden (tehokkaiden laskujen) kannalta olisi tietenkin järkevää muuntaa luvut binäärijärjestelmään. Tässä tapauksessa saattaa myös laskutoimenpiteiden koodaaminen olla helpompaa.

C++:llahan tuosta kannattaisi ehdottomasti tehdä luokka. C:ssä onkin sitten tyytyminen structeihin...

Jaska [16.01.2007 06:51:47]

#

tn kirjoitti:

Tehokkuuden (tehokkaiden laskujen) kannalta olisi tietenkin järkevää muuntaa luvut binäärijärjestelmään.

Totta, mutta jos luvut ovat vain alle tuhat desimaalia, on ajansäästö melko pieni. Miten muuten kannattaisi toteuttaa suurempien lukujen laskin, jotta muistia kuluisi mahdollisimman vähän? Onko optimaalisempaa tapaa kuin linkitetty lista, jossa solmussa yksi bitti kuvaa lukua, yksi edellistä solmua ja yksi seuraavaa?

tn [16.01.2007 20:17:19]

#

Jaska kirjoitti:

tn kirjoitti:

Tehokkuuden (tehokkaiden laskujen) kannalta olisi tietenkin järkevää muuntaa luvut binäärijärjestelmään.

Totta, mutta jos luvut ovat vain alle tuhat desimaalia, on ajansäästö melko pieni.

Niin, tuokin varmaankin riippuu siitä, paljonko laskee. Ja siitä, mitä pitää "pienenä" ajansäästönä ja mitä suurena. En toki ole itse kokeillut.

lainaus:

Miten muuten kannattaisi toteuttaa suurempien lukujen laskin, jotta muistia kuluisi mahdollisimman vähän? Onko optimaalisempaa tapaa kuin linkitetty lista, jossa solmussa yksi bitti kuvaa lukua, yksi edellistä solmua ja yksi seuraavaa?

No eikös tuo nyt riipu aika monestakin asiasta. Jos lukujen (maksimi)koko on vakio, niin eiköhän ne kannattaisi jonnekin taulukkoon tallentaa. Linkitetyssä listassa kuitenkin nuo linkit vievät tilaa. Jos taas luvut voivat olla mielivaltaisen isoja (muistin rajoissa tietenkin), onkin kysymys jo ongelmallisempi. Jos pelkkää tilansäästöä katsotaan, niin taulukko on toki tässäkin tapauksessa edullisin ratkaisu. Toisaalta listan tapauksessa käy luvun kasvattaminen jouhevammin, kun taas taulukon tapauksessa täytyy suorittaa "raskas" muistinvaraus + kopiointi -operaatio, jos taulukon kapasiteetti loppuu. Itse käyttäisin varmaankin taulukkoa. Edellä mainitsemani GMP:n lähdekoodista varmaankin ainakin löytyisi kohtuullisen tehokas ratkaisu.

lainaus:

... jossa solmussa yksi bitti kuvaa lukua, yksi edellistä solmua ja yksi seuraavaa?

Miksi pitäisi rajoittua yhteen bittiin per solmu? Minä ainakin käyttäisin kokonaisen int:in kapasiteetin hyväkseni. Mahdollisesti jopa useammankin per solmu. Niin, ja tässä:

tn kirjoitti:

Tehokkuuden (tehokkaiden laskujen) kannalta olisi tietenkin järkevää muuntaa luvut binäärijärjestelmään. Tässä tapauksessa saattaa myös laskutoimenpiteiden koodaaminen olla helpompaa.

en tarkoittanut, että tieto pitäisi tallentaa bitti kerrallaan vaan int:ti kerrallaan "232-järjestelmään" (tai vastaavaan). Siis esimerkiksi luku 2001599834386810 = 123456789ABC16 tallennettaisiin kahtena 32-bittisenä etuperkittömänä kokonaislukuna: 466010 = 123416 ja 145074450810 = 56789ABC16. Muunnos binäärijärjestelmän ja muiden 2n-järjestelmien välillähän on triviaalia, joten puhuin tuosta binäärijärjestelmänä.

Vastaus

Aihe on jo aika vanha, joten et voi enää vastata siihen.

Tietoa sivustosta