def feed_forward(self, values): # generating hidden output hidden = Matrix.mult(self.weights_ih, values) hidden = Matrix.add(hidden, self.bias_h) hidden = list(Sigmoid.matrix(hidden)) # generating output nodes output = Matrix.mult(self.weights_ho, hidden) output = Matrix.add(output, self.bias_o) output = list(Sigmoid.matrix(output)) return output
def predict(self, arr): # INPUT => HIDDEN input = Matrix.array_to_matrix(arr) hidden = Matrix.multiply(self.ih_weights, input) hidden = Matrix.add(hidden, self.ih_biases) hidden.map(sigmoid) # HIDDEN => OUTPUT output = Matrix.multiply(self.ho_weights, hidden) output = Matrix.add(output, self.ho_biases) output.map(sigmoid) output = Matrix.matrix_to_array(output) return output
def cg(A,b): #guess x all 0s x = Matrix(i=A.columns,j=1) #set r and p r = b.subtract(A.multiply(x)) p = b.subtract(A.multiply(x)) r_norm_inf = 0 for i in range(1,r.rows+1): v = r.get(i,1) if (v > r_norm_inf): r_norm_inf = v r_norm_2 = 0 r_norm_2 = math.sqrt(r.transpose().multiply(r).get(1,1)) iteration = 1 while( r_norm_2 > LIMITERROR): p_t = p.transpose() alpha = p_t.multiply(r).get(1,1) / p_t.multiply(A.multiply(p)).get(1,1) # a_p for alpha*p a_p = copy.deepcopy(p) for i in range(1,a_p.rows+1): for j in range(1,a_p.columns+1): a_p.set(i,j,a_p.get(i,j)*alpha) x = x.add(a_p) r = b.subtract(A.multiply(x)) beta = -1 * (p_t.multiply(A.multiply(r)).get(1,1) / p_t.multiply(A.multiply(p)).get(1,1)) # b_p for beta*p b_p = p #no need to copy (as we update cell by cell of p to b_p and we don't need it later) for i in range(1,b_p.rows+1): for j in range(1,b_p.columns+1): b_p.set(i,j,p.get(i,j)*beta) p = r.add(b_p) # compute r norms and f.write r_norm_inf = 0 for i in range(1,r.rows+1): v = r.get(i,1) if (v > r_norm_inf): r_norm_inf = v r_norm_2 = math.sqrt(r.transpose().multiply(r).get(1,1)) f.write(str(iteration)+","+str(r_norm_inf)+","+str(r_norm_2)+"\n") iteration+=1 f.write(",,,"+str(iteration-1)) return x
class Particle: position:Matrix velocity:Matrix bestPosition:Matrix # Personal best solution. bestEval:Matrix # Personal best value. function = None # The evaluation function to use. def __init__(self, func, beginRange, endRange) -> None: super().__init__() if (beginRange >= endRange): raise ValueError("Begin range must be less than end range.") self.function = func self.position = Matrix() self.velocity = Matrix() self.setRandomPosition(beginRange, endRange) self.bestPosition = self.velocity.clone() self.bestEval = self.evaluate() def evaluate(self): return self.function(self.position.x, self.position.y) def setRandomPosition (self, beginRange, endRange): x = random.uniform(beginRange, endRange) y = random.uniform(beginRange, endRange) z = random.uniform(beginRange, endRange) self.position.x = x self.position.y = y self.position.z = z def updatePersonalBest(self): evaluation = self.evaluate() if (evaluation < self.bestEval): self.bestPosition = self.position.clone() self.bestEval = evaluation def updatePosition(self): self.position.add(self.velocity)
def train(self, arr, target): # INPUT => HIDDEN input = Matrix.array_to_matrix(arr) hidden = Matrix.multiply(self.ih_weights, input) hidden = Matrix.add(hidden, self.ih_biases) hidden.map(sigmoid) # HIDDEN => OUTPUT output = Matrix.multiply(self.ho_weights, hidden) output = Matrix.add(output, self.ho_biases) output.map(sigmoid) # BACKPROPAGATION # OUTPUT => HIDDEN expected = Matrix.array_to_matrix(target) output_error = Matrix.subtract(expected, output) d_output = Matrix.map(output, dsigmoid) hidden_T = Matrix.transpose(hidden) gradient = Matrix.hadamard(d_output, output_error) gradient = Matrix.scalar_multiply(gradient, self.learning_rate) # Apply to ho_biases self.ho_biases = Matrix.add(self.ho_biases, gradient) # Apply to ho_weights weights_ho_deltas = Matrix.multiply(gradient, hidden_T) self.ho_weights = Matrix.add(self.ho_weights, weights_ho_deltas) # HIDDEN => INPUT weights_ho_T = Matrix.transpose(self.ho_weights) hidden_error = Matrix.multiply(weights_ho_T, output_error) d_hidden = Matrix.map(hidden, dsigmoid) input_T = Matrix.transpose(input) gradient_H = Matrix.hadamard(d_hidden, hidden_error) gradient_H = Matrix.scalar_multiply(gradient_H, self.learning_rate) # Apply to ih_biases self.ih_biases = Matrix.add(self.ih_biases, gradient_H) # Apply to ih_weights weights_ih_deltas = Matrix.multiply(gradient_H, input_T) self.ih_weights = Matrix.add(self.ih_weights, weights_ih_deltas)
class Console: def __init__(self): self.matrix = Matrix([]) self.graph = Graph() @property def matrix(self): return self.__matrix @matrix.setter def matrix(self, value): self.__matrix = value @property def graph(self): return self.__graph @graph.setter def graph(self, value): self.__graph = value @staticmethod def start(): console = Console().run() return console def run(self): while True: # Nacteni vstupu input = self.get_input() # Validace vstupu if input == "" or input.isspace(): continue elif not self.validate_input(input): print("Invalid input") continue # Urceni akce action = self.evaulate_input(input) # Vyhodnoceni akce result = self.perform_action(action) if result.is_error(): print(result.get_error()) elif result.get_stop(): break return self def get_input(self): return input("GraphIt.Command>").strip() def validate_input(self, input): return True def evaulate_input(self, input): command = "" params = [] flags = [] # Pokud je na zacatku cislo → vyhodnoceni vyrazu if len(input) > 0 and ((ord(input[0]) > 47 and ord(input[0]) < 58) or ord(input[0]) == 40): params.clear() params.append(input.replace(" ","")) command = "nexp.infix" # Pokud na na zacatku slozena zavorka - matice elif len(input) > 0 and input[0] == "[": input = input.replace(" ","") lb = input.find("]") sign = input[lb + 1] if sign == "+": command = "matrix.add" elif sign == "-": command = "matrix.sub" elif sign == "*": command = "matrix.mlp" params.clear() params.append(input[:lb + 1]) params.append(input[lb + 2:]) # Vyraz s parametry else: quotation_marks = False space = 0 val = "" for i in range(len(input)): if quotation_marks: if input[i] == "\"": quotation_marks = False else: val = val + input[i] else: if input[i] == "\"": if val != "": if space == 1: params.append(val) elif space == 2: flags.append(val) quotation_marks = True val = "" elif input[i] == ";": if space == 1: params.append(val) elif space == 2: flags.append(val) val = "" elif input[i] == " ": if space == 0: command = val elif space == 1: params.append(val) elif space == 2: flags.append(val) space += 1 val = "" else: val = val + input[i] if val != "": if space == 0: command = val elif space == 1: params.append(val) elif space == 2: flags.append(val) return Action(command, params, flags) def print_msg(self, msg): print("[ =========== MESSAGE =========== ] \n " + msg + "\n[ =============================== ]") def perform_action(self, action): try: command = action.get_command() command_subs = command.split(".") params = action.get_params() flags = action.get_flags() if len(command) == 0: command_subs = [""] * 5 # ====== STOP ====== if command_subs[0] == "stop": return ActionResult(stop = True) # ====== TESTOVACI PRINT ====== elif command_subs[0] == "print": for param in params: print(param) # ====== NUMERICKE VYRAZY ====== elif command_subs[0] == "nexp": if len(command_subs) > 1 and command_subs[1] == "i2p": num_expression = NumericalExpression(params[0]) print(params[0], "->", num_expression.infix_to_postfix()) elif len(command_subs) > 1 and command_subs[1] == "infix": num_expression = NumericalExpression(params[0]) result = "" result = num_expression.evaulate_infix() print(params[0], "=", result) # ====== MATICE ====== elif command_subs[0] == "matrix": if len(command_subs) > 1: if command_subs[1] == "new": self.matrix = Matrix([]) print(self.matrix.to_string()) elif command_subs[1] == "print": print(self.matrix.to_string()) elif command_subs[1] == "load": print(self.matrix.load(params[0]).to_string()) elif command_subs[1] == "tr": print(self.matrix.transpose().to_string()) elif command_subs[1] == "ref": print(self.matrix.REF().to_string()) elif command_subs[1] == "rref": print(self.matrix.RREF().to_string()) elif command_subs[1] == "mlp": if len(command_subs) > 2 and command_subs[2] == "left": matrix_2 = Matrix().load(params[0]) print(self.matrix.multiply_left(matrix_2).to_string()) elif len(command_subs) > 2 and command_subs[2] == "right": matrix_2 = Matrix().load(params[0]) print(self.matrix.multiply_right(matrix_2).to_string()) else: # [1,2;1,2;1,2]*[1;2] if len(params) > 1: self.matrix = Matrix([]) self.matrix.load(params[0]) matrix_2 = Matrix().load(params[1]) else: matrix_2 = Matrix().load(params[0]) print(self.matrix.multiply_right(matrix_2).to_string()) elif command_subs[1] == "add": # [2,2;2,2]+[2,2;2,2] if len(params) > 1: self.matrix = Matrix([]) self.matrix.load(params[0]) matrix_2 = Matrix().load(params[1]) else: matrix_2 = Matrix().load(params[0]) print(self.matrix.add(matrix_2).to_string()) elif command_subs[1] == "sub": if len(params) > 1: self.matrix = Matrix([]) self.matrix.load(params[0]) matrix_2 = Matrix().load(params[1]) else: matrix_2 = Matrix().load(params[0]) print(self.matrix.substract(matrix_2).to_string()) # ====== GRAFIKY ====== elif command_subs[0] == "graph": if len(command_subs) > 1: if command_subs[1] == "new": self.graph = Graph() self.graph.print() elif command_subs[1] == "print": self.graph.print() elif command_subs[1] == "import": self.graph.import_file(params[0]) self.graph.print() elif command_subs[1] == "export": self.graph.export_file(params[0]) self.print_msg("Export successful") elif command_subs[1] == "vertex": if command_subs[2] == "set": self.graph.set_vertex(Vertex(params[0], params[1] if len(params) > 1 else params[0])) self.graph.print() elif command_subs[2] == "remove": self.graph.remove_vertex(Vertex(params[0])) self.graph.print() elif command_subs[1] == "edge": if command_subs[2] == "set": self.graph.set_edge(Edge(Vertex(params[0]), Vertex(params[1]), params[2] if len(params) > 2 else 1), "a") self.graph.print() elif command_subs[2] == "remove": self.graph.remove_edge(Edge(Vertex(params[0]), Vertex(params[1]))) self.graph.print() elif command_subs[1] == "findroute": arr = self.graph.find_route(Vertex(params[0]), Vertex(params[1])) for i in range(len(arr)): print(arr[i][0], "-", arr[i][1]) elif command_subs[1] == "minspntree": self.graph = self.graph.get_minSpanningTree() self.graph.print() elif command_subs[1] == "connected": print(self.graph.is_connected()) return ActionResult() except Exception as err: tr = traceback.format_exc() return ActionResult(error = ("[ =========== ERROR MESSAGE =========== ] \n" + tr + "[ ===================================== ]"))
class NeuralNetwork: def __init__(self, input_nodes, hidden_nodes, output_nodes): self.input_nodes = input_nodes self.hidden_nodes = hidden_nodes self.output_nodes = output_nodes self.learning_rate = 0.2 # weights between input and hidden layer self.weights_input_to_hidden = Matrix(self.hidden_nodes, self.input_nodes) self.weights_input_to_hidden.randomize() # outputs will be row and one col for bias self.bias_hidden = Matrix(self.hidden_nodes, 1) self.bias_hidden.randomize() # weights between hidden and output layer self.weights_hidden_to_output = Matrix(self.output_nodes, self.hidden_nodes) self.weights_hidden_to_output.randomize() # outputs will be row and one col for bias self.bias_output = Matrix(self.output_nodes, 1) self.bias_output.randomize() def predict(self, input_array): inputs = Matrix.from_array(input_array) # hidden layer is input multiplied by weights hidden = Matrix.multiply(self.weights_input_to_hidden, inputs) # bias applied hidden.add(self.bias_hidden) # sigmoid to normalize value hidden.apply(self.__sigmoid) outputs = Matrix.multiply(self.weights_hidden_to_output, hidden) outputs.add(self.bias_output) outputs.apply(self.__sigmoid) return outputs.to_array() def train(self, input_array, target_array): inputs = Matrix.from_array(input_array) # hidden layer is input multiplied by weights hidden = Matrix.multiply(self.weights_input_to_hidden, inputs) # bias applied hidden.add(self.bias_hidden) # sigmoid to normalize value hidden.apply(self.__sigmoid) outputs = Matrix.multiply(self.weights_hidden_to_output, hidden) outputs.add(self.bias_output) outputs.apply(self.__sigmoid) # Error calculated to tune weights # using back propagation # Error = target - output target = Matrix.from_array(target_array) error_output = Matrix.subtract(target, outputs) # delta w = learning rate * error * (s(o) * (1 - s(o)) ) * input transposed # ---------- ^^^^^^^^^^^^^ this is gradient ^^^^^^^^^^^^^ -------------------- # w - hidden to output = learning_rate * error_output * __derivative(outputs) * transpose(hidden) gradient = outputs.map(self.__derivative) gradient.multiply_element_wise(error_output) gradient.multiply_element_wise(self.learning_rate) hidden_transposed = Matrix.transpose(hidden) delta_hidden_to_outputs_weight = Matrix.multiply(gradient, hidden_transposed) # update weights and bias self.weights_hidden_to_output.add(delta_hidden_to_outputs_weight) self.bias_output.add(gradient) # Hidden layer error = output error - output error_hidden = Matrix.multiply(Matrix.transpose(self.weights_hidden_to_output), error_output) # w - input to hidden = learning_rate * error_hidden * __derivative(hidden) * transpose(inputs) gradient_hidden = hidden.map(self.__derivative) gradient_hidden.multiply_element_wise(error_hidden) gradient_hidden.multiply_element_wise(self.learning_rate) inputs_transposed = Matrix.transpose(inputs) delta_inputs_to_hidden_weight = Matrix.multiply(gradient_hidden, inputs_transposed) # update weights and bias self.weights_input_to_hidden.add(delta_inputs_to_hidden_weight) self.bias_hidden.add(gradient_hidden) @staticmethod def __sigmoid(x): return 1 / (1 + math.exp(-x)) @staticmethod def __derivative(y): return y * (1 - y)
class Operations: def __init__(self): self.data = [] self.matrices = [] self.mean = Matrix([[0, 0]]) self.covariance = Matrix([[0, 0], [0, 0]]) self.setup() self.set_mean() self.set_covariance() print(len(self.matrices)) def get_mean(self): return self.mean def get_covariance(self): return self.covariance # Read in and prepare the eigendata from a file def setup(self): temp = [] filename = open('eigendata.txt', 'r') for line in filename: row = line.strip() temp.append(row) for i in range(0, len(temp)): self.data.append(temp[i].split()) for i in self.data: matrix = Matrix([[float(i[0]), float(i[1])]]) self.matrices.append(matrix) # Calculate the mean and assign it to the Class variable self.mean def set_mean(self): for i in self.matrices: self.mean = self.mean.add(i) self.mean.scaler(1 / len(self.matrices)) # Calculate the covariance and assign it to the Class variable self.covariance def set_covariance(self): for i in self.matrices: a = i.subtract(self.mean) a_transpose = Matrix(a.get_data()) a_transpose.transpose() b = a_transpose.multiply(a) self.covariance = self.covariance.add(b) self.covariance.scaler(1 / len(self.matrices)) # Implementation of the power method for finding the dominant eigenvalue for a square matrix # Returns both eigenvalues for a 2x2 matrix as well as a unit length vector. # If the matrix is not a 2x2 matrix mu will be the dominant eigenvalue. # iterations: max number of iterations allowed # mat: the covariance matrix of the matrix being tested # estimate: a matrix to begin with as the estimate def power(self, iterations, mat, estimate): r = 1 k = 0 m = iterations y = estimate x = mat.multiply(y) while r > .001 and k < m: max_x = x.find_max() x.scaler(1 / max_x) y = Matrix(x.get_data()) x = mat.multiply(y) temp = Matrix(y.get_data()) temp.transpose() a = temp.multiply(x).get_data()[0][0] b = temp.multiply(y).get_data()[0][0] mu = a / b r = Matrix(y.get_data()) r.scaler(mu) r = r.subtract(x) r = r.find_max() k += 1 y.scaler(1 / mu) return mu, mat.trace() - mu, y # Implementation of the leverrier method for finding the characteristic equation for a polynomial def leverrier(self, companion): res = [] b = companion a = -(b.trace()) res.append(a) for i in range(companion.get_rows() - 1, 0, -1): ai = companion.identity() ai.scaler(a) b = companion.multiply(b.add(ai)) a = -(b.trace()) / (5 - i + 1) res.append(a) return res # This method is used to find the roots of a polynomial equation by providing the companion matrix # for the polynomial and an estimate matrix for the power method. # Based on Deflation from this site: http://www.maths.qmul.ac.uk/~wj/MTH5110/notes/notes08.pdf def find_roots(self, comp, est): count = comp.get_rows() for i in range(count): e1, e2, vector = self.power(1000, comp, est) print('comp eigen:', round(e1)) scale = vector.get_data()[i][0] new = vector.multiply(Matrix([comp.get_data()[i]])) new.scaler(1 / scale) comp = comp.subtract(new)
class NeuralNetwork: def __init__(self, input_nodes, hidden_nodes, output_nodes, learning_rate): self.input_nodes = input_nodes self.hidden_nodes = hidden_nodes self.output_nodes = output_nodes self.weights_ih = Matrix(hidden_nodes, input_nodes) self.weights_ho = Matrix(output_nodes, hidden_nodes) self.weights_ih.randomize() self.weights_ho.randomize() self.bias_h = Matrix(self.hidden_nodes, 1) self.bias_o = Matrix(self.output_nodes, 1) self.bias_h.randomize() self.bias_o.randomize() self.learning_rate = learning_rate # Return predicted output without training the network def feed_forward(self, input_array): inputs = Matrix.from_array(input_array) hidden = Matrix.multiply(self.weights_ih, inputs) hidden.add(self.bias_h) # Activation function hidden.map(sigmoid) output = Matrix.multiply(self.weights_ho, hidden) output.add(self.bias_o) # Activation function output.map(sigmoid) return Matrix.to_array(output) def get_weights(self): state = { 'input-hidden': self.weights_ih, 'hidden-output': self.weights_ho } return state def get_activations(self): state = { 'input': self.inputs, 'hidden': self.hidden, 'output': self.outputs } return state def train(self, input_array, target_array): inputs = Matrix.from_array(input_array) self.inputs = inputs # Activations of Hidden Layer hidden = Matrix.multiply(self.weights_ih, inputs) hidden.add(self.bias_h) # Activation function hidden.map(sigmoid) self.hidden = hidden # Activations of Output layer outputs = Matrix.multiply(self.weights_ho, hidden) outputs.add(self.bias_o) # Activation function outputs.map(sigmoid) self.outputs = outputs targets = Matrix.from_array(target_array) # Calculate the error # OUTPUT_ERROR = TARGETS - OUTPUTS output_errors = Matrix.subtract(targets, outputs) # Calculate gradient # GRADIENT = OUTPUTS * (1 - OUTPUTS) * LEARNING_RATE gradients = Matrix.map_static(outputs, d_sigmoid) gradients.scale(output_errors) gradients.scale(self.learning_rate) # Calculate hidden to output deltas # DELTA = GRADIENTS * HIDDEN_t hidden_t = Matrix.transpose(hidden) weights_ho_delta = Matrix.multiply(gradients, hidden_t) # Adjust bias self.bias_o.add(gradients) # Calculate hidden errors # HIDDEN_ERROR = HIDDEN_WEIGHTS_t * OUTPUT_ERROR weights_ho_t = Matrix.transpose(self.weights_ho) hidden_errors = Matrix.multiply(weights_ho_t, output_errors) # Calculate hidden gradient hidden_gradients = Matrix.map_static(hidden, d_sigmoid) hidden_gradients.scale(hidden_errors) hidden_gradients.scale(self.learning_rate) # Calculate input to hidden deltas # HIDDEN_DELTA = GRADIENTS * INPUT_t inputs_t = Matrix.transpose(inputs) weights_ih_delta = Matrix.multiply(hidden_gradients, inputs_t) self.bias_h.add(hidden_gradients) self.weights_ih.add(weights_ih_delta) self.weights_ho.add(weights_ho_delta)
import sys sys.path.append('src') from Matrix import Matrix mat1 = Matrix([[1, 2], [3, 2]]) mat2 = Matrix([[3, 4], [4, 10]]) print("Testing Arithmetic Operations:") result = Matrix.add(mat1,mat2) assert result.test_show()==Matrix([[4, 6], [7, 12]]).test_show(), "Test Addition failed: output "+ result.test_show() + " expected to be "+Matrix([[4, 6], [5, 12]]).test_show() print("Test passed") result = Matrix.subtract(mat2,mat1) assert result.test_show()==Matrix([[2, 2], [1, 8]]).test_show(), "Test Subtraction failed: output "+ result.test_show() + " expected to be "+Matrix([[2, 2], [1, 8]]).test_show() print("Test passed") result = Matrix.scale(mat1,2) assert result.test_show()==Matrix([[2, 4], [6, 4]]).test_show(), "Test Scaling failed: output "+ result.test_show() + " expected to be "+Matrix([[2, 4], [6, 4]]).test_show() print("Test passed") result = Matrix.multiply(mat1,mat2) assert result.test_show()==Matrix([[11, 24], [17, 32]]).test_show(), "Test Matrix Mult failed: output "+ result.test_show() + " expected to be "+Matrix([[11, 24], [17, 32]]).test_show() print("Test passed") result = Matrix.transpose(mat1)
class TestMatrixMethods(unittest.TestCase): def setUp(self): self.tested_matrix_1 = Matrix(10, 21, 700, 3) self.tested_matrix_2 = Matrix(1) self.tested_matrix_3 = Matrix(1, 2, 3, 4, 5, 6, 0, 0, 0) self.tested_matrix_4 = Matrix() self.tested_matrix_5 = Matrix(1, 2, 3, 4) def test_get_matrix_dimention(self): self.assertEqual(self.tested_matrix_1.get_matrix_dimention(), 2) self.assertEqual(self.tested_matrix_2.get_matrix_dimention(), 1) self.assertEqual(self.tested_matrix_3.get_matrix_dimention(), 3) self.assertEqual(self.tested_matrix_4.get_matrix_dimention(), 0) def test_get_matrix_element(self): self.assertEqual(self.tested_matrix_1.get_matrix_element(0, 0), 10) self.assertEqual(self.tested_matrix_1.get_matrix_element(0, 1), 21) self.assertEqual(self.tested_matrix_1.get_matrix_element(1, 0), 700) self.assertEqual(self.tested_matrix_1.get_matrix_element(1, 1), 3) self.assertRaisesRegex(IndexError, "Element out of range", self.tested_matrix_2.get_matrix_element, 3, 3) def test_check_dimention_equality(self): self.assertRaisesRegex( ValueError, "^Wrong matrices dimentions: [0-9]+ is not equal [0-9]+$", Matrix.check_dimention_equality, self.tested_matrix_1, self.tested_matrix_3) self.assertIsNone( Matrix.check_dimention_equality(self.tested_matrix_5, self.tested_matrix_1)) def test_check_number_of_arguments(self): self.assertRaisesRegex(ValueError, "Wrong size", Matrix.check_number_of_arguments, 12) def test_check_argument_type(self): self.assertTrue(Matrix.check_argument_type(self.tested_matrix_1)) self.assertTrue(Matrix.check_argument_type(1)) self.assertTrue(Matrix.check_argument_type(2.5)) self.assertRaisesRegex(TypeError, "Wrong type of argument.", Matrix.check_argument_type, "test_string") def test_multiply_by_constant_value(self): self.assertEqual( self.tested_matrix_1.multiply_by_constant_value(5).elements[0], [50, 105]) self.assertEqual( self.tested_matrix_1.multiply_by_constant_value(5).elements[1], [3500, 15]) def test_construct(self): elements = [1, 2, 3, 4, 5, 6, 7, 8, 9] self.assertIsInstance(Matrix.construct(*elements), Matrix) wrong_elements = [1, 2, 3] self.assertRaises(ValueError, Matrix.construct, *wrong_elements) def test_str(self): self.assertIsInstance(str(self.tested_matrix_3), str) self.assertEqual( str(self.tested_matrix_1), "This is 2x2 quadratic matrix - contains 4 elements.") self.assertEqual( str(self.tested_matrix_2), "This is 1x1 quadratic matrix - contains 1 elements.") self.assertEqual( str(self.tested_matrix_4), "This is 0x0 quadratic matrix - contains 0 elements.") def test_add(self): self.assertIsInstance(self.tested_matrix_1.add(self.tested_matrix_5), Matrix) self.assertEqual( self.tested_matrix_1.add(self.tested_matrix_5).elements[0], [11, 23]) self.assertEqual( self.tested_matrix_1.add(self.tested_matrix_5).elements[1], [703, 7]) self.assertRaises(ValueError, self.tested_matrix_1.add, "error") def test_mul(self): self.assertEqual( (self.tested_matrix_1 * self.tested_matrix_5).elements, [[73, 104], [709, 1412]]) def test_sub(self): self.assertEqual( (self.tested_matrix_1 - self.tested_matrix_5).elements, [[9, 19], [697, -1]])
class OnStart: def __init__(self): self.data = [] self.matrices = [] self.mean = Matrix([[0, 0]]) self.covariance = Matrix([[0, 0], [0, 0]]) self.determinant = 0 self.inverse = [] self.onStart() self.find_mean() self.find_covariance() self.find_covariance_determinant() self.find_inverse_covariance_matrix() # Read in the data. def onStart(self): temp = [] filename = open('classOne.txt', 'r') for line in filename: row = line.strip() temp.append(row) for i in range(0, len(temp)): self.data.append(temp[i].split()) for i in self.data: matrix = Matrix([[float(i[0]), float(i[1])]]) self.matrices.append(matrix) # find the determinant of the covariance matrix def find_covariance_determinant(self): copy_matrix = deepcopy(self.covariance.get_data()) self.determinant = determinant(copy_matrix) # find the inverse of the covariance matrix def find_inverse_covariance_matrix(self): self.inverse = invert(self.covariance.get_data()) # Find the mean of the read-in data def find_mean(self): for x in self.matrices: self.mean = self.mean.add(x) self.mean.scalar(1 / len(self.matrices)) # Find the covariance of the read-ion data def find_covariance(self): for x in self.matrices: val = x.subtract(self.mean) val_transposed = Matrix(val.get_data()) val_transposed.transpose() result = val_transposed.multiply(val) self.covariance = self.covariance.add(result) self.covariance.scalar(1 / len(self.matrices)) # getter methods def get_inverse(self): return self.inverse def get_covariance_determinant(self): return self.determinant def get_mean(self): return self.mean def get_covariance(self): return self.covariance
class NeuralNetwork: def __init__(self, inputsCount, hiddenCount, outputCount): if (isinstance(inputsCount, NeuralNetwork)): a = inputsCount self.input_nodes = a.input_nodes self.hidden_nodes = a.hidden_nodes self.output_nodes = a.output_nodes self.weights_inputs_hidden = a.weights_inputs_hidden.copy() self.weights_hidden_outputs = a.weights_hidden_outputs.copy() self.bias_hidden = a.bias_hidden.copy() self.bias_output = a.bias_output.copy() else: self.input_nodes = inputsCount self.hidden_nodes = hiddenCount self.output_nodes = outputCount self.weights_inputs_hidden = Matrix(self.hidden_nodes, self.input_nodes) self.weights_hidden_outputs = Matrix(self.output_nodes, self.hidden_nodes) self.weights_inputs_hidden.randomize() self.weights_hidden_outputs.randomize() self.bias_hidden = Matrix(self.hidden_nodes, 1) self.bias_output = Matrix(self.output_nodes, 1) self.bias_hidden.randomize() self.bias_output.randomize() self.learning_rate = 0.1 def predict(self, input_array): inputs = Matrix.fromArray(input_array) hidden = Matrix.algebra_multiply(self.weights_inputs_hidden, inputs) hidden.add(self.bias_hidden) hidden.map(sigmoid) output = Matrix.algebra_multiply(self.weights_hidden_outputs, hidden) output.add(self.bias_output) output.map(sigmoid) return output.toArray() def train(self, inputs_array, targets): inputs = Matrix.fromArray(inputs_array) hidden = Matrix.algebra_multiply(self.weights_inputs_hidden, inputs) hidden.add(self.bias_hidden) hidden.map(sigmoid) outputs = Matrix.algebra_multiply(self.weights_hidden_outputs, hidden) outputs.add(self.bias_output) outputs.map(sigmoid) target = Matrix.fromArray(targets) output_errors = Matrix.sub(target, outputs) gradients = Matrix.staticMap(outputs, dsigmoid) gradients.multiply(output_errors) gradients.multiply(self.learning_rate) hidden_t = Matrix.transpose(hidden) weight_hidden_out_deltas = Matrix.algebra_multiply(gradients, hidden_t) self.weights_hidden_outputs.add(weight_hidden_out_deltas) self.bias_output.add(gradients) who_t = Matrix.transpose(self.weights_hidden_outputs) hidden_errors = Matrix.algebra_multiply(who_t, output_errors) hidden_gradient = Matrix.staticMap(hidden, dsigmoid) hidden_gradient.multiply(hidden_errors) hidden_gradient.multiply(self.learning_rate) inputs_t = Matrix.transpose(inputs) weight_ih_deltas = Matrix.algebra_multiply(hidden_gradient, inputs_t) self.weights_inputs_hidden.add(weight_ih_deltas) self.bias_hidden.add(hidden_gradient) def copy(self): return NeuralNetwork(self, 0, 0)
class Operations: def __init__(self): self.data = [] self.matrices = [] self.mean = Matrix([[0, 0]]) self.covariance = Matrix([[0, 0], [0, 0]]) self.setup() self.set_mean() self.set_covariance() print(len(self.matrices)) def get_mean(self): return self.mean def get_covariance(self): return self.covariance # Read in and prepare the eigendata from a file def setup(self): temp = [] filename = open('eigendata.txt', 'r') for line in filename: row = line.strip() temp.append(row) for i in range(0, len(temp)): self.data.append(temp[i].split()) for i in self.data: matrix = Matrix([[float(i[0]), float(i[1])]]) self.matrices.append(matrix) # Calculate the mean and assign it to the Class variable self.mean def set_mean(self): for i in self.matrices: self.mean = self.mean.add(i) self.mean.scaler(1 / len(self.matrices)) # Calculate the covariance and assign it to the Class variable self.covariance def set_covariance(self): for i in self.matrices: a = i.subtract(self.mean) a_transpose = Matrix(a.get_data()) a_transpose.transpose() b = a_transpose.multiply(a) self.covariance = self.covariance.add(b) self.covariance.scaler(1 / len(self.matrices)) # Implementation of the power method for finding the dominant eigenvalue for a square matrix # Returns both eigenvalues for a 2x2 matrix as well as a unit length vector. # If the matrix is not a 2x2 matrix mu will be the dominant eigenvalue. # iterations: max number of iterations allowed # mat: the covariance matrix of the matrix being tested # estimate: a matrix to begin with as the estimate def power(self, iterations, mat, estimate): r = 1 k = 0 m = iterations y = estimate x = mat.multiply(y) while r > .001 and k < m: max_x = x.find_max() x.scaler(1 / max_x) y = Matrix(x.get_data()) x = mat.multiply(y) temp = Matrix(y.get_data()) temp.transpose() a = temp.multiply(x).get_data()[0][0] b = temp.multiply(y).get_data()[0][0] mu = a / b r = Matrix(y.get_data()) r.scaler(mu) r = r.subtract(x) r = r.find_max() k += 1 y.scaler(1 / mu) return mu, mat.trace() - mu, y # Implementation of the leverrier method for finding the characteristic equation for a polynomial def leverrier(self, companion): res = [] b = companion a = -(b.trace()) res.append(a) for i in range(companion.get_rows() - 1, 0, -1): ai = companion.identity() ai.scaler(a) b = companion.multiply(b.add(ai)) a = -(b.trace()) / (5 - i + 1) res.append(a) return res # This method is used to find the roots of a polynomial equation by providing the companion matrix # for the polynomial and an estimate matrix for the power method. # Based on Deflation from this site: http://www.maths.qmul.ac.uk/~wj/MTH5110/notes/notes08.pdf def find_roots(self, comp, est): count = comp.get_rows() for i in range(count): e1, e2, vector = self.power(1000, comp, est) print('comp eigen:', round(e1)) scale = vector.get_data()[i][0] new = vector.multiply(Matrix([comp.get_data()[i]])) new.scaler(1 / scale) comp = comp.subtract(new)
class NeuralNetwork: def __init__(self, input_nodes, hidden_nodes, output_nodes): self.input_nodes = input_nodes self.hidden_nodes = hidden_nodes self.output_nodes = output_nodes self.weights_ih = Matrix(self.hidden_nodes, self.input_nodes) self.weights_ih.randomize() self.weights_ho = Matrix(self.output_nodes, self.hidden_nodes) self.weights_ho.randomize() self.bias_h = Matrix(self.hidden_nodes, 1) self.bias_h.randomize() self.bias_o = Matrix(self.output_nodes, 1) self.bias_o.randomize() self.learning_rate = 1 def predict(self, input_array): # Generating the hidden outputs inputs = Matrix.fromArray(input_array) hidden = Matrix.matrixMultiply(self.weights_ih, inputs) hidden.add(self.bias_h) # Activation function hidden.map(sigmoid) # Generating the output of the NN output = Matrix.matrixMultiply(self.weights_ho, hidden) output.add(self.bias_o) output.map(sigmoid) return Matrix.toArray(output) def train(self, input_array, target_array): # Generating the hidden outputs inputs = Matrix.fromArray(input_array) hidden = Matrix.matrixMultiply(self.weights_ih, inputs) hidden.add(self.bias_h) # Activation function hidden.map(sigmoid) # Generating the output of the NN outputs = Matrix.matrixMultiply(self.weights_ho, hidden) outputs.add(self.bias_o) outputs.map(sigmoid) # Convert array to matrix object targets = Matrix.fromArray(target_array) # Calculate the error # ERROR = TARGETS - OUTPUTS output_errors = Matrix.subtract(targets, outputs) # Calculate Gradient Descent gradients = Matrix.mapMatrix(outputs, derivativeSigmoid) # TODO: Aca gradients y output_errors son los dos de 2x1, ver esto bien gradients = Matrix.matrixMultiply(gradients, output_errors) gradients.scalarMultiply(self.learning_rate) self.bias_o.add(gradients) # Calculate hidden->output deltas hidden_t = Matrix.transpose(hidden) weights_ho_deltas = Matrix.matrixMultiply(gradients, hidden_t) # Adjust hidden->output weights self.weights_ho.add(weights_ho_deltas) # Calculate the hidden layer errors weights_ho_t = Matrix.transpose(self.weights_ho) hidden_errors = Matrix.matrixMultiply(weights_ho_t, output_errors) # Calculate hidden gradient hidden_gradient = Matrix.mapMatrix(hidden, derivativeSigmoid) hidden_gradient = Matrix.matrixMultiply(hidden_gradient, hidden_errors) hidden_gradient.scalarMultiply(self.learning_rate) self.bias_h.add(hidden_gradient) # Calculate input->hidden deltas inputs_t = Matrix.transpose(inputs) weights_ih_deltas = Matrix.matrixMultiply(hidden_gradient, inputs_t) # Adjust input->hidden weights self.weights_ih.add(weights_ih_deltas)
class NeuralNetwork(object): def __init__(self, nInputs, nHidden, nOutputs): # learning rate self.learning_rate = 0.1 # nodes self.nInputs = nInputs self.nHidden = nHidden self.nOutputs = nOutputs #self.nHidden = int(15 / (2 * (self.nInputs + self.nOutputs))) # weights self.weights_ih = Matrix(self.nHidden, self.nInputs) self.weights_ho = Matrix(self.nOutputs, self.nHidden) self.weights_ih.randomize() self.weights_ho.randomize() # biases self.bias_h = Matrix(self.nHidden, 1) self.bias_o = Matrix(self.nOutputs, 1) self.bias_h.randomize() self.bias_o.randomize() # Pass inputs through the network def feed_forward(self, array): inputs = Matrix.from_array(array) # Generate hidden outputs hidden = Matrix.dot(self.weights_ih, inputs) hidden.add(self.bias_h) hidden = Matrix.map(hidden, self.sigmoid) # Generate output output = Matrix.dot(self.weights_ho, hidden) output.add(self.bias_o) output = Matrix.map(output, self.sigmoid) return output.to_array() def train(self, inputs_array, targets_array): inputs = Matrix.from_array(inputs_array) # Generate hidden outputs hidden = Matrix.dot(self.weights_ih, inputs) hidden.add(self.bias_h) hidden = Matrix.map(hidden, self.sigmoid) # Generate output outputs = Matrix.dot(self.weights_ho, hidden) outputs.add(self.bias_o) outputs = Matrix.map(outputs, self.sigmoid) targets = Matrix.from_array(targets_array) # Calculate output errors # e = targets - outputs output_errors = Matrix.subtract(targets, outputs) # Calculate hidden layer errors weights_ho_t = Matrix.transpose(self.weights_ho) hidden_errors = Matrix.dot(weights_ho_t, output_errors) # Calculate output deltas gradients = Matrix.map(outputs, self.dsigmoid) gradients.multiply(output_errors) gradients.multiply(self.learning_rate) hidden_T = Matrix.transpose(hidden) weights_ho_deltas = Matrix.dot(gradients, hidden_T) # Adjust output weights&bias self.weights_ho.add(weights_ho_deltas) self.bias_o.add(gradients) # Calculate hidden deltas hidden_gradient = Matrix.map(hidden, self.dsigmoid) hidden_gradient.multiply(hidden_errors) hidden_gradient.multiply(self.learning_rate) inputs_T = Matrix.transpose(inputs) weights_ih_deltas = Matrix.dot(hidden_gradient, inputs_T) # Adjust hidden weights&bias self.weights_ih.add(weights_ih_deltas) self.bias_h.add(hidden_gradient) # Activation function @staticmethod def sigmoid(x): return 1 / (1 + np.exp(-x)) # Activation function derivative @staticmethod def dsigmoid(x): return x * (1 - x)