Unify primality checking (#6228)

* renames prime functions and occurances in comments

* changes implementation of primality testing to be uniform

* adds static typing as per conventions

* updating DIRECTORY.md

Co-authored-by: github-actions <${GITHUB_ACTOR}@users.noreply.github.com>
This commit is contained in:
Nikos Giachoudis 2022-07-11 10:36:57 -04:00 committed by GitHub
parent dad789d903
commit f7c58e4c4b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 87 additions and 53 deletions

View File

@ -444,7 +444,6 @@
* [Scoring Functions](machine_learning/scoring_functions.py) * [Scoring Functions](machine_learning/scoring_functions.py)
* [Sequential Minimum Optimization](machine_learning/sequential_minimum_optimization.py) * [Sequential Minimum Optimization](machine_learning/sequential_minimum_optimization.py)
* [Similarity Search](machine_learning/similarity_search.py) * [Similarity Search](machine_learning/similarity_search.py)
* [Support Vector Machines](machine_learning/support_vector_machines.py)
* [Word Frequency Functions](machine_learning/word_frequency_functions.py) * [Word Frequency Functions](machine_learning/word_frequency_functions.py)
## Maths ## Maths

View File

@ -1,6 +1,6 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
from .hash_table import HashTable from .hash_table import HashTable
from .number_theory.prime_numbers import check_prime, next_prime from .number_theory.prime_numbers import is_prime, next_prime
class DoubleHash(HashTable): class DoubleHash(HashTable):
@ -15,7 +15,7 @@ class DoubleHash(HashTable):
next_prime_gt = ( next_prime_gt = (
next_prime(value % self.size_table) next_prime(value % self.size_table)
if not check_prime(value % self.size_table) if not is_prime(value % self.size_table)
else value % self.size_table else value % self.size_table
) # gt = bigger than ) # gt = bigger than
return next_prime_gt - (data % next_prime_gt) return next_prime_gt - (data % next_prime_gt)

View File

@ -3,25 +3,55 @@
module to operations with prime numbers module to operations with prime numbers
""" """
import math
def check_prime(number):
"""
it's not the best solution
"""
special_non_primes = [0, 1, 2]
if number in special_non_primes[:2]:
return 2
elif number == special_non_primes[-1]:
return 3
return all(number % i for i in range(2, number)) def is_prime(number: int) -> bool:
"""Checks to see if a number is a prime in O(sqrt(n)).
A number is prime if it has exactly two factors: 1 and itself.
>>> is_prime(0)
False
>>> is_prime(1)
False
>>> is_prime(2)
True
>>> is_prime(3)
True
>>> is_prime(27)
False
>>> is_prime(87)
False
>>> is_prime(563)
True
>>> is_prime(2999)
True
>>> is_prime(67483)
False
"""
# precondition
assert isinstance(number, int) and (
number >= 0
), "'number' must been an int and positive"
if 1 < number < 4:
# 2 and 3 are primes
return True
elif number < 2 or not number % 2:
# Negatives, 0, 1 and all even numbers are not primes
return False
odd_numbers = range(3, int(math.sqrt(number) + 1), 2)
return not any(not number % i for i in odd_numbers)
def next_prime(value, factor=1, **kwargs): def next_prime(value, factor=1, **kwargs):
value = factor * value value = factor * value
first_value_val = value first_value_val = value
while not check_prime(value): while not is_prime(value):
value += 1 if not ("desc" in kwargs.keys() and kwargs["desc"] is True) else -1 value += 1 if not ("desc" in kwargs.keys() and kwargs["desc"] is True) else -1
if value == first_value_val: if value == first_value_val:

View File

@ -4,31 +4,36 @@ import math
import unittest import unittest
def prime_check(number: int) -> bool: def is_prime(number: int) -> bool:
"""Checks to see if a number is a prime in O(sqrt(n)). """Checks to see if a number is a prime in O(sqrt(n)).
A number is prime if it has exactly two factors: 1 and itself. A number is prime if it has exactly two factors: 1 and itself.
>>> prime_check(0) >>> is_prime(0)
False False
>>> prime_check(1) >>> is_prime(1)
False False
>>> prime_check(2) >>> is_prime(2)
True True
>>> prime_check(3) >>> is_prime(3)
True True
>>> prime_check(27) >>> is_prime(27)
False False
>>> prime_check(87) >>> is_prime(87)
False False
>>> prime_check(563) >>> is_prime(563)
True True
>>> prime_check(2999) >>> is_prime(2999)
True True
>>> prime_check(67483) >>> is_prime(67483)
False False
""" """
# precondition
assert isinstance(number, int) and (
number >= 0
), "'number' must been an int and positive"
if 1 < number < 4: if 1 < number < 4:
# 2 and 3 are primes # 2 and 3 are primes
return True return True
@ -42,35 +47,35 @@ def prime_check(number: int) -> bool:
class Test(unittest.TestCase): class Test(unittest.TestCase):
def test_primes(self): def test_primes(self):
self.assertTrue(prime_check(2)) self.assertTrue(is_prime(2))
self.assertTrue(prime_check(3)) self.assertTrue(is_prime(3))
self.assertTrue(prime_check(5)) self.assertTrue(is_prime(5))
self.assertTrue(prime_check(7)) self.assertTrue(is_prime(7))
self.assertTrue(prime_check(11)) self.assertTrue(is_prime(11))
self.assertTrue(prime_check(13)) self.assertTrue(is_prime(13))
self.assertTrue(prime_check(17)) self.assertTrue(is_prime(17))
self.assertTrue(prime_check(19)) self.assertTrue(is_prime(19))
self.assertTrue(prime_check(23)) self.assertTrue(is_prime(23))
self.assertTrue(prime_check(29)) self.assertTrue(is_prime(29))
def test_not_primes(self): def test_not_primes(self):
self.assertFalse( self.assertFalse(
prime_check(-19), is_prime(-19),
"Negative numbers are excluded by definition of prime numbers.", "Negative numbers are excluded by definition of prime numbers.",
) )
self.assertFalse( self.assertFalse(
prime_check(0), is_prime(0),
"Zero doesn't have any positive factors, primes must have exactly two.", "Zero doesn't have any positive factors, primes must have exactly two.",
) )
self.assertFalse( self.assertFalse(
prime_check(1), is_prime(1),
"One only has 1 positive factor, primes must have exactly two.", "One only has 1 positive factor, primes must have exactly two.",
) )
self.assertFalse(prime_check(2 * 2)) self.assertFalse(is_prime(2 * 2))
self.assertFalse(prime_check(2 * 3)) self.assertFalse(is_prime(2 * 3))
self.assertFalse(prime_check(3 * 3)) self.assertFalse(is_prime(3 * 3))
self.assertFalse(prime_check(3 * 5)) self.assertFalse(is_prime(3 * 5))
self.assertFalse(prime_check(3 * 5 * 7)) self.assertFalse(is_prime(3 * 5 * 7))
if __name__ == "__main__": if __name__ == "__main__":

View File

@ -41,7 +41,7 @@ goldbach(number) // Goldbach's assumption
from math import sqrt from math import sqrt
def isPrime(number): def is_prime(number: int) -> bool:
""" """
input: positive integer 'number' input: positive integer 'number'
returns true if 'number' is prime otherwise false. returns true if 'number' is prime otherwise false.
@ -129,7 +129,7 @@ def getPrimeNumbers(N):
# if a number is prime then appends to list 'ans' # if a number is prime then appends to list 'ans'
for number in range(2, N + 1): for number in range(2, N + 1):
if isPrime(number): if is_prime(number):
ans.append(number) ans.append(number)
@ -164,11 +164,11 @@ def primeFactorization(number):
ans.append(number) ans.append(number)
# if 'number' not prime then builds the prime factorization of 'number' # if 'number' not prime then builds the prime factorization of 'number'
elif not isPrime(number): elif not is_prime(number):
while quotient != 1: while quotient != 1:
if isPrime(factor) and (quotient % factor == 0): if is_prime(factor) and (quotient % factor == 0):
ans.append(factor) ans.append(factor)
quotient /= factor quotient /= factor
else: else:
@ -317,8 +317,8 @@ def goldbach(number):
isinstance(ans, list) isinstance(ans, list)
and (len(ans) == 2) and (len(ans) == 2)
and (ans[0] + ans[1] == number) and (ans[0] + ans[1] == number)
and isPrime(ans[0]) and is_prime(ans[0])
and isPrime(ans[1]) and is_prime(ans[1])
), "'ans' must contains two primes. And sum of elements must been eq 'number'" ), "'ans' must contains two primes. And sum of elements must been eq 'number'"
return ans return ans
@ -462,11 +462,11 @@ def getPrime(n):
# if ans not prime then # if ans not prime then
# runs to the next prime number. # runs to the next prime number.
while not isPrime(ans): while not is_prime(ans):
ans += 1 ans += 1
# precondition # precondition
assert isinstance(ans, int) and isPrime( assert isinstance(ans, int) and is_prime(
ans ans
), "'ans' must been a prime number and from type int" ), "'ans' must been a prime number and from type int"
@ -486,7 +486,7 @@ def getPrimesBetween(pNumber1, pNumber2):
# precondition # precondition
assert ( assert (
isPrime(pNumber1) and isPrime(pNumber2) and (pNumber1 < pNumber2) is_prime(pNumber1) and is_prime(pNumber2) and (pNumber1 < pNumber2)
), "The arguments must been prime numbers and 'pNumber1' < 'pNumber2'" ), "The arguments must been prime numbers and 'pNumber1' < 'pNumber2'"
number = pNumber1 + 1 # jump to the next number number = pNumber1 + 1 # jump to the next number
@ -495,7 +495,7 @@ def getPrimesBetween(pNumber1, pNumber2):
# if number is not prime then # if number is not prime then
# fetch the next prime number. # fetch the next prime number.
while not isPrime(number): while not is_prime(number):
number += 1 number += 1
while number < pNumber2: while number < pNumber2:
@ -505,7 +505,7 @@ def getPrimesBetween(pNumber1, pNumber2):
number += 1 number += 1
# fetch the next prime number. # fetch the next prime number.
while not isPrime(number): while not is_prime(number):
number += 1 number += 1
# precondition # precondition