[Fix] Simplify Depth adjustment (#386)

Co-authored-by: Tim Lorsbach <tim@lorsba.ch>
Reviewed-on: enviPath/enviPy#386
This commit is contained in:
2026-05-12 21:04:56 +12:00
parent b39fc7eaf8
commit 1e43c298d2

View File

@ -2179,18 +2179,20 @@ class Pathway(EnviPathModel, AliasMixin, ScenarioMixin, AdditionalInformationMix
return Edge.create(self, start_nodes, end_nodes, rule, name=name, description=description) return Edge.create(self, start_nodes, end_nodes, rule, name=name, description=description)
def update_depths(self): def update_depths(self):
# Collect number of in and out links per node
in_count = defaultdict(lambda: 0) in_count = defaultdict(lambda: 0)
out_count = defaultdict(lambda: 0) out_count = defaultdict(lambda: 0)
for e in self.edges: for e in self.edges:
# TODO check if this will remain
for react in e.start_nodes.all(): for react in e.start_nodes.all():
out_count[str(react.uuid)] += 1 out_count[str(react.uuid)] += 1
for prod in e.end_nodes.all(): for prod in e.end_nodes.all():
in_count[str(prod.uuid)] += 1 in_count[str(prod.uuid)] += 1
root_nodes = [] depth_map = {}
depth_map[0] = list()
for n in self.nodes: for n in self.nodes:
num_parents = in_count[str(n.uuid)] num_parents = in_count[str(n.uuid)]
if num_parents == 0: if num_parents == 0:
@ -2201,28 +2203,30 @@ class Pathway(EnviPathModel, AliasMixin, ScenarioMixin, AdditionalInformationMix
# Only root node may have children # Only root node may have children
if out_count[str(n.uuid)] > 0: if out_count[str(n.uuid)] > 0:
root_nodes.append(n) depth_map[0].append(n)
levels = [root_nodes] # At most depth len(nodes) is possible
seen = set() for i in range(self.nodes.count()):
# Do a bfs to determine depths starting with level 0 a.k.a. root nodes level_nodes = depth_map.get(i, [])
for i, level_nodes in enumerate(levels):
new_level = [] if len(level_nodes) == 0:
break
unique_next_level = set()
for n in level_nodes: for n in level_nodes:
for e in n.out_edges.all(): for e in self.edges:
for prod in e.end_nodes.all(): if n in e.start_nodes.all():
if str(prod.uuid) not in seen: for p in e.end_nodes.all():
old_depth = prod.depth unique_next_level.add(p)
if old_depth != i + 1:
prod.depth = i + 1
prod.save()
new_level.append(prod) if len(unique_next_level) > 0:
depth_map[i + 1] = list(unique_next_level)
seen.add(str(n.uuid)) for depth, nodes in depth_map.items():
for n in nodes:
if new_level: if n.depth != depth:
levels.append(new_level) n.depth = depth
n.save()
class Node(EnviPathModel, AliasMixin, ScenarioMixin, AdditionalInformationMixin): class Node(EnviPathModel, AliasMixin, ScenarioMixin, AdditionalInformationMixin):