





from __future__ import annotations

import math





def lowerCAmelCase__(__snake_case ,__snake_case							)       ->   list:







	'''simple docstring'''







	if len(__snake_case							) != 2 or len(a[0]							) != 2 or len(__snake_case							) != 2 or len(b[0]							) != 2:
		raise Exception('''Matrices are not 2x2'''							)
	lowerCamelCase__              =	[
	    [a[0][0] * b[0][0] + a[0][1] * b[1][0], a[0][0] * b[0][1] + a[0][1] * b[1][1]],
	    [a[1][0] * b[0][0] + a[1][1] * b[1][0], a[1][0] * b[0][1] + a[1][1] * b[1][1]],
	]
	return new_matrix





def lowerCAmelCase__(__snake_case ,__snake_case							)       ->   List[str]:







	'''simple docstring'''







	return [
	    [matrix_a[row][col] + matrix_b[row][col] for col in range(len(matrix_a[row]							)							)]
	    for row in range(len(__snake_case							)							)
	]





def lowerCAmelCase__(__snake_case ,__snake_case							)       ->   str:







	'''simple docstring'''







	return [
	    [matrix_a[row][col] - matrix_b[row][col] for col in range(len(matrix_a[row]							)							)]
	    for row in range(len(__snake_case							)							)
	]





def lowerCAmelCase__(__snake_case							)       ->   tuple[list, list, list, list]:







	'''simple docstring'''







	if len(__snake_case							) % 2 != 0 or len(a[0]							) % 2 != 0:
		raise Exception('''Odd matrices are not supported!'''							)

	lowerCamelCase__              =	len(__snake_case							)
	lowerCamelCase__              =	matrix_length // 2

	lowerCamelCase__              =	[[a[i][j] for j in range(__snake_case ,__snake_case							)] for i in range(__snake_case							)]
	lowerCamelCase__              =	[
	    [a[i][j] for j in range(__snake_case ,__snake_case							)] for i in range(__snake_case ,__snake_case							)
	]

	lowerCamelCase__              =	[[a[i][j] for j in range(__snake_case							)] for i in range(__snake_case							)]
	lowerCamelCase__              =	[[a[i][j] for j in range(__snake_case							)] for i in range(__snake_case ,__snake_case							)]

	return top_left, top_right, bot_left, bot_right





def lowerCAmelCase__(__snake_case							)       ->   tuple[int, int]:







	'''simple docstring'''







	return len(__snake_case							), len(matrix[0]							)





def lowerCAmelCase__(__snake_case							)       ->   None:







	'''simple docstring'''







	print('''\n'''.join(str(__snake_case							) for line in matrix							)							)





def lowerCAmelCase__(__snake_case ,__snake_case							)       ->   list:







	'''simple docstring'''







	if matrix_dimensions(__snake_case							) == (2, 2):
		return default_matrix_multiplication(__snake_case ,__snake_case							)

	lowerCamelCase__       ,			lowerCamelCase__       ,			lowerCamelCase__       ,			lowerCamelCase__              =	split_matrix(__snake_case							)
	lowerCamelCase__       ,			lowerCamelCase__       ,			lowerCamelCase__       ,			lowerCamelCase__              =	split_matrix(__snake_case							)

	lowerCamelCase__              =	actual_strassen(__snake_case ,matrix_subtraction(__snake_case ,__snake_case							)							)
	lowerCamelCase__              =	actual_strassen(matrix_addition(__snake_case ,__snake_case							) ,__snake_case							)
	lowerCamelCase__              =	actual_strassen(matrix_addition(__snake_case ,__snake_case							) ,__snake_case							)
	lowerCamelCase__              =	actual_strassen(__snake_case ,matrix_subtraction(__snake_case ,__snake_case							)							)
	lowerCamelCase__              =	actual_strassen(matrix_addition(__snake_case ,__snake_case							) ,matrix_addition(__snake_case ,__snake_case							)							)
	lowerCamelCase__              =	actual_strassen(matrix_subtraction(__snake_case ,__snake_case							) ,matrix_addition(__snake_case ,__snake_case							)							)
	lowerCamelCase__              =	actual_strassen(matrix_subtraction(__snake_case ,__snake_case							) ,matrix_addition(__snake_case ,__snake_case							)							)

	lowerCamelCase__              =	matrix_addition(matrix_subtraction(matrix_addition(__snake_case ,__snake_case							) ,__snake_case							) ,__snake_case							)
	lowerCamelCase__              =	matrix_addition(__snake_case ,__snake_case							)
	lowerCamelCase__              =	matrix_addition(__snake_case ,__snake_case							)
	lowerCamelCase__              =	matrix_subtraction(matrix_subtraction(matrix_addition(__snake_case ,__snake_case							) ,__snake_case							) ,__snake_case							)

	# construct the new matrix from our 4 quadrants
	lowerCamelCase__              =	[]
	for i in range(len(__snake_case							)							):
		new_matrix.append(top_left[i] + top_right[i]							)
	for i in range(len(__snake_case							)							):
		new_matrix.append(bot_left[i] + bot_right[i]							)
	return new_matrix





