เรารู้ว่าตัวอย่างโมดูโลของกำลังสองสามารถแสดงได้ดังนี้:
x % 2 inpower n == x & (2 inpower n - 1).
ตัวอย่าง:
x % 2 == x & 1
x % 4 == x & 3
x % 8 == x & 7
แล้ว nonpower ทั่วไปของสองจำนวนล่ะ?
สมมติว่า:
x% 7 ==?
เรารู้ว่าตัวอย่างโมดูโลของกำลังสองสามารถแสดงได้ดังนี้:
x % 2 inpower n == x & (2 inpower n - 1).
ตัวอย่าง:
x % 2 == x & 1
x % 4 == x & 3
x % 8 == x & 7
แล้ว nonpower ทั่วไปของสองจำนวนล่ะ?
สมมติว่า:
x% 7 ==?
คำตอบ:
ก่อนอื่นการพูดแบบนั้นไม่ถูกต้อง
x % 2 == x & 1
ตัวอย่างง่ายๆตัวอย่าง: x = -1
. -1 % 2 == -1
ในหลายภาษารวมทั้งภาษาจาวา นั่นคือ%
ไม่จำเป็นต้องเป็นคำจำกัดความทางคณิตศาสตร์แบบดั้งเดิมของโมดูโล Java เรียกมันว่า "ตัวดำเนินการที่เหลือ" เช่น
เกี่ยวกับการเพิ่มประสิทธิภาพระดับบิตมีเพียงพาวเวอร์โมดูโลสองตัวเท่านั้นที่สามารถ "ทำได้อย่างง่ายดาย" ในการคำนวณทางคณิตศาสตร์ระดับบิต โดยทั่วไปมีเพียงพลังโมดูโลของฐานbเท่านั้นที่สามารถ "ทำได้อย่างง่ายดาย" ด้วยการแทนค่าฐานb
ในฐานที่ 10 ตัวอย่างเช่นสำหรับที่ไม่ใช่เชิงลบN
, N mod 10^k
เป็นเพียงการอย่างมีนัยสำคัญน้อยกว่าk
ตัวเลข
-1 = -1 (mod 2)
ไม่แน่ใจว่าคุณได้อะไร - คุณหมายความว่ามันไม่เหมือนกับส่วนที่เหลือของ IEEE 754 ใช่หรือไม่
(a / b) / b + a % b == a
สำหรับตัวดำเนินการประเภท C จำนวนเต็ม a และ b, b ไม่ใช่ศูนย์และabs(a % b) < abs(b)
ด้วยเงื่อนไขเดียวกัน
(a / b)
b + a % b == a
สิ่งนี้ใช้ได้เฉพาะกับพาวเวอร์สองตัว (และมักจะเป็นค่าบวกเท่านั้น) เนื่องจากมีคุณสมบัติเฉพาะในการตั้งค่าเป็น '1' เพียงบิตเดียวในการแทนค่าไบนารี เนื่องจากไม่มีคลาสของตัวเลขอื่นที่ใช้คุณสมบัตินี้คุณจึงไม่สามารถสร้างบิตและนิพจน์สำหรับนิพจน์โมดูลัสส่วนใหญ่ได้
นี่เป็นกรณีพิเศษโดยเฉพาะเนื่องจากคอมพิวเตอร์เป็นตัวแทนของตัวเลขในฐาน 2 ซึ่งเป็นลักษณะทั่วไป:
(ตัวเลข) ฐาน % ฐานx
จะเทียบเท่ากับหลักสุดท้ายของ x (จำนวน) ฐาน
มีโมดูลอื่นที่ไม่ใช่พาวเวอร์ของ 2 ซึ่งมีอัลกอริทึมที่มีประสิทธิภาพอยู่
ตัวอย่างเช่นถ้า x เป็น 32 บิต int ที่ไม่ได้ลงนามแล้ว x% 3 = popcnt (x & 0x55555555) - popcnt (x & 0xaaaaaaaa)
Modulo "7" ที่ไม่มีตัวดำเนินการ "%"
int a = x % 7;
int a = (x + x / 7) & 7;
ไม่ใช้ bitwise-and (&
) ในไบนารีจะไม่มี ร่างหลักฐาน:
สมมติว่ามีค่าkดังกล่าวว่าx & k == x % (k + 1)
แต่k = 2 ^ n - 1 แล้วถ้าx == kแสดงออกx & k
ดูเหมือนว่าจะ "ทำงานอย่างถูกต้อง" และผลที่ได้คือk ตอนนี้พิจารณาx == ki : ถ้ามีคนใด "0" บิตในk , มีบางฉันมากกว่า 0 ซึ่งkiอาจจะแสดงออกด้วย 1 บิตในตำแหน่งนั้น (เช่น 1011 (11) ต้องกลายเป็น 0111 (7) เมื่อลบ 100 (4) ออกจากมันในกรณีนี้ 000 บิตจะกลายเป็น 100 เมื่อi = 4 ) ถ้าบิตจากนิพจน์ของkต้องเปลี่ยนจากศูนย์ หนึ่งเพื่อแสดงถึงkiดังนั้นจึงไม่สามารถคำนวณx% (k + 1)ได้อย่างถูกต้องซึ่งในกรณีนี้ควรเป็นkiแต่ไม่มีวิธีใดสำหรับบูลีนระดับบิตและสร้างค่านั้นตามมาสก์
ในกรณีเฉพาะนี้ (mod 7) เรายังคงสามารถแทนที่% 7 ด้วยตัวดำเนินการแบบบิต:
// Return X%7 for X >= 0.
int mod7(int x)
{
while (x > 7) x = (x&7) + (x>>3);
return (x == 7)?0:x;
}
มันใช้งานได้เพราะ 8% 7 = 1 เห็นได้ชัดว่าโค้ดนี้น่าจะมีประสิทธิภาพน้อยกว่า x% 7 ธรรมดาและอ่านได้น้อยกว่า
การใช้ bitwise_and, bitwise_or และ bitwise_not คุณสามารถแก้ไขการกำหนดค่าบิตใด ๆ เป็นการกำหนดค่าบิตอื่นได้ (กล่าวคือชุดของตัวดำเนินการเหล่านี้ "เสร็จสมบูรณ์ตามหน้าที่") อย่างไรก็ตามสำหรับการดำเนินการเช่นโมดูลัสสูตรทั่วไปจะต้องค่อนข้างซับซ้อนฉันไม่ต้องกังวลกับการพยายามสร้างมันขึ้นมาใหม่