131 lines
4 KiB
Python
131 lines
4 KiB
Python
![]() |
from extensions.list import CoreList
|
||
|
from itertools import repeat
|
||
|
|
||
|
|
||
|
class AllSequencesModel:
|
||
|
"""
|
||
|
A class that processes information from the assembly and creates the objects necessary to create the assembly sequence
|
||
|
|
||
|
"""
|
||
|
|
||
|
all_sequences = None
|
||
|
adj_matrix = None
|
||
|
topologyIds = None
|
||
|
adj_matrix_names = None
|
||
|
|
||
|
def __init__(self, adj_matrix, restrictions: list[str]) -> None:
|
||
|
self.adj_matrix = adj_matrix
|
||
|
self.all_possible_sequences(self.adj_matrix)
|
||
|
self.matrix_by_name()
|
||
|
if restrictions.__len__() != 0:
|
||
|
self.restrictionsValidate(restrictions)
|
||
|
pass
|
||
|
|
||
|
def restrictionsValidate(self, restrictions: CoreList[str]):
|
||
|
"""_summary_
|
||
|
|
||
|
Args:
|
||
|
restrictions (CoreList[str]): _description_
|
||
|
"""
|
||
|
filterMatrix = CoreList()
|
||
|
|
||
|
for el in self.adj_matrix_names:
|
||
|
result = False
|
||
|
for restraint in restrictions:
|
||
|
result = CoreList(el).indexedPriorities(restraint[0], restraint[1])
|
||
|
if result:
|
||
|
filterMatrix.onlyUniqueElementAppend(el)
|
||
|
self.adj_matrix_names = filterMatrix
|
||
|
pass
|
||
|
|
||
|
def matrix_by_name(self):
|
||
|
result = self.all_sequences
|
||
|
inc = 0
|
||
|
for matrix in self.all_sequences:
|
||
|
for index in range(len(matrix)):
|
||
|
result[inc][index] = CoreList(
|
||
|
filter(
|
||
|
lambda el: el.get("number") == matrix[index] + 1,
|
||
|
self.topologyIds,
|
||
|
)
|
||
|
)[0].get("name")
|
||
|
inc += 1
|
||
|
self.adj_matrix_names = result
|
||
|
pass
|
||
|
|
||
|
def find_all_sequences(self, adj_matrix):
|
||
|
"""Find all assembly sequences with dfs
|
||
|
|
||
|
Args:
|
||
|
adj_matrix (dict): Assembly ajacency matrix
|
||
|
"""
|
||
|
sequences = []
|
||
|
num_vertices = len(adj_matrix)
|
||
|
|
||
|
def dfs(vertex, sequence):
|
||
|
sequence.append(vertex)
|
||
|
|
||
|
if len(sequence) == num_vertices:
|
||
|
sequences.append(sequence)
|
||
|
return
|
||
|
|
||
|
for i in range(num_vertices):
|
||
|
if adj_matrix[vertex][i] == 1 and i not in sequence:
|
||
|
dfs(i, sequence.copy())
|
||
|
|
||
|
for i in range(num_vertices):
|
||
|
dfs(i, [])
|
||
|
|
||
|
self.all_sequences = sequences
|
||
|
|
||
|
def findId(self, listMatrix, id):
|
||
|
def filter_odd_num(in_num):
|
||
|
if in_num["name"] == id:
|
||
|
return True
|
||
|
else:
|
||
|
return False
|
||
|
|
||
|
return list(filter(filter_odd_num, listMatrix))[0]["number"]
|
||
|
|
||
|
def iter_paths(self, adj, min_length=6, path=None):
|
||
|
if not path:
|
||
|
for start_node in range(len(adj)):
|
||
|
yield from self.iter_paths(adj, min_length, [start_node])
|
||
|
else:
|
||
|
if len(path) >= min_length:
|
||
|
yield path
|
||
|
if path[-1] in path[:-1]:
|
||
|
return
|
||
|
current_node = path[-1]
|
||
|
for next_node in range(len(adj[current_node])):
|
||
|
if adj[current_node][next_node] == 1:
|
||
|
yield from self.iter_paths(adj, min_length, path + [next_node])
|
||
|
|
||
|
def allUnique(self, x):
|
||
|
seen = set()
|
||
|
return not any(i in seen or seen.add(i) for i in x)
|
||
|
|
||
|
def all_possible_sequences(self, matrix):
|
||
|
topologyIds = []
|
||
|
topologyMatrixNumber = {}
|
||
|
inc = 0
|
||
|
for k, v in matrix.items():
|
||
|
inc += 1
|
||
|
topologyIds.append({"name": k, "number": inc})
|
||
|
inc = 0
|
||
|
for k, v in matrix.items():
|
||
|
inc += 1
|
||
|
topologyMatrixNumber[inc] = list(
|
||
|
map(lambda el: self.findId(topologyIds, el), v)
|
||
|
)
|
||
|
self.topologyIds = topologyIds
|
||
|
adj = []
|
||
|
matrixSize = matrix.keys().__len__()
|
||
|
inc = 0
|
||
|
for k, v in topologyMatrixNumber.items():
|
||
|
adj.append(list(repeat(0, matrixSize)))
|
||
|
for el in v:
|
||
|
adj[inc][el - 1] = 1
|
||
|
inc += 1
|
||
|
return self.find_all_sequences(adj)
|