Skip to content

Commit 447e02d

Browse files
goswami-rahulHai Hoang Dang
authored andcommitted
added exponential and some refactors to maths/ (keon#361)
* added maths/modular_exponential.py and tests * cleared the requirements.txt * refactor math/factorial * refactor prime_check and sieve * added test_requirements.txt for travis
1 parent 6ad74b6 commit 447e02d

18 files changed

Lines changed: 155 additions & 115 deletions

.travis.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ matrix:
1212
- python: 3.6
1313
env: TOX_ENV=py36
1414
install:
15-
- pip install -r requirements.txt
15+
- pip install -r test_requirements.txt
1616
before_script:
1717
# stop the build if there are Python syntax errors or undefined names
1818
- flake8 . --count --select=E901,E999,F821,F822,F823 --show-source --statistics

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,7 @@ If you want to uninstall algorithms, it is as simple as:
187187
- [gcd/lcm](algorithms/maths/gcd.py)
188188
- [generate_strobogrammtic](algorithms/maths/generate_strobogrammtic.py)
189189
- [is_strobogrammatic](algorithms/maths/is_strobogrammatic.py)
190+
- [modular_exponential](algorithms/maths/modular_exponential.py)
190191
- [next_bigger](algorithms/maths/next_bigger.py)
191192
- [next_perfect_square](algorithms/maths/next_perfect_square.py)
192193
- [nth_digit](algorithms/maths/nth_digit.py)

README_CN.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -183,6 +183,7 @@ pip3 uninstall -y algorithms
183183
- [primes_sieve_of_eratosthenes:埃拉托色尼的质数筛](algorithms/maths/primes_sieve_of_eratosthenes.py)
184184
- [generate_strobogrammtic:生成对称数](algorithms/maths/generate_strobogrammtic.py)
185185
- [is_strobogrammatic:判断对称数](algorithms/maths/is_strobogrammatic.py)
186+
- [modular_exponential](algorithms/maths/modular_exponential.py)
186187
- [nth_digit:第n位](algorithms/maths/nth_digit.py)
187188
- [rabin_miller:米勒-拉宾素性检验](algorithms/maths/rabin_miller.py)
188189
- [rsa:rsa加密](algorithms/maths/rsa.py)

README_GE.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -193,6 +193,7 @@ Um das Projekt zu deinstallieren tippen Sie folgendes:
193193
- [gcd/lcm](algorithms/maths/gcd.py)
194194
- [generate_strobogrammtic](algorithms/maths/generate_strobogrammtic.py)
195195
- [is_strobogrammatic](algorithms/maths/is_strobogrammatic.py)
196+
- [modular_exponential](algorithms/maths/modular_exponential.py)
196197
- [next_bigger](algorithms/maths/next_bigger.py)
197198
- [next_perfect_square](algorithms/maths/next_perfect_square.py)
198199
- [nth_digit](algorithms/maths/nth_digit.py)

README_JP.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,7 @@ if __name__ == "__main__":
187187
- [gcd/lcm](algorithms/maths/gcd.py)
188188
- [generate_strobogrammtic](algorithms/maths/generate_strobogrammtic.py)
189189
- [is_strobogrammatic](algorithms/maths/is_strobogrammatic.py)
190+
- [modular_exponential](algorithms/maths/modular_exponential.py)
190191
- [next_bigger](algorithms/maths/next_bigger.py)
191192
- [next_perfect_square](algorithms/maths/next_perfect_square.py)
192193
- [nth_digit](algorithms/maths/nth_digit.py)

README_KR.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -184,6 +184,7 @@ if __name__ == "__main__":
184184
- [gcd/lcm](algorithms/maths/gcd.py)
185185
- [generate_strobogrammtic](algorithms/maths/generate_strobogrammtic.py)
186186
- [is_strobogrammatic](algorithms/maths/is_strobogrammatic.py)
187+
- [modular_exponential](algorithms/maths/modular_exponential.py)
187188
- [next_bigger](algorithms/maths/next_bigger.py)
188189
- [next_perfect_square](algorithms/maths/next_perfect_square.py)
189190
- [nth_digit](algorithms/maths/nth_digit.py)

algorithms/maths/__init__.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
from .gcd import *
66
from .generate_strobogrammtic import *
77
from .is_strobogrammatic import *
8+
from .modular_exponential import *
89
from .next_perfect_square import *
910
from .prime_check import *
1011
from .primes_sieve_of_eratosthenes import *

algorithms/maths/extended_gcd.py

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,10 @@
1-
"""
2-
extended GCD algorithm
3-
return s,t,g
4-
such that a s + b t = GCD(a, b)
5-
and s and t are coprime
6-
"""
1+
def extended_gcd(a, b):
2+
"""Extended GCD algorithm.
3+
Return s, t, g
4+
such that a * s + b * t = GCD(a, b)
5+
and s and t are co-prime.
6+
"""
77

8-
def extended_gcd(a,b):
98
old_s, s = 1, 0
109
old_t, t = 0, 1
1110
old_r, r = a, b

algorithms/maths/factorial.py

Lines changed: 24 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,32 @@
1-
#
2-
# This function calculates n!
3-
# Factorial function not works in less than 0
4-
#
5-
6-
def factorial(n):
7-
1+
def factorial(n, mod=None):
2+
"""Calculates factorial iteratively.
3+
If mod is not None, then return (n! % mod)
4+
Time Complexity - O(n)"""
5+
if not (isinstance(n, int) and n >= 0):
6+
raise ValueError("'n' must be a non-negative integer.")
7+
if mod is not None and not (isinstance(mod, int) and mod > 0):
8+
raise ValueError("'mod' must be a positive integer")
89
result = 1
10+
if n == 0:
11+
return 1
912
for i in range(2, n+1):
1013
result *= i
11-
14+
if mod:
15+
result %= mod
1216
return result
1317

1418

15-
def factorial_recur(n):
19+
def factorial_recur(n, mod=None):
20+
"""Calculates factorial recursively.
21+
If mod is not None, then return (n! % mod)
22+
Time Complexity - O(n)"""
23+
if not (isinstance(n, int) and n >= 0):
24+
raise ValueError("'n' must be a non-negative integer.")
25+
if mod is not None and not (isinstance(mod, int) and mod > 0):
26+
raise ValueError("'mod' must be a positive integer")
1627
if n == 0:
1728
return 1
18-
19-
return n * factorial(n-1)
20-
29+
result = n * factorial(n - 1, mod)
30+
if mod:
31+
result %= mod
32+
return result
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
def modular_exponential(base, exponent, mod):
2+
"""Computes (base ^ exponent) % mod.
3+
Time complexity - O(log n)
4+
Use similar to Python in-built function pow."""
5+
if exponent < 0:
6+
raise ValueError("Exponent must be positive.")
7+
base %= mod
8+
result = 1
9+
10+
while exponent > 0:
11+
# If the last bit is 1, add 2^k.
12+
if exponent & 1:
13+
result = (result * base) % mod
14+
exponent = exponent >> 1
15+
# Utilize modular multiplication properties to combine the computed mod C values.
16+
base = (base * base) % mod
17+
18+
return result

0 commit comments

Comments
 (0)