เนื่องจากการดำเนินการโมดูลัสจำนวนเต็มเป็นวงแหวนโฮโมมอร์ฟิซึม ( Wikipedia ) จากℤ -> ℤ / nℤ,
(X * Y) mod N = (X mod N) * (Y mod N) mod N
คุณสามารถยืนยันตัวเองด้วยพีชคณิตแบบง่าย ๆ (โปรดทราบว่าสุดท้ายmod
ที่ด้านขวามือจะปรากฏขึ้นเนื่องจากคำจำกัดความของการคูณในวงแหวนแบบแยกส่วน)
คอมพิวเตอร์ใช้เคล็ดลับนี้เพื่อคำนวณเลขยกกำลังในวงแหวนแบบแยกส่วนโดยไม่ต้องคำนวณตัวเลขจำนวนมาก
/ 1 I = 0,
|
(X ^ I) mod N = <(X * (X ^ (I-1) mod N)) mod NI คี่
|
\ (X ^ (I / 2) mod N) ^ 2 mod NI แม้ & I / = 0
ในรูปแบบอัลกอริทึม
-- compute X^I mod N
function expmod(X, I, N)
if I is zero
return 1
elif I is odd
return (expmod(X, I-1, N) * X) mod N
else
Y <- expmod(X, I/2, N)
return (Y*Y) mod N
end if
end function
คุณสามารถใช้สิ่งนี้เพื่อคำนวณ(855^2753) mod 3233
ด้วยการลงทะเบียนแบบ 16 บิตเท่านั้นหากคุณต้องการ
อย่างไรก็ตามค่าของ X และ N ใน RSA นั้นใหญ่กว่ามากเกินกว่าที่จะพอดีกับรีจิสเตอร์ โดยทั่วไปโมดูลัสจะยาว 1024-4096 บิต! คุณสามารถให้คอมพิวเตอร์ทำการคูณด้วยวิธี "ยาว" เช่นเดียวกับที่เราคูณด้วยมือ เฉพาะการใช้ตัวเลข 0-9 เท่านั้นคอมพิวเตอร์จะใช้ "คำ" 0-2 16 -1 หรืออะไรทำนองนั้น (การใช้เพียง 16 บิตหมายความว่าเราสามารถคูณตัวเลข 16 บิตสองตัวและรับผลลัพธ์เต็ม 32 บิตโดยไม่ต้องใช้ภาษาแอสเซมบลีในภาษาแอสเซมบลีมักจะง่ายมากที่จะได้ผลลัพธ์เต็ม 64 บิตหรือสำหรับคอมพิวเตอร์ 64 บิต ผลลัพธ์เต็ม 128 บิต)
-- Multiply two bigints by each other
function mul(uint16 X[N], uint16 Y[N]):
Z <- new array uint16[N*2]
for I in 1..N
-- C is the "carry"
C <- 0
-- Add Y[1..N] * X[I] to Z
for J in 1..N
T <- X[I] * Y[J] + C + Z[I + J - 1]
Z[I + J - 1] <- T & 0xffff
C <- T >> 16
end
-- Keep adding the "carry"
for J in (I+N)..(N*2)
T <- C + Z[J]
Z[J] <- T & 0xffff
C <- T >> 16
end
end
return Z
end
-- footnote: I wrote this off the top of my head
-- so, who knows what kind of errors it might have
สิ่งนี้จะทวีคูณ X ด้วย Y ในระยะเวลาเท่ากับจำนวนคำใน X คูณด้วยจำนวนคำใน Y ซึ่งเรียกว่าเวลา O (N 2 ) หากคุณดูอัลกอริทึมด้านบนแล้วแยกมันเป็น "การคูณแบบยาว" ที่พวกเขาสอนในโรงเรียน คุณไม่มีตารางเวลาที่จำได้ถึง 10 หลัก แต่คุณยังสามารถคูณ 1,926,348 x 8,192,004 ถ้าคุณนั่งลงและทำงานออกมา
การคูณยาว:
1,234
x 5,678
---------
9,872
86,38
740,4
6,170
---------
7,006,652
จริงๆแล้วมีบางอัลกอริทึมที่เร็วกว่าสำหรับการคูณ ( Wikipedia ) เช่นวิธี Fourier ที่รวดเร็วของ Strassen และวิธีที่ง่ายกว่าที่จะทำการบวกและการลบเพิ่มเติม แต่การคูณน้อยลงและจบลงโดยรวมเร็วขึ้น ห้องสมุดเชิงตัวเลขเช่น GMP มีความสามารถในการเลือกอัลกอริทึมที่แตกต่างกันตามจำนวนที่มีขนาดใหญ่: การแปลงฟูริเยร์เป็นเพียงเร็วที่สุดสำหรับหมายเลขที่ใหญ่ที่สุด