@@ -78,37 +78,41 @@ $3⁻¹\,mod\;11 = 3¹¹⁻²\,mod\;11=3⁹\,mod\;11=19683\,mod\;11=4$
7878
7979확장 유클리드 알고리즘(Extended Euclidean Algorithm)을 활용하여 모듈러 역원을 구할 수 있습니다.
8080
81- $a\times x+m\times y=gcd(a,m)$ 에서 <b >gcd가 1일 때(=a와 m이 서로소)</ b > 의 x 값이 a의 역원입니다 .
81+ $a\times x+m\times y=gcd(a,m)$ 에서 <b >gcd가 1일 때(=a와 m이 서로소)의 x 값이 a의 역원</ b >입니다 .
8282
8383$3x+11y=1$
8484
8585$x=-7,\, y=2$
8686
87+ $x=4,\, y=-1$
88+
8789$(-7)\, mod\; 11=4\, mod\; 11=4$
8890
8991``` javascript
90- const modInverse = (a , m ) => {
91- if (m === 1 ) {
92- return 0 ;
93- }
92+ const extendedGCD = (a , b ) => {
93+ if (b === 0 ) {
94+ return { gcd: a, x: 1 , y: 0 };
95+ } else {
96+ const { gcd , x: x1 , y: y1 } = extendedGCD (b, a % b);
9497
95- const m0 = m;
96- let x0 = 0 ;
97- let x1 = 1 ;
98+ const x = y1;
99+ const y = x1 - Math .floor (a / b) * y1;
98100
99- while (a > 1 ) {
100- const q = Math .floor (a / m);
101- [a, m] = [m, a % m];
102- [x0, x1] = [x1 - q * x0, x0];
101+ return { gcd, x, y };
103102 }
103+ };
104104
105- if (x1 < 0 ) {
106- x1 += m0;
105+ const modInverse = (a , m ) => {
106+ const { gcd , x } = extendedGCD (a, m);
107+
108+ // 모듈러 역원이 존재하지 않는 경우 -1 리턴.
109+ if (gcd !== 1 ) {
110+ return - 1 ;
107111 }
108- return x1;
109- };
110112
111- console .log (modInverse (3 , 11 )); // 4
113+ // 음수인 경우 양수로 조정.
114+ return ((x % m) + m) % m;
115+ };
112116```
113117
114118## Example
@@ -164,36 +168,32 @@ console.log(modInverse(3, 11)); // 4
164168 // 1 <= A < N
165169 const [N , A ] = input .split (" " ).map (Number );
166170
167- const gcd = (a , b ) => {
171+ const extendedGCD = (a , b ) => {
168172 if (b === 0 ) {
169- return a ;
173+ return { gcd : a, x : 1 , y : 0 } ;
170174 } else {
171- return gcd (b, a % b);
175+ const { gcd , x: x1 , y: y1 } = extendedGCD (b, a % b);
176+
177+ const x = y1;
178+ const y = x1 - Math .floor (a / b) * y1;
179+
180+ return { gcd, x, y };
172181 }
173182 };
174183
175184 const modInverse = (a , m ) => {
176- if (m === 1 ) {
177- return 0 ;
178- }
179-
180- const m0 = m;
181- let x0 = 0 ;
182- let x1 = 1 ;
185+ const { gcd , x } = extendedGCD (a, m);
183186
184- while (a > 1 ) {
185- const q = Math .floor (a / m);
186- [a, m] = [m, a % m];
187- [x0, x1] = [x1 - q * x0, x0];
187+ // 모듈러 역원이 존재하지 않는 경우 -1 리턴.
188+ if (gcd !== 1 ) {
189+ return - 1 ;
188190 }
189191
190- if (x1 < 0 ) {
191- x1 += m0;
192- }
193- return x1;
192+ // 음수인 경우 양수로 조정.
193+ return ((x % m) + m) % m;
194194 };
195195
196- console .log (N - A , gcd (A , N ) === 1 ? modInverse (A , N ) : - 1 );
196+ console .log (N - A , extendedGCD (A , N ). gcd === 1 ? modInverse (A , N ) : - 1 );
197197 ```
198198
199199## 참고 자료
0 commit comments