import math def _is_rectangular(matrix: list[list[float]]) -> bool: """Check whether a matrix is non-empty and rectangular.""" if not matrix: return False first_length = len(matrix[0]) return first_length > 0 and all( len(row) == first_length for row in matrix ) def matmul( a: list[list[float]], b: list[list[float]], ) -> list[list[float]]: """Multiply two matrices and return their product. Raises: ValueError: If a matrix is invalid or dimensions do not match. """ if not _is_rectangular(a) or not _is_rectangular(b): raise ValueError("Both matrices must be non-empty and rectangular.") if len(a[0]) != len(b): raise ValueError("Number of columns in a must equal rows in b.") result = [] for row in a: result_row = [] for column_index in range(len(b[0])): total = sum( row[k] * b[k][column_index] for k in range(len(b)) ) result_row.append(total) result.append(result_row) return result def transpose(matrix: list[list[float]]) -> list[list[float]]: """Return the transpose of a matrix. Raises: ValueError: If the matrix is invalid. """ if not _is_rectangular(matrix): raise ValueError("Matrix must be non-empty and rectangular.") return [ [matrix[row][column] for row in range(len(matrix))] for column in range(len(matrix[0])) ] def rot_2D(theta: float) -> list[list[float]]: """Create a 2D rotation matrix for an angle in radians.""" cos_theta = math.cos(theta) sin_theta = math.sin(theta) return [ [cos_theta, -sin_theta], [sin_theta, cos_theta], ] def rotate(matrix: list[list[float]]) -> list[list[float]]: """Rotate a matrix 90 degrees clockwise. Raises: ValueError: If the matrix is invalid. """ if not _is_rectangular(matrix): raise ValueError("Matrix must be non-empty and rectangular.") return [ [ matrix[row][column] for row in range(len(matrix) - 1, -1, -1) ] for column in range(len(matrix[0])) ] if __name__ == "__main__": # Test 1: Matrix multiplication a = [[1, 2, 3], [4, 5, 6]] b = [[7, 8], [9, 10], [11, 12]] assert matmul(a, b) == [[58, 64], [139, 154]] print("Matrix multiplication: passed") print(matmul(a, b)) # Test 2: Matrix multiplication with another example assert matmul([[1, 2]], [[3], [4]]) == [[11]] print("Second multiplication test: passed") # Test 3: Transpose matrix = [[1, 2, 3], [4, 5, 6]] assert transpose(matrix) == [[1, 4], [2, 5], [3, 6]] print("Transpose: passed") # Test 4: Rotation clockwise assert rotate(matrix) == [[4, 1], [5, 2], [6, 3]] print("Rotation: passed") # Test 5: 2D rotation matrix rotation = rot_2D(0.01) assert len(rotation) == 2 and len(rotation[0]) == 2 print("2D rotation matrix: passed") print(rotation) # Test 6: Invalid multiplication dimensions try: matmul([[1, 2], [3, 4]], [[5, 6, 7]]) except ValueError: print("Invalid multiplication dimensions: handled") else: raise AssertionError("Expected ValueError for matmul") # Test 7: Invalid matrices for function in (transpose, rotate): try: function([]) except ValueError: print(f"{function.__name__}: invalid matrix handled") else: raise AssertionError( f"Expected ValueError for {function.__name__}" ) # Test 8: Non-rectangular matrix try: transpose([[1, 2], [3]]) except ValueError: print("Non-rectangular matrix: handled") else: raise AssertionError("Expected ValueError for transpose") print("All tests passed!")