def lowerCAmelCase__(__snake_case ,__snake_case							)       ->   list:







	'''simple docstring'''







	if matrix_dimensions(__snake_case							)[1] != matrix_dimensions(__snake_case							)[0]:
		lowerCamelCase__              =	(
		    '''Unable to multiply these matrices, please check the dimensions.\n'''
		    F'Matrix A: {matrixa}\n'
		    F'Matrix B: {matrixa}'
		)
		raise Exception(__snake_case							)
	lowerCamelCase__              =	matrix_dimensions(__snake_case							)
	lowerCamelCase__              =	matrix_dimensions(__snake_case							)

	if dimensiona[0] == dimensiona[1] and dimensiona[0] == dimensiona[1]:
		return [matrixa, matrixa]

	lowerCamelCase__              =	max(*__snake_case ,*__snake_case							)
	lowerCamelCase__              =	int(math.pow(2 ,math.ceil(math.loga(__snake_case							)							)							)							)
	lowerCamelCase__              =	matrixa
	lowerCamelCase__              =	matrixa

	# Adding zeros to the matrices so that the arrays dimensions are the same and also
	# power of 2
	for i in range(0 ,__snake_case							):
		if i < dimensiona[0]:
			for _ in range(dimensiona[1] ,__snake_case							):
				new_matrixa[i].append(0							)
		else:
			new_matrixa.append([0] * maxim							)
		if i < dimensiona[0]:
			for _ in range(dimensiona[1] ,__snake_case							):
				new_matrixa[i].append(0							)
		else:
			new_matrixa.append([0] * maxim							)

	lowerCamelCase__              =	actual_strassen(__snake_case ,__snake_case							)

	# Removing the additional zeros
	for i in range(0 ,__snake_case							):
		if i < dimensiona[0]:
			for _ in range(dimensiona[1] ,__snake_case							):
				final_matrix[i].pop()
		else:
			final_matrix.pop()
	return final_matrix


if __name__ == "__main__":
			_a						=   [
			    [2, 3, 4, 5],
			    [6, 4, 3, 1],
			    [2, 3, 6, 7],
			    [3, 1, 2, 4],
			    [2, 3, 4, 5],
			    [6, 4, 3, 1],
			    [2, 3, 6, 7],
			    [3, 1, 2, 4],
			    [2, 3, 4, 5],
			    [6, 2, 3, 1],
			]
			_a						=   [[0, 2, 1, 1], [16, 2, 3, 3], [2, 2, 7, 7], [13, 11, 22, 4]]
			print(strassen(matrixa, matrixa))










from __future__ import annotations





def lowerCAmelCase__(__snake_case ,__snake_case ,__snake_case							)       ->   float:







	'''simple docstring'''







	if days_between_payments <= 0:
		raise ValueError('''days_between_payments must be > 0'''							)
	if daily_interest_rate < 0:
		raise ValueError('''daily_interest_rate must be >= 0'''							)
	if principal <= 0:
		raise ValueError('''principal must be > 0'''							)
	return principal * daily_interest_rate * days_between_payments





def lowerCAmelCase__(__snake_case ,__snake_case ,__snake_case ,)       ->   float:







	'''simple docstring'''







	if number_of_compounding_periods <= 0:
		raise ValueError('''number_of_compounding_periods must be > 0'''							)
	if nominal_annual_interest_rate_percentage < 0:
		raise ValueError('''nominal_annual_interest_rate_percentage must be >= 0'''							)
	if principal <= 0:
		raise ValueError('''principal must be > 0'''							)

	return principal * (
	    (1 + nominal_annual_interest_rate_percentage) ** number_of_compounding_periods
	    - 1
	)





def lowerCAmelCase__(__snake_case ,__snake_case ,__snake_case ,)       ->   float:







	'''simple docstring'''







	if number_of_years <= 0:
		raise ValueError('''number_of_years must be > 0'''							)
	if nominal_annual_percentage_rate < 0:
		raise ValueError('''nominal_annual_percentage_rate must be >= 0'''							)
	if principal <= 0:
		raise ValueError('''principal must be > 0'''							)

	return compound_interest(
	    __snake_case ,nominal_annual_percentage_rate / 365 ,number_of_years * 365							)


if __name__ == "__main__":
			import doctest

			doctest.testmod()



