Commit dec2092a authored by Bram Schoenmakers's avatar Bram Schoenmakers

Get rid of numbers map, look it up directly from the array.

Also modify the keys for the dependency graph, use the hashed version of
the todo instead of its position.
The position may shift when deleting tasks, which affects the consistency
of the dependency graph.
parent c0ab5647
...@@ -24,7 +24,6 @@ class TodoList(object): ...@@ -24,7 +24,6 @@ class TodoList(object):
The string will be parsed. The string will be parsed.
""" """
self._todos = [] self._todos = []
self._numbers = {} # maintains todo -> number mapping
self._depgraph = Graph.DirectedGraph() self._depgraph = Graph.DirectedGraph()
for string in p_todostrings: for string in p_todostrings:
...@@ -46,6 +45,18 @@ class TodoList(object): ...@@ -46,6 +45,18 @@ class TodoList(object):
return result return result
def todo_by_hash(self, p_hash):
"""
Given the hash value of a todo, return the corresponding hash instance.
"""
result = None
for todo in self._todos:
if hash(todo) == p_hash:
result = todo
break
return result
def todo_by_dep_id(self, p_dep_id): def todo_by_dep_id(self, p_dep_id):
""" """
Returns the todo that has the id tag set to the value p_dep_id. Returns the todo that has the id tag set to the value p_dep_id.
...@@ -65,19 +76,19 @@ class TodoList(object): ...@@ -65,19 +76,19 @@ class TodoList(object):
dep_id = p_todo.tag_value('id') dep_id = p_todo.tag_value('id')
# maintain dependency graph # maintain dependency graph
if dep_id: if dep_id:
self._depgraph.add_node(self.number(p_todo)) self._depgraph.add_node(hash(p_todo))
# connect all tasks we have in memory so far that refer to this # connect all tasks we have in memory so far that refer to this
# task # task
for dep in \ for dep in \
[dep for dep in self._todos if dep.has_tag('p', dep_id)]: [dep for dep in self._todos if dep.has_tag('p', dep_id)]:
self._depgraph.add_edge(self.number(p_todo), self.number(dep), dep_id) self._depgraph.add_edge(hash(p_todo), hash(dep), dep_id)
for child in p_todo.tag_values('p'): for child in p_todo.tag_values('p'):
parent = self.todo_by_dep_id(child) parent = self.todo_by_dep_id(child)
if parent: if parent:
self._depgraph.add_edge(self.number(parent), self.number(p_todo), child) self._depgraph.add_edge(hash(parent), hash(p_todo), child)
def add(self, p_src): def add(self, p_src):
""" Given a todo string, parse it and put it to the end of the list. """ """ Given a todo string, parse it and put it to the end of the list. """
...@@ -105,7 +116,6 @@ class TodoList(object): ...@@ -105,7 +116,6 @@ class TodoList(object):
Then there will be an edge 1 --> 2 with ID 4. Then there will be an edge 1 --> 2 with ID 4.
""" """
self._numbers[p_todo] = len(self._todos) + 1
self._todos.append(p_todo) self._todos.append(p_todo)
self._maintain_dep_graph(p_todo) self._maintain_dep_graph(p_todo)
...@@ -124,7 +134,6 @@ class TodoList(object): ...@@ -124,7 +134,6 @@ class TodoList(object):
self.remove_dependency(self.number(parent), self.number(todo)) self.remove_dependency(self.number(parent), self.number(todo))
del self._todos[p_number - 1] del self._todos[p_number - 1]
del self._numbers[todo]
self.dirty = True self.dirty = True
...@@ -189,9 +198,9 @@ class TodoList(object): ...@@ -189,9 +198,9 @@ class TodoList(object):
return '%d' % new_id return '%d' % new_id
if not self._depgraph.has_edge(p_number1, p_number2):
from_todo = self.todo(p_number1) from_todo = self.todo(p_number1)
to_todo = self.todo(p_number2) to_todo = self.todo(p_number2)
if not self._depgraph.has_edge(hash(from_todo), hash(to_todo)):
if not from_todo or not to_todo: if not from_todo or not to_todo:
return return
...@@ -204,7 +213,7 @@ class TodoList(object): ...@@ -204,7 +213,7 @@ class TodoList(object):
from_todo.set_tag('id', dep_id) from_todo.set_tag('id', dep_id)
to_todo.add_tag('p', dep_id) to_todo.add_tag('p', dep_id)
self._depgraph.add_edge(p_number1, p_number2, dep_id) self._depgraph.add_edge(hash(from_todo), hash(to_todo), dep_id)
self._update_parent_cache() self._update_parent_cache()
self.dirty = True self.dirty = True
...@@ -220,7 +229,7 @@ class TodoList(object): ...@@ -220,7 +229,7 @@ class TodoList(object):
if dep_id: if dep_id:
to_todo.remove_tag('p', dep_id) to_todo.remove_tag('p', dep_id)
self._depgraph.remove_edge(p_number1, p_number2) self._depgraph.remove_edge(hash(from_todo), hash(to_todo))
self._update_parent_cache() self._update_parent_cache()
if not self.children(p_number1, True): if not self.children(p_number1, True):
...@@ -233,17 +242,19 @@ class TodoList(object): ...@@ -233,17 +242,19 @@ class TodoList(object):
Returns a list of parent todos that (in)directly depend on the Returns a list of parent todos that (in)directly depend on the
given todo. given todo.
""" """
parents = self._depgraph.incoming_neighbors(p_number, not p_only_direct) todo = self.todo(p_number)
return [self.todo(parent) for parent in parents] parents = self._depgraph.incoming_neighbors(hash(todo), not p_only_direct)
return [self.todo_by_hash(parent) for parent in parents]
def children(self, p_number, p_only_direct=False): def children(self, p_number, p_only_direct=False):
""" """
Returns a list of child todos that the given todo (in)directly depends Returns a list of child todos that the given todo (in)directly depends
on. on.
""" """
todo = self.todo(p_number)
children = \ children = \
self._depgraph.outgoing_neighbors(p_number, not p_only_direct) self._depgraph.outgoing_neighbors(hash(todo), not p_only_direct)
return [self.todo(child) for child in children] return [self.todo_by_hash(child) for child in children]
def clean_dependencies(self): def clean_dependencies(self):
""" """
...@@ -293,7 +304,7 @@ class TodoList(object): ...@@ -293,7 +304,7 @@ class TodoList(object):
self.dirty = True self.dirty = True
def number(self, p_todo): def number(self, p_todo):
return self._numbers[p_todo] return self._todos.index(p_todo) + 1
def pp_number(self): def pp_number(self):
""" """
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment