חילוק מודולרי

מתוך המכלול, האנציקלופדיה היהודית
גרסה מ־13:28, 18 בנובמבר 2019 מאת יהודה שמחה ולדמן (שיחה | תרומות) (הגהה, שיפוץ קודים מתמטיים)
קפיצה לניווט קפיצה לחיפוש

חילוק מודולרי הוא פעולת חילוק המתבצעת בין מספרים שלמים בחשבון מודולרי.

בהינתן שני מספרים שלמים ומודולוס , תוצאת החילוק המודולרי של ב־ היא מספר המקיים:

למשל

כי

קיום ויחידות

בניגוד לשלוש פעולות החשבון האחרות, תוצאת החילוק המודולרי לא תמיד קיימת. למשל, המספר אינו קיים, כי אין שלם עבורו .

תנאי הכרחי ומספיק לכך שהתוצאה תתקיים היא, שהמ.מ.ג.ב מחלק את .

בדוגמה למעלה, המ.מ.ג.ב של 8 ו־2 הוא 2, והמחולק 1 אינו מתחלק ב־2, ולכן תוצאת החילוק אינה קיימת.


בניגוד לשלוש פעולות החשבון האחרות, תוצאת החילוק המודולרי אינה בהכרח יחידה. למשל:

כי .

באופן כללי, אם אזי לכל מספר שלם

כי לכל מתקיים

תוצאת החילוק היא יחידה מודולו המספר .

חישוב

ניתן לחשב חילוק מודולרי על ידי חישוב הופכי כפלי מודולרי של המחלק , אם הוא קיים. בפרט, אם הוא ההופכי הכפלי המודולרי של מודולו , אז על־פי ההגדרה:

ומכאן

אולם, ישנם מקרים שבהם ההופכי הכפלי המודולרי אינו קיים – כאשר ל־ ישנו מחלק משותף גדול מ־1 (ראו הופכי כפלי מודולרי), ועדיין ניתן לבצע חילוק. לפיכך טוב יותר לבצע חילוק ישירות בעזרת אלגוריתם אוקלידס המורחב. אלגוריתם זה מוצא את המ.מ.ג.ב של שני מספרים נתונים, ובנוסף לכך מחשב שני מספרים המקיימים את המשוואה:

כאמור בסעיף הקודם, ניתן לבצע את החילוק אם ורק אם הוא כפולה שלמה של , כלומר כאשר קיים מספר שלם עבורו

במקרה זה ניתן להכפיל את המשוואה הקודמת ב־ ולקבל:

מכאן, על־פי הגדרת החשבון המודולרי:

ומכאן הוא תוצאת החילוק.

לפניכם מימוש מעשי של האלגוריתם בשפת C++:[1]

/**
 * Euclid's extended algorithm:
 * Given a,b, Find gcd,x,y that solve the equation:
 *  ax + by = gcd(a,b)
 * @see http://en.wikipedia.org/wiki/Modular_multiplicative_inverse#Computation
 */
void xgcd (int a, int b,
	int& gcd, int& x, int& y) {
	x=0, y=1; 
	int u=1, v=0, m, n, q, r;
	gcd = b;
	while (a!=0) {
		q=gcd/a; r=gcd%a;
		m=x-u*q; n=y-v*q;
		gcd=a; a=r; x=u; y=v; u=m; v=n;
	}
}


/**
 * Modular division:
 * @return integer z such that: z * B mod m == A.
 * If there is more than one (i.e. when gcd(B,m)>1) - returns the smallest such integer
 */
int divide (int A, int B, int m) {
	assert (0 <= A && A<m);
	assert (0 <= B && B<m);

	int gcd, x, y;
	xgcd (B, m, gcd, x, y);  // x B + y m = gcd(B,m)
	if (A%gcd == 0) {        
		int q = A / gcd;       // x q B + y q m = m gcd = A
		return ((x + m)*q) % (m/gcd);   // Return the smallest result possible
	} else {
		throw "no quotient";
	}
}

ראו גם

קישורים חיצוניים

הערות שוליים

  1. ^ מסתמך על מימוש בשפת פייתון בדף en:Modular multiplicative inverse.