Quello che vorrei fare è il seguente.
(Non sono sicuro se questa domanda dovrebbe andare a StackOverflow, o qui)
Considera una struttura dati come questa:
interface IAction {
IAction[] afterActions()
IAction[] beforeActions()
void execute()
}
Quello che mi piacerebbe fare è execute()
a IAction
collection, nel modo in cui
- Tutte le
beforeActions()
vengono eseguite prima che il fornitore dellabeforeActions()
invochi il risultato. - Tutti
afterActions()
vengono eseguiti dopo che il fornitore delafterActions()
chiama risultato. - Essere in grado di rilevare "dipendenze cicliche", quindi se si deve eseguire prima e dopo un'altra, o dopo di sé, o dopo un'altra azione, quella su qualsiasi percorso deve essere eseguita prima, ecc.
In altri mondi vorrei "ordinare" queste azioni in un ordine eseguibile.
Mi piacerebbe avere solo una spiegazione su come dovrei (potrei) fare questo, non mi aspetto che qualcuno possa implementare qualcosa per me (nota che non ho intenzionalmente specificato una lingua).
Se conosci qualche algoritmo generico per questo scopo, che ritieni sia adatto al problema, non esitare a condividere con una spiegazione minima, su come lo traducesti in questo problema
Modifica
Dopo aver riflettuto molto sul problema, ho capito che per quanto riguarda la dipendenza, afterActions()
è assolutamente inutile (un'azione non dovrebbe sapere cosa viene eseguito dopo, dovrebbe solo descrivere ciò che deve essere completato prima , per eseguire correttamente). Sapendo questo ho finito per fare qualcosa di simile a ciò che @Rafael Eyng ha suggerito:
Ho creato un Iterator
, che ha avvolto la raccolta originale e ha avuto un next()
, che ha sempre restituito l'azione successiva (risolta). L'iteratore non era stateless, aveva un riferimento alla collezione con tutte le azioni e aveva una (crescente) Set
di azioni, che sono state risolte. Per ottenere ciò, ogni volta che è stato chiamato next()
ho fatto quanto segue:
- Esegui l'iter su tutte le azioni
- Se uno non ha dipendenze o tutte sono incluse nell'elenco già risolto, può essere restituito come dopo.
- Se ha delle dipendenze, fallo in modo ricorsivo per tutti i prerequisiti.
- Stavo anche raccogliendo le azioni già visitate, dalla radice della chiamata ricorsiva, in modo che i cicli potessero essere rilevati