Lång aritmetik

Den aktuella versionen av sidan har ännu inte granskats av erfarna bidragsgivare och kan skilja sig väsentligt från versionen som granskades den 21 januari 2022; kontroller kräver 2 redigeringar .

Lång aritmetik - aritmetiska operationer som  utförs med hjälp av en dator ( addition , subtraktion , multiplikation , division , exponentiering , elementära funktioner ) på tal vars bitdjup överstiger längden på maskinordet i denna dator. Dessa operationer implementeras inte i hårdvara, utan i mjukvara, med hjälp av den grundläggande hårdvaran för att arbeta med antal lägre beställningar. Ett specialfall - godtycklig precisionsaritmetik  - hänvisar till aritmetik där längden på siffror endast begränsas av mängden tillgängligt minne.

Applikation

Lång aritmetik används inom följande områden:

Hårdvara som krävs för att arbeta med lång aritmetik

Strängt taget krävs endast indirekt adressering från processorn för att implementera aritmetik med godtycklig precision ; i aritmetik med fast precision kan du till och med klara dig utan den. Vissa processorfunktioner påskyndar dock lång aritmetik samtidigt som de förenklar programmeringen.

Implementering i programmeringsspråk

Programmeringsspråk har inbyggda datatyper som i allmänhet inte överstiger 64 bitar (cirka 10 19 ). Decimal lång aritmetik implementerades i de sovjetiska programmeringsspråken ALMIR-65MIR-1- datorn och ANALYTIKMIR-2- datorn . För att arbeta med stora siffror finns det i moderna programmeringsspråk en hel del färdiga optimerade bibliotek för lång aritmetik.

De flesta funktionella språk låter dig byta från vanlig aritmetik till lång aritmetik utan att behöva ändra den aritmetiska koden. Till exempel representerar Erlang och Schema alltid exakta siffror så långa. I Standard ML bestäms implementeringar av alla varianter av heltal baserat på signaturen INTEGER, vilket gör att du kan välja önskad dimension, inklusive en modul IntInfsom implementerar heltal med godtycklig precision; PolyML-implementeringen använder denna modul som standard.

Det finns inbyggda bibliotek för att arbeta med stora siffror i PascalABC.NET, Ruby , Python och Java .

Algoritmer

Multiplikationsalgoritmer

Följande representation av heltal används vanligtvis för att beskriva algoritmer. Basen är vald . Sedan kan längdheltalet representeras som [1] :

var

Grundläggande

Det är en algoritm enligt skolmetoden "i en kolumn". Det tar tid var  är storleken på de multiplicerade talen.

Algoritmen kan representeras som [1] [2] :

Algoritm 1 BasecaseMultiply
Input: Output: för från att göra




Multiplikation av Karatsuba

Karatsubas multiplikationsmetod tillhör paradigmet " dela och erövra ". Algoritmens beräkningskomplexitet :

.

Denna algoritm är en enkel implementering [3] av idén om att dela upp indata, som har blivit grunden för algoritmerna som listas nedan. Tanken är att dela upp en multiplikationsoperation på siffriga tal i tre multiplikationsoperationer på tal med längd plus [1] .

För att multiplicera två tal större än ett maskinord, kallas Karatsubas algoritm rekursivt tills talen är tillräckligt små för att kunna multipliceras direkt. Ett exempel på en sådan algoritm:

Algoritm 2 KaratsubaMultiply
Input: Output: KaratsubaMultiply KaratsubaMultiply KaratsubaMultiply







Låt oss räkna :

Tre mellanliggande koefficienter måste beräknas:

Resultat:

Toomas algoritm

Denna algoritm är en generalisering av Karatsuba-algoritmen och är snabbare. Med tanke på två heltal och , delar Tooms algoritm upp dem i mindre delar, som var och en är lika med längden på ett maskinord, och utför operationer på dessa delar. Beräkningskomplexitet för algoritmen:

Tooma-3 algoritm

Idén föreslogs först av A. L. Toom 1963 [4] , och består i att dela in indata (multiplikatorer) i 3 lika delar (för enkelhetens skull anses alla delar vara lika). Toom-3 minskar antalet elementära multiplikationsoperationer från 9 till 5. Algoritmkomplexitet

Betrakta denna algoritm i följande exempel. Låt det vara två siffror och . Låt operationer definieras på tal vars storlek är lika med 1/3 av storleken på de ursprungliga talen (se figur). Vi antar också att talen upptar lika mycket minne och är delbara med exakt 3 delar, annars fyller vi båda talen med nollor till önskad storlek.

Sedan sker en mappning (parametrisering) av dessa delar till polynom av 2:a graden.

Låt oss introducera , per definition, så att polynomens värden är lika med ingångstalen respektive . För en bitvis representation av siffror är detta nummer två i potens lika med längden av varje del i bitar.

Vi introducerar också ett polynom:

(ett)

Efter att elementen har bestämts  - koefficienterna för polynomet , kommer de att användas för att erhålla , eftersom . Storleken på koefficienterna är 2 gånger större (från minnet) än partitionen eller . Det slutliga numret som är lika med produkten kan hittas genom att lägga till med ett skift, som visas i figuren nedan.

Koefficienterna kan beräknas enligt följande: och så vidare, men detta kommer att kräva alla 9 multiplikationer: för i, j=0,1,2, och kommer att vara ekvivalent med en enkel multiplikation.

Istället togs ett annat grepp. beräknas i (1) till 5 poäng för olika .

Tabellen nedan visar värdena för polynomen i ekvation (1)

Parametern är villkorad. Det betyder den banala likheten av koefficienterna vid , så vi kommer att få värdet omedelbart. Detta system är linjärt i 5 okända. När det är löst får vi okända . Därefter får vi värdet på polynomet, som beskrivits ovan.

Tooma-4 algoritm

Algoritmens komplexitet representerar 7 elementära multiplikationsoperationer. Toom-4 delar upp ingången i 4 delar.

Enligt samma princip som i Toom-3 bygger vi två polynom:

och beräknas vid 7 olika punkter, beräknas även värdet på dessa punkter.

varifrån vi omedelbart kommer
varifrån vi omedelbart kommer

Antalet additions- och multiplikationsoperationer för Toom-4 är mycket större än för Toom-3. Men vissa uttryck förekommer mer än en gång. Till exempel beräknat för och för [5] .

Tooms algoritm för en godtycklig partition

Tooms algoritm för att dela in ingångsnummer i n operander är likvärdig med den som beskrivs ovan. Generellt sett resulterar en uppdelning av två lika långa operander i delar i beräkningen av punktvärden . Som poäng för att lösa systemet tar de vanligtvis .

Fouriermultiplikation

Denna multiplikationsalgoritm används för stora och mycket stora tal [6] .

Denna algoritm multiplicerar två tal i tiden där  är antalet signifikanta siffror i de multiplicerade talen (förutsatt att de är lika). Skapelsen tillskrivs Cooley (Coolet) och Tyuki (Tukey) - 1965. Det finns också förslag på att denna algoritm var känd tidigare, men inte var av stor betydelse innan de första datorerna uppfanns. Troliga kandidater för författarskapet till uppfinningen av denna algoritm kallas också Runge (Runge) och Koenig (Konig) - 1924, såväl som Gauss - 1805.

Låt det finnas ett tal, vi representerar det som ett polynom, som vi gjorde tidigare. Låt oss kalla detta polynom Vi introducerar också den diskreta Fouriertransformen av polynomet som en vektor , med koordinater . Där definieras som  - den komplexa roten av den e graden av 1, inte lika med 1. Faktum är att den komplexa roten av 1 definieras upp till en fasfaktor, antalet av dessa rötter är . Fouriertransformen tillämpas för att ersätta faltningen av polynomens koefficienter och :  - med produkten av deras Fourierbilder.

där multiplikation betyder skalärprodukten av vektorer.

Anta att det finns en tvåpotens.

Att hitta görs rekursivt (dela och härska). Tanken är att dela upp det ursprungliga polynomet i två polynom,

Sedan .

Observera att bland alla nummer , bara olika. Därför kommer DFT att vara -element. Och eftersom DFT består av element, kommer den komplexa roten av 1 att vara roten till graden .

Betyder att,

var och

Vi använde egenskaperna hos komplexa tal: olika rötter av graden av allt . .

Vi får en rekursiv algoritm:
DFT för ett element är lika med detta element
för att hitta DFT A, vi delar upp koefficienterna A i jämna och udda, vi får två polynom och , vi hittar DFT för dem, vi hittar DFT : för . Det finns bevis för följande påstående: Den inversa DFT hittas på samma sätt som den direkta DFT, förutom att punkterna tas som punkter som är symmetriska kring den reella axeln, istället för de som används i den direkta DFT-transformationen. Det är också nödvändigt att dividera alla koefficienter för polynomet med n



Rotextraktionsalgoritmer

Kvadratrot

En av kvadratrotsalgoritmerna är Karatsuba Square Root-algoritmen. Detta är den i särklass mest kända metoden för att beräkna kvadratroten ur ett n -siffrigt tal. Denna algoritm använder den snabba Fouriertransformen och Newtons metod med komplexitet 5 M ( n ) [7] .

Den presenterade algoritmen är baserad på uppdelningen av Burnickel-Ziegler (Burnikel-Ziegler) Karatsuba. Givet ett heltal n , beräknar algoritmen samtidigt sin heltalskvadratrot och motsvarande återstod, vilket är Detta är inte asymptotiskt optimalt, men mycket effektivt i praktiken med operationsordningskomplexitet, där K ( n ) är antalet operationer som krävs för att multiplicera två n -bitars nummer med hjälp av Karatsuba-algoritmen. Anledningen till denna låga komplexitet är den vackra Karatsuba-divisionen som nyligen upptäckts av Burnickel och Ziegler, och den noggranna hanteringen av rester som undviker onödiga beräkningar.

Teorem . Antalet operationer som SqrtRem-algoritmen använder med en 2n -bitars ingång är begränsat

där K ( n ) är antalet operationer som krävs för att multiplicera 2 n -bitars tal med hjälp av Karatsubas algoritm.

Algoritm SqrtRem Input: med Output: sådan att om sedan returnera

Algoritmer för att konvertera talsystemet

Antag att du konverterar från bas b till bas B [8] .

Sätt att konvertera heltal


Metod 1 (Division med B med bas b representation av tal). För ett givet heltal u kan man
få en representation i bas B-format av formen genom att göra

, , , tills .


Metod 2 (Multiplikation med B med bas b-representation). Om representationen av talet u i bas b har formen , då med aritmetiska operationer med tal som representeras i formatet i bas B, kan du få ett polynom i formen (( .


Metod 1 (a) (Multiplikation med b med bas B-representation av tal). För ett givet bråktal och du kan beräkna värdena för siffrorna i dess representation i bas B enligt följande: , , ,... där {x} betyder xmod1 = x- . För att avrunda resultatet till M siffror kan beräkningen avbrytas efter att ha tagits emot , och om {...{{uВ}В}...В} är större än 1/2, så bör värdet ökas med ett. (Observera dock att denna operation kan leda till behovet av att utföra översättningar, vilket bör inkluderas i resultatet med aritmetiska operationer i bas B. Det skulle vara lättare att lägga till en konstant till det ursprungliga talet u innan beräkningarna påbörjas , men detta kan leda till ett felaktigt resultat, om talet i en dator inte kan representeras exakt i bas b-format Observera också att det är möjligt att avrunda resultatet till if ). Metod 2 (a) (Multiplikation med B med bas b-representation). Om representationen av ett tal och i bas b har formen , då med aritmetiska operationer med tal som presenteras i formatet i bas B, kan du få ett polynom i formen ((… + …) + .


Sätt att konvertera bråktal


Metod 1 (b) (Multiplikation med b med bas B-representation av tal). För ett givet bråktal u kan du beräkna värdena för bitarna i dess representation i bas B enligt följande: , , ,... där {x} betyder xmod1 = x- . För att avrunda resultatet till M siffror kan beräkningen avbrytas efter att ha tagits emot , och om {...{{uВ}В}...В} är större än 1/2, så bör värdet ökas med ett. (Observera dock att denna operation kan leda till behovet av att utföra översättningar, vilket bör inkluderas i resultatet med aritmetiska operationer i bas B. Det skulle vara lättare att lägga till en konstant till det ursprungliga talet u innan beräkningarna påbörjas , men detta kan leda till ett felaktigt resultat, om talet i en dator inte kan representeras exakt i bas b-format Observera också att det är möjligt att avrunda resultatet till if ).


Metod 2 (b) (Division med b med bas B-representation av tal). Om talet u representeras i basen b som , då med aritmetiska operationer i basen B, kan det beräknas som . Det är nödvändigt att noggrant övervaka de fel som uppstår vid trunkering eller avrundning under divisionsoperationen med b; de är vanligtvis obetydliga, men så är inte alltid fallet.

Multiple Precision Transformation


Det är mest bekvämt att börja konvertera mycket långa tal genom att konvertera block av bitar, operationer som kan utföras med enkel precision. Du kombinerar sedan dessa block med enkla metoder som är specifika för multipel precision. Låt till exempel 10n vara den högsta potensen av 10 mindre än maskinordstorleken. Sedan:
a) för att konvertera ett heltal "Tal med multipel precision från binärt till decimalt, är det nödvändigt att multiplicera det med 10n (därmed konvertera från binärt till decimalt med basen 10n med hjälp av metod 1, a); använda operationer med en enda precision, vi får n decimaler för varje representationsenhet i basen 10n;
b) för att omvandla bråktalet "Del av ett tal med flera precision från binärt till decimalt, fortsätt på liknande sätt genom att multiplicera det med : (dvs. med metod 2, a, där B \u003d 10n); c) för att konvertera ett heltal med multipel precision från decimal till binär, konverterar vi först block med n bitar; använd sedan metod 1, b för att konvertera från bas 10n till binär; d) För att konvertera en bråkdel med multipel precision från decimal till binär, konvertera först till bas 10n som i procedur (c) och använd sedan metod 2, b.

Divisionsalgoritmer

Algoritmen för att dividera ett n-bitars tal u med ett n-bitars tal v måste resultera i två n-bitars tal - u mod v och u div v. Algoritmerna som beskrivs nedan är inte tillämpliga i praktiken, eftersom de hittar ett reellt tal, och inte två n-bitars tal, resultatet av division.

I teorin, för att dividera ett n-bitars tal u med ett n-bitars tal v, kan du först hitta en n-bitars approximation till talet 1/v, sedan multiplicera det med u, vilket ger en approximation till , och slutligen utför ytterligare en multiplikation för att göra en liten korrigering för att se till att ojämlikheten håller . Baserat på det föregående räcker det att ha en effektiv algoritm som skulle bilda, från ett givet n-bitars tal, ett ungefärligt värde på talet som är inversen av ett n-bitars tal. Använd sedan algoritmen för att multiplicera n-bitars tal. [9]


Algoritm R (Erhålla den reciproka med hög precision) Låt talet v har en binär representation , där . Denna algoritm beräknar en approximation z av talet så att . R1 (Initial gissning) Tilldela och . R2 (Newton Iteration) Här har vi talet z i binär form med tecken efter delningspunkten och . Beräkna exakt med det snabba multiplikationsprogrammet . Efter det beräkna exakt var . Sedan tilldela , där , som uppfyller olikheten , läggs till vid behov för att avrunda så att det är en multipel av . Och slutligen tilldela . R3 Om , gå tillbaka till steg R2; annars avslutas exekveringen av algoritmen.



Andra algoritmer

Anteckningar

  1. 1 2 3 Richard P. Brent och Paul Zimmermann, Modern datoraritmetik
  2. Donald E. Knuth "Konsten att programmera", avsnitt 4.3.1
  3. Donald E. Knuth "Konsten att programmera", avsnitt 4.3.3, del A
  4. Rapporter från USSRs vetenskapsakademi 150 (1963), 496-498
  5. Toom 4-vägs multiplikation - GNU MP 5.1.3 . Hämtad 13 december 2013. Arkiverad från originalet 14 mars 2013.
  6. Donald E. Knuth "Konsten att programmera", avsnitt 4.3.3, del C
  7. Paul Zimmermann. Karatsuba kvadratrot. [Forskningsrapport] RR-3805, 1999, s.8. < inria-00072854 Arkiverad 2 december 2014 på Wayback Machine >
  8. Donald E. Knuth "Konsten att programmera datorer", volym 2, avsnitt 4.4
  9. Donald E. Knuth "Konsten att programmera datorer", volym 2, avsnitt 4.3.3

Litteratur

  • Donald E. Knuth, " The Art of Computer Programming ", volym 2, "Seminumerical Algorithms", 3:e upplagan, Addison-Wesley, 1998
  • Dan Zuras, "On Squaring and Multiplying Large Integers", ARITH-11: IEEE Symposium on Computer Arithmetic, 1993, s. 260 till 271.
  • DAN SSSR 150 (1963), 496-498
  • Richard P. Brent och Paul Zimmermann, Modern datoraritmetik
  • Elektroniska medel och kontrollsystem: Proceedings of the reports of the International Scientific and Practical Conference (13-16 oktober 2010). - Tomsk: V-Spectrum, 2011: Vid 2 timmar - Del 2.  - 178 sid. ISBN 978-5-91191-223-6 , s.123-129