diff --git a/electronics/electric_power.py b/electronics/electric_power.py index 8b92e320ace3..8e3454e39c3f 100644 --- a/electronics/electric_power.py +++ b/electronics/electric_power.py @@ -23,20 +23,22 @@ def electric_power(voltage: float, current: float, power: float) -> tuple: >>> electric_power(voltage=2, current=4, power=2) Traceback (most recent call last): ... - ValueError: Only one argument must be 0 + ValueError: Exactly one argument must be 0 >>> electric_power(voltage=0, current=0, power=2) Traceback (most recent call last): ... - ValueError: Only one argument must be 0 + ValueError: Exactly one argument must be 0 >>> electric_power(voltage=0, current=2, power=-4) Traceback (most recent call last): ... ValueError: Power cannot be negative in any electrical/electronics system >>> electric_power(voltage=2.2, current=2.2, power=0) Result(name='power', value=4.84) + >>> electric_power(current=0, power=6, voltage=2) + Result(name='current', value=3.0) """ if (voltage, current, power).count(0) != 1: - raise ValueError("Only one argument must be 0") + raise ValueError("Exactly one argument must be 0") elif power < 0: raise ValueError( "Power cannot be negative in any electrical/electronics system" @@ -48,7 +50,7 @@ def electric_power(voltage: float, current: float, power: float) -> tuple: elif power == 0: return Result("power", float(round(abs(voltage * current), 2))) else: - raise ValueError("Exactly one argument must be 0") + raise AssertionError if __name__ == "__main__": diff --git a/machine_learning/linear_regression.py b/machine_learning/linear_regression.py index 839a5366d1cc..1d11e5a9cc2b 100644 --- a/machine_learning/linear_regression.py +++ b/machine_learning/linear_regression.py @@ -41,6 +41,14 @@ def run_steep_gradient_descent(data_x, data_y, len_data, alpha, theta): :param theta : Feature vector (weight's for our model) ;param return : Updated Feature's, using curr_features - alpha_ * gradient(w.r.t. feature) + >>> import numpy as np + >>> data_x = np.array([[1, 2], [3, 4]]) + >>> data_y = np.array([5, 6]) + >>> len_data = len(data_x) + >>> alpha = 0.01 + >>> theta = np.array([0.1, 0.2]) + >>> run_steep_gradient_descent(data_x, data_y, len_data, alpha, theta) + array([0.196, 0.343]) """ n = len_data @@ -58,6 +66,12 @@ def sum_of_square_error(data_x, data_y, len_data, theta): :param len_data : len of the dataset :param theta : contains the feature vector :return : sum of square error computed from given feature's + + Example: + >>> vc_x = np.array([[1.1], [2.1], [3.1]]) + >>> vc_y = np.array([1.2, 2.2, 3.2]) + >>> round(sum_of_square_error(vc_x, vc_y, 3, np.array([1])),3) + np.float64(0.005) """ prod = np.dot(theta, data_x.transpose()) prod -= data_y.transpose() @@ -93,6 +107,11 @@ def mean_absolute_error(predicted_y, original_y): :param predicted_y : contains the output of prediction (result vector) :param original_y : contains values of expected outcome :return : mean absolute error computed from given feature's + + >>> predicted_y = [3, -0.5, 2, 7] + >>> original_y = [2.5, 0.0, 2, 8] + >>> mean_absolute_error(predicted_y, original_y) + 0.5 """ total = sum(abs(y - predicted_y[i]) for i, y in enumerate(original_y)) return total / len(original_y) @@ -114,4 +133,7 @@ def main(): if __name__ == "__main__": + import doctest + + doctest.testmod() main() diff --git a/maths/matrix_exponentiation.py b/maths/matrix_exponentiation.py index 7c37151c87ca..7cdac9d34674 100644 --- a/maths/matrix_exponentiation.py +++ b/maths/matrix_exponentiation.py @@ -39,6 +39,21 @@ def modular_exponentiation(a, b): def fibonacci_with_matrix_exponentiation(n, f1, f2): + """ + Returns the nth number of the Fibonacci sequence that + starts with f1 and f2 + Uses the matrix exponentiation + >>> fibonacci_with_matrix_exponentiation(1, 5, 6) + 5 + >>> fibonacci_with_matrix_exponentiation(2, 10, 11) + 11 + >>> fibonacci_with_matrix_exponentiation(13, 0, 1) + 144 + >>> fibonacci_with_matrix_exponentiation(10, 5, 9) + 411 + >>> fibonacci_with_matrix_exponentiation(9, 2, 3) + 89 + """ # Trivial Cases if n == 1: return f1 @@ -50,21 +65,34 @@ def fibonacci_with_matrix_exponentiation(n, f1, f2): def simple_fibonacci(n, f1, f2): + """ + Returns the nth number of the Fibonacci sequence that + starts with f1 and f2 + Uses the definition + >>> simple_fibonacci(1, 5, 6) + 5 + >>> simple_fibonacci(2, 10, 11) + 11 + >>> simple_fibonacci(13, 0, 1) + 144 + >>> simple_fibonacci(10, 5, 9) + 411 + >>> simple_fibonacci(9, 2, 3) + 89 + """ # Trivial Cases if n == 1: return f1 elif n == 2: return f2 - fn_1 = f1 - fn_2 = f2 n -= 2 while n > 0: - fn_1, fn_2 = fn_1 + fn_2, fn_1 + f2, f1 = f1 + f2, f2 n -= 1 - return fn_1 + return f2 def matrix_exponentiation_time(): diff --git a/maths/special_numbers/armstrong_numbers.py b/maths/special_numbers/armstrong_numbers.py index b2b4010a8f5b..a3cb69b814de 100644 --- a/maths/special_numbers/armstrong_numbers.py +++ b/maths/special_numbers/armstrong_numbers.py @@ -43,9 +43,9 @@ def armstrong_number(n: int) -> bool: def pluperfect_number(n: int) -> bool: """Return True if n is a pluperfect number or False if it is not - >>> all(armstrong_number(n) for n in PASSING) + >>> all(pluperfect_number(n) for n in PASSING) True - >>> any(armstrong_number(n) for n in FAILING) + >>> any(pluperfect_number(n) for n in FAILING) False """ if not isinstance(n, int) or n < 1: @@ -70,9 +70,9 @@ def pluperfect_number(n: int) -> bool: def narcissistic_number(n: int) -> bool: """Return True if n is a narcissistic number or False if it is not. - >>> all(armstrong_number(n) for n in PASSING) + >>> all(narcissistic_number(n) for n in PASSING) True - >>> any(armstrong_number(n) for n in FAILING) + >>> any(narcissistic_number(n) for n in FAILING) False """ if not isinstance(n, int) or n < 1: diff --git a/maths/special_numbers/bell_numbers.py b/maths/special_numbers/bell_numbers.py index 5d99334d7add..d573e7a3962d 100644 --- a/maths/special_numbers/bell_numbers.py +++ b/maths/special_numbers/bell_numbers.py @@ -21,6 +21,10 @@ def bell_numbers(max_set_length: int) -> list[int]: list: A list of Bell numbers for sets of lengths from 0 to max_set_length. Examples: + >>> bell_numbers(-2) + Traceback (most recent call last): + ... + ValueError: max_set_length must be non-negative >>> bell_numbers(0) [1] >>> bell_numbers(1) diff --git a/maths/special_numbers/hamming_numbers.py b/maths/special_numbers/hamming_numbers.py index 4575119c8a95..a473cc93883b 100644 --- a/maths/special_numbers/hamming_numbers.py +++ b/maths/special_numbers/hamming_numbers.py @@ -13,6 +13,10 @@ def hamming(n_element: int) -> list: :param n_element: The number of elements on the list :return: The nth element of the list + >>> hamming(-5) + Traceback (most recent call last): + ... + ValueError: n_element should be a positive number >>> hamming(5) [1, 2, 3, 4, 5] >>> hamming(10) @@ -22,7 +26,7 @@ def hamming(n_element: int) -> list: """ n_element = int(n_element) if n_element < 1: - my_error = ValueError("a should be a positive number") + my_error = ValueError("n_element should be a positive number") raise my_error hamming_list = [1] diff --git a/maths/special_numbers/harshad_numbers.py b/maths/special_numbers/harshad_numbers.py index 61667adfa127..417120bd840e 100644 --- a/maths/special_numbers/harshad_numbers.py +++ b/maths/special_numbers/harshad_numbers.py @@ -11,6 +11,8 @@ def int_to_base(number: int, base: int) -> str: Where 'base' ranges from 2 to 36. Examples: + >>> int_to_base(0, 21) + '0' >>> int_to_base(23, 2) '10111' >>> int_to_base(58, 5) @@ -26,6 +28,10 @@ def int_to_base(number: int, base: int) -> str: Traceback (most recent call last): ... ValueError: 'base' must be between 2 and 36 inclusive + >>> int_to_base(-99, 16) + Traceback (most recent call last): + ... + ValueError: number must be a positive integer """ if base < 2 or base > 36: @@ -101,6 +107,8 @@ def harshad_numbers_in_base(limit: int, base: int) -> list[str]: Traceback (most recent call last): ... ValueError: 'base' must be between 2 and 36 inclusive + >>> harshad_numbers_in_base(-12, 6) + [] """ if base < 2 or base > 36: