ThinkChat🤖让你学习和工作更高效,注册即送10W Token,即刻开启你的AI之旅 广告
## 10.5 Computing Modular Powers ![](https://box.kancloud.cn/485bc67a7beadb016ac9d44f235f6e03_27x27.jpg) For an element \[*m*\]*n* ∊ **Z***n* and nonnegative integer *k*, the problem of computing ![](https://box.kancloud.cn/04db6718a6bfd3237514c21e9fbd62d6_60x28.jpg) is called the *problem of computing modular powers.* [Examples 10.43](LiB0083.html#1105) and [Examples 10.44](LiB0083.html#1106) showed the computation of some modular powers. Another example follows. Example 10.51**![Start example](https://box.kancloud.cn/e95df9d604ab2d89febe370ae4d88fb1_1x1.gif)**![](https://box.kancloud.cn/44c6e5b0628dc8a29323fbd49f3a833e_279x26.jpg) In [Example 10.51](#ch10ex89) we determined the power simply by taking 7 to the 11th power. Clearly, this method has exponential time complexity in terms of the input size (approximately the logarithms of the numbers). Next we develop a more efficient algorithm. **![End example](https://box.kancloud.cn/e95df9d604ab2d89febe370ae4d88fb1_1x1.gif)** The algorithm requires we represent *k* as a binary number. Let ![](https://box.kancloud.cn/ffd474fa55e3f1773acbea90e9f7b74c_159x22.jpg) be the ordered set of binary digits in that representation. For example, since the binary representation of 13 is 1101, if *k* = 13, ![](https://box.kancloud.cn/625b6e6c61cd7dd10042ae8f21aecc4b_215x22.jpg) The algorithm now follows. We say that the algorithm uses the method of ***repeated squaring.*** The reason is obvious. Algorithm 10.4 Compute Modular Power**![Start example](https://box.kancloud.cn/e95df9d604ab2d89febe370ae4d88fb1_1x1.gif)**Problem: For an element \[*m*\]*n* ∊ **Z**n and nonnegative integer *k*, compute (\[*m*\]*n*)*k.* **![End example](https://box.kancloud.cn/e95df9d604ab2d89febe370ae4d88fb1_1x1.gif)** Inputs: positive integer *n*, and nonnegative integers *m* and *k.* Outputs: (\[*m*\]*n*)*k.* ``` void compute_power (int n, int m, int k, Znmember& a) { index i; a = [1]n; {bj, bj-1, . . ., b1, b0} = ordered set of digits in binary representation of k; for (i = j; i >= 0; i - -) a = a2; if (bi = = 1) a = a×[m]n; } ``` Next we show an example of applying [Algorithm 10.4](#ch10ex90). Example 10.52**![Start example](https://box.kancloud.cn/e95df9d604ab2d89febe370ae4d88fb1_1x1.gif)**Suppose **![End example](https://box.kancloud.cn/e95df9d604ab2d89febe370ae4d88fb1_1x1.gif)** ![](https://box.kancloud.cn/a598d570a086488f2cff1142da7c2f9c_241x17.jpg) Since the binary representation of 45 is 101101, ![](https://box.kancloud.cn/034f6946c373f38a73483f8203adb1ed_297x22.jpg) [Table 10.2](#ch10table02) shows the state of *a* after each iteration of the **for**-*i* loop in [Algorithm 10.4](#ch10ex90) given this input. The final value of *a*, namely \[147\]257, is the value of (\[5\]257)45. Table 10.2: The state of *a* after each iteration of the for-*i* loop in [Algorithm 10.4](#ch10ex90) when *n* = 257, *m* = 5, and *k* = 45. The third row shows the value determined by the high-order *j* - *i* + 1 bits in the binary representation of *k.*i 5 4 3 2 1 0 bi 1 0 1 1 0 1 ki 1 2 5 11 22 45 a \[5\]257 \[25\]257 \[41\]257 \[181\]257 \[122\]257 \[147\]257 In [Table 10.2](#ch10table02), *ki* is the value determined by the high-order *j* - *i* + 1 bits in the binary representation of *k.* That is, ![](https://box.kancloud.cn/85f273eefa3ed81a43dd60cce7ef0060_159x24.jpg) For example, ![](https://box.kancloud.cn/1e5115692d2bc56e3a6cbb1768a7f299_221x23.jpg) Clearly, *k*0 = *k.* We will use these variables to prove the correctness of the algorithm, which we do next. Theorem 10.26**![Start example](https://box.kancloud.cn/e95df9d604ab2d89febe370ae4d88fb1_1x1.gif)**After each iteration of the **for**-*i* loop in [Algorithm 10.4](#ch10ex90), **![End example](https://box.kancloud.cn/e95df9d604ab2d89febe370ae4d88fb1_1x1.gif)** ![](https://box.kancloud.cn/17d72dce49ebe66b465efb5c93c4ad66_107x28.jpg) Since *k*0 = *k*, this means the final value of *a* is (\[*m*\]*n*)*k.* Proof: The proof is by induction. Induction base: We assume a minimal binary representation; so the high-order bit *bj* equals 1. Therefore, ![](https://box.kancloud.cn/04c6719a03bd2a740172f556959b724a_57x22.jpg) Before entering the **for**-*i* loop, *a* = \[1\]*n.* Since *bj* equals 1, the **if** condition is true in the first iteration, which means the instruction *a* = *a*×\[*m*\]*n* executes. Therefore, we have ![](https://box.kancloud.cn/c74a3f3eca938d48f4258fe9f8e99eb8_313x26.jpg) after the first iteration. Induction hypothesis: Suppose after the iteration with index value *i* that ![](https://box.kancloud.cn/9d4a835bf7eef6cf769b40e6f0c0cb33_107x27.jpg) Induction step: We need to show that, after the iteration with index value (*i* - 1), ![](https://box.kancloud.cn/4e0cdecb192644e0e8b2bf6e18409944_124x28.jpg) There are two cases: If *bi*-1 = 0, clearly ![](https://box.kancloud.cn/25649d453f1ca2bea7cedc6d4876c6af_90x20.jpg) Since the condition in the **if** statement is false, only the instruction *a* = *a*2 changes the value of *a.* Since by the induction hypothesis the previous value of *a* is (\[*m*\]*n*)*ki*, we have ![](https://box.kancloud.cn/cb32893a158fb63f7f68b7030343fc00_208x27.jpg) after this iteration. If *bi*-1 = 1, clearly ![](https://box.kancloud.cn/f95cccb94d50c13b0ab67e14bcf62595_119x20.jpg) Since the condition in the **if** statement is true, the instruction *a* = *a*×\[*m*\]*n* also executes. So in this case, ![](https://box.kancloud.cn/69e7b95bb444e25bfc6a4f24fad7660f_378x27.jpg) after this iteration. It is straightforward that, if we let *s* be the number of bits it take to encode the input, the time complexity of [Algorithm 10.4](#ch10ex90) is in *O*(*s*3).