diff --git a/README.md b/README.md index 303f968..322db94 100644 --- a/README.md +++ b/README.md @@ -5,4 +5,7 @@ Code Fellows Dev Accelerator: This repository will be for implementations of cla parens.py: -Includes a function balanceness() that takes string and determines if it is 'open', 'balanced', or 'broken', depending on the sequence of parenthesis contained. 'Open', 'balanced', and 'broken' are respectively determined as more leading '('s than ')'s, equal number of leading '(' and ')', and any sequence including ')' that do not have a preceding '('. 'Open' strings are represented by returning a 1, 'balanced' by 0, and 'broken' by -1, with an emptry string being considered 'balanced'. \ No newline at end of file +Includes a function balanceness() that takes string and determines if it is 'open', 'balanced', or 'broken', depending on the sequence of parenthesis contained. 'Open', 'balanced', and 'broken' are respectively determined as more leading '('s than ')'s, equal number of leading '(' and ')', and any sequence including ')' that do not have a preceding '('. 'Open' strings are represented by returning a 1, 'balanced' by 0, and 'broken' by -1, with an emptry string being considered 'balanced'. + +Shortest-path algorithms: +Making a decision regarding which algorithm to use to implement finding the 'shortest-path' between two vertices in a graph will probably be motivated by the nature of the use. For problems where edges represent either a cost, difficulty or some other deterrent of 'traveling' from one node to another, location or some state, then Djikstra's algorithm or some other which simply minimize the total weight of a single path, will do just fine. However, if perhaps you are interested in knowing the 'shortest-path' between all points, then perhaps the Floyd-Warshall would be more appropriate, or if speed of determination of path was important, than maybe yet another algorithm would be more appropriate. \ No newline at end of file diff --git a/graph.py b/graph.py index 4f46c19..9813fa1 100644 --- a/graph.py +++ b/graph.py @@ -129,6 +129,9 @@ def breadth_iterator(self, children, grandchildren, result): return grandchildren, result def dijkstra(self, start, end): + """ + Find a path always using smallest weight and return the path and weight + """ # set a temp current value to start current = start path = [start] @@ -149,13 +152,18 @@ def dijkstra(self, start, end): return path, path_weight def find_paths(self, start, end, result=[], path=[]): - if start is end: # found + """ + Find all paths possible with a start and an end nodes + + and return a list with possibles path inside + """ + if start is end: path.append(end) result.append(path[:]) path.pop() - elif start not in path: # not loop - if self.g[start]: # not empty + elif start not in path: + if self.g[start]: path.append(start) for edge_node, weight in self.g[start]: self.find_paths(edge_node, end, result, path) @@ -164,10 +172,11 @@ def find_paths(self, start, end, result=[], path=[]): return result def get_path_weight(self, path): + """ + Return the weight of a path when giving the path as a list + """ weight = 0 - # for index, node in enumerate(path)[:-1]: - # weight += self.g[node][path[index + 1][1]] - for num in range(len(path)-1): + for num in range(len(path) - 1): n1 = path[num] n2 = path[num + 1] for node in self.g[n1]: @@ -177,6 +186,9 @@ def get_path_weight(self, path): return weight def find_shortest_path(self, start, end): + """ + Return the shortest path to two nodes and the weight of the path + """ paths = self.find_paths(start, end, [], []) weight = float('inf') shortest_path = [] diff --git a/test_graph.py b/test_graph.py index 0f67048..ce4e446 100644 --- a/test_graph.py +++ b/test_graph.py @@ -208,6 +208,9 @@ def popd_graph_weighted(request): def test_djkst_short(): + """ + Test for a short path has lowest weight graph with Dijkstra + """ g = Graph() g.add_node('a') g.add_edge('a', 'b', 9) @@ -222,8 +225,10 @@ def test_djkst_short(): assert g.dijkstra('a', 'd') == (['a', 'e', 'd'], 4) - def test_djkst_long(): + """ + Test for a long path has lowest weight graph with Dijkstra + """ g = Graph() g.add_node('a') g.add_edge('a', 'b', 1) @@ -239,6 +244,9 @@ def test_djkst_long(): def test_djkst_loop(): + """ + Test a graph with a loop with Dijkstra + """ g = Graph() g.add_node('a') g.add_edge('a', 'b', 1) @@ -246,9 +254,13 @@ def test_djkst_loop(): g.add_edge('b', 'c', 12345) assert g.dijkstra('a', 'c') == (['a', 'b', 'c'], 12346) + assert g.dijkstra('a', 'a') == (['a'], 0) def test_find_paths(): + """ + Test find path, get path weight and the shortest path + """ g = Graph() g.add_edge('a', 'b', 1) g.add_edge('b', 'c', 1) @@ -258,8 +270,10 @@ def test_find_paths(): assert g.get_path_weight(['a','b','c']) == 2 assert g.find_shortest_path('a', 'c') == (['a', 'c'], 1) - def test_real_short(): + """ + Test with the shortest path having the lowest weight + """ g = Graph() g.add_node('a') g.add_edge('a', 'b', 9) @@ -272,11 +286,13 @@ def test_real_short(): g.add_edge('e', 'f', 3) g.add_edge('f', 'a', 8) - print g.find_paths('a','d',[],[]) assert g.find_shortest_path('a', 'd') == (['a', 'e', 'd'], 4) def test_real_long(): + """ + Test the longest path having the shortest weight + """ g = Graph() g.add_node('a') g.add_edge('a', 'b', 1) @@ -289,20 +305,12 @@ def test_real_long(): g.add_edge('f', 'd', 1) assert g.find_shortest_path('a', 'd') == (['a', 'b', 'c', 'e', 'f', 'd'], 5) - -def test_short(): - g = Graph() - g.add_edge('a', 'b', 1) - g.add_edge('b', 'd', 1) - g.add_edge('a', 'c', 1) - g.add_edge('c', 'd', 3) - g.add_edge('d', 'e', 1) - assert g.find_shortest_path('a', 'e') == (['a','b','d','e'], 3) - - - + assert g.find_shortest_path('a', 'a') == (['a'], 0) def test_real_loop(): + """ + Test shortest_path with a loop + """ g = Graph() g.add_node('a') g.add_edge('a', 'b', 1)