3

The documentation about the pow(base, exp[, mod]) function says,
"If mod is present and exp is negative, base must be relatively prime to mod. In that case, pow(inv_base, -exp, mod) is returned, where inv_base is an inverse to base modulo mod."

I don't understand the line at all and also how it works. The provided example is as follows:

>>> pow(38, -1, mod=97) 23 >>> 23 * 38 % 97 == 1 True 

Shouldn't it behave like (38**-1)%97 = 0.02631578947368421 ?
If I try to go from 23 * 38 % 97 == 1 to backward, I don't know what's the inverse of modulo.

Can anyone kindly give me a clear explanation of how it ended being 23? A mathematical explanation will be highly helpful.

4
  • TypeError: pow() takes no keyword arguments is the error i get when i run it Commented Sep 8, 2020 at 21:16
  • @CoolCloud Try a later python. Commented Sep 8, 2020 at 21:16
  • @alani Yes found that out: Changed in version 3.8: Allow keyword arguments. Formerly, only positional arguments were supported. Commented Sep 8, 2020 at 21:17
  • 2
    You need at least Python 3.8 to run this. Commented Sep 8, 2020 at 21:20

3 Answers 3

3

In modular arithmetic division does not have a unique answer, so we do not have a division operation. Instead you have modular inverses.

The docs are trying to explain that pow(b, -1, mod=m) can be used to calculate the inverse of b, modulo m. That is, finding some number d such that d * b % m = 1.

The line 23 * 38 % 97 == 1 is simply demonstrating that the answer 23, which was the result of pow(38, -1, mod=97), is the correct modular inverse of 38.

The explanation in the docs seems to be assuming the reader already has some familiarity with modular arithmetic.

Can anyone kindly give me a clear explanation of how it ended being 23? A mathematical explanation will be highly helpful.

Try running this code snippet:

for i in range(97): s = f"{i} * 38 % 97" print(s, "==", eval(s)) 

Exactly one of the lines will reveal the congruence d * 38 % 97 == 1. There are, of course, smarter ways to compute the inverse but the brute force demonstration above should make it easier to understand what a modular inverse means.

Sign up to request clarification or add additional context in comments.

3 Comments

That helps! Just got to know about the topic. Still trying to understand how to calculate that d by hand.
@SMFahim I added a brute-force example code snippet which outlines a naive approach for calculating the same (it should also reveal why the base should be relatively prime to mod).
This method helps me understand better. Don't know if it's correct, but it's working with every example. I'm writing it in detail in a new reply to the question. Please tell me whether I'm right or wrong.
1

With integer arguments and mod specified, pow() does arithmetic in the "multiplicative group of integers modulo mod"

For example, the integers relatively prime to 8 (1, 3, 5, and 7) form a group under multiplication mod 8. The identity is 1. Since 3*3 = 9 is congruent to 1 modulo 8, 3 is its own inverse in this group, and

>>> pow(3, -1, 8) 3 

In the doc example, 23 and 38 are inverses modulo 97.

>>> pow(23, -1, 97) 38 >>> pow(38, -1, 97) 23 

This isn't particularly esoteric, but rather basic tools in number theory.

Comments

0

The answer from @wim and the example by @Tim Peters helps me understand what's going on in this pow() function. Let's take an example,

>>> pow(3, -1, 8) 3 

Modulo by a number m must be in the range(0,m). For example 14%5 must be in range(0,5), hence it's 4.

So modulo 1/3 % 8 must be in the range(8). But as 1/3=0.33 which is not in the range, we need a way around to find it.

1/3 % 8 cannot be zero, as it's not divisible. So the lowest possible value is 1. That means, we need to represent 1/3 in such a way that x % 8 == 1 becomes True. It's obvious that 9 % 8 == 1.
As 3(target value) * 3(base) = 9, hence, the answer is 3(target value).

For a complex example, let's take:

>>> pow(38, -1, mod=97) 23 

1/38=0.026. Again, need a way around. As the lowest mod should be 1, hence x % 97 == 1. Obviously 98 % 97 == 1, but 98/38 is not a whole number. Next, (2*97+1) or 195 % 97 == 1, but 195/38 is not a whole number.

In this process, (9*97+1) or 874 % 97 == 1 and 874/38=23. So the final expression becomes:

23 * 38 % 97 == 1 

Hence, the answer is 23.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.