Commit 801cea03 authored by Guillaume Sabbagh's avatar Guillaume Sabbagh
Browse files

Clusters fonctionnels

parent 79cc5242
This diff is collapsed.
......@@ -97,7 +97,10 @@ class Categorie:
## On vérifie que les identités sont neutres
for morphisme in self(self.objets,self.objets):
if not (morphisme@self.identite(morphisme.source) == self.identite(morphisme.cible)@morphisme == morphisme):
raise Exception("Incoherence Categorie : le morphisme "+str(morphisme)+" est modifie par une identite.")
raise Exception("Incoherence Categorie : le morphisme "+str(morphisme)+" est modifie par une identite.\n"\
+repr(morphisme)+" o "+repr(self.identite(morphisme.source))+" = "+repr(morphisme@self.identite(morphisme.source))+"\n"\
+repr(self.identite(morphisme.cible))+" o "+repr(morphisme)+" = "+repr(self.identite(morphisme.cible)@morphisme)+"\n"+\
repr(morphisme))
## On vérifie l'associativité
for m1,m2,m3 in itertools.product(sorted(self(self.objets,self.objets)),repeat=3):
......
from Categorie import Categorie
import Cluster
from Cluster import ClusterActif,CompositionClustersActifs
from Diagramme import Triangle,DiagrammeIdentite, DiagrammeObjets
import itertools
from Morphisme import Composition,Morphisme
from config import TOUJOURS_VERIFIER_COHERENCE
class CategorieClustersAbstraite(Categorie):
"""Catégorie dont les objets sont des diagrammes Di d'intérêt d'une catégorie C.
Les flèches entre les diagrammes sont des clusters."""
def __init__(self,categorie,representant="Categorie de clusters"):
Categorie.__init__(self,representant)
self.categorie_initiale = categorie
# on ajoute tous les diagrammes constants
self.diagrammes_constants = dict() #{obj:Δ(obj)}
self.cat_cones_cocones = {} #{diagramme:{"cat_cones":CategorieCones,"cat_cocones":CategorieCocones}}
for obj in categorie.objets:
print(obj)
diag_constant = DiagrammeObjets(categorie,[obj])
diag_constant.representant = "C("+str(obj)+")"
self.diagrammes_constants[obj] = diag_constant
self.ajouter_diagramme_interet(diag_constant)
if TOUJOURS_VERIFIER_COHERENCE:
self.verifier_coherence2()
def verifier_coherence2(self):
for A,B,C in itertools.product(self.objets,repeat=3):
for morph1 in self.fleches_elem(A,B,inclure_id=False):
for morph2 in self.fleches_elem(B,C,inclure_id=False):
if Composition(morph1,morph2) not in self.Composee.loi_de_composition:
raise Exception("Incohérence CategorieClustersAbstraite : les morphismes "+str(morph1)+" et "+str(morph2)+" n'ont pas de composée dans la loi de composition")
def ajouter_diagramme_interet(self,diagramme):
if diagramme.cat_cible != self.categorie_initiale:
raise Exception("Incohérence CategorieClustersAbstraite : tentative d'ajout d'un diagramme d'interet qui n'a pas pour cible la meme categorie initiale que les autres diagrammes."+str(diagramme))
self.ajouter_objet(diagramme)
for obj in self.objets:
cluster = self.chercher_clusters(obj,diagramme)
self.ajouter_morphismes(cluster)
if obj != diagramme: #on a déjà fait les flèches de diag vers diag
cluster = self.chercher_clusters(diagramme,obj)
self.ajouter_morphismes(cluster)
for A,B,C in itertools.product(self.objets,repeat=3):
for morph1 in self.fleches_elem(A,B,False):
for morph2 in self.fleches_elem(B,C,False):
composee = self.composer_clusters(morph1,morph2)
for fleche in self.morphismes:
if fleche == composee:
composee = fleche
break
else:
raise Exception("Composition des clusters n'est pas un cluster "+str(morph1)+" "+str(morph2)+" "+str(composee)+"\n"+str(self.morphismes))
diagramme = Triangle(self,[A,B,C],[morph1,morph2,composee])
diagramme.faire_commuter()
def chercher_clusters(self,source,cible):
raise NotImplementedError("Les classes filles doivent implementer la méthode chercher_clusters")
def composer_clusters(self,cluster1,cluster2):
raise NotImplementedError("Les classes filles doivent implementer la méthode composer_clusters")
class CategorieClustersActifs(CategorieClustersAbstraite):
"""Catégorie fleurie où les morphismes sont des bouquets actifs"""
def __init__(self,categorie,representant="Categorie de clusters actifs"):
CategorieClustersAbstraite.__init__(self,categorie,representant)
def chercher_clusters(self,source,cible):
result = ClusterActif(source,cible)
return [result] if result != None else []
def composer_clusters(self,cluster1,cluster2):
result = CompositionClustersActifs(cluster1,cluster2)
return result
def main():
import CategorieAleatoire
import random
import Diagramme
random.seed(196587456841456485485485648564856456565656564516412)
youpi = False
while not youpi:
cat = CategorieAleatoire.CategorieAleaPreOrdre(nb_objets = 5)
diag1 = Diagramme.DiagrammeAlea(cat)
diag2 = Diagramme.DiagrammeAlea(cat)
diag1.transformer_graphviz()
diag2.transformer_graphviz()
# cat_f = CategorieClustersActifs(cat)
# cat_f.transformer_graphviz(complet=True)
# cat_f.ajouter_diagramme_interet(diag1)
# cat_f.transformer_graphviz()
# cat_f.ajouter_diagramme_interet(diag2)
# cat_f.transformer_graphviz()
youpi = False
a = ClusterActif(diag1,diag2)
if a == None:
youpi = True
b = ClusterActif(diag2,diag1)
if b == None:
youpi = True
fonct = diag1.est_homologue_a(diag2)
if fonct == None or len(fonct.cat_source.objets) == 0:
youpi=False
cat.transformer_graphviz(afficher_identites=True)
fonct.transformer_graphviz()
print(a,b,fonct)
b.transformer_graphviz()
# cat = Categorie("3")
# cat.ajouter_objets("ABabC")
# F,G,f,g = [Morphisme('A','C','F'),Morphisme('B','C','G'),Morphisme('a','C','f'),Morphisme('b','C','g')]
# cat.ajouter_morphismes([F,G,f,g])
# diag1 = Diagramme.DiagrammeObjets(cat,"Aa")
# diag2 = Diagramme.DiagrammeObjets(cat,"Bb")
# diag1.transformer_graphviz()
# diag2.transformer_graphviz()
# cat_clusters = CategorieClustersActifs(cat)
# cat_clusters.transformer_graphviz(afficher_identites=True)
# cat_clusters.ajouter_diagramme_interet(diag1)
# cat_clusters.transformer_graphviz(afficher_identites=True)
# cat_clusters.ajouter_diagramme_interet(diag2)
# cat_clusters.transformer_graphviz(afficher_identites=True)
# cat_clusters.csv_loi_de_composition("lois de composition/loi1.csv",';')
# print(diag1.est_homologue_a(diag2))
if __name__ == '__main__':
main()
\ No newline at end of file
from Categorie import Categorie
from CategorieCones import CategorieCones
from CategorieCocones import CategorieCocones
from Bouquet import BouquetsPerceptifs, BouquetsActifs, Bouquets, Bouquet,CompositionBouquets
from Diagramme import Triangle,DiagrammeIdentite, DiagrammeObjets
import itertools
from Morphisme import Composition,Morphisme
from config import TOUJOURS_VERIFIER_COHERENCE
class CategorieFleurieAbstraite(Categorie):
"""Catégorie dont les objets sont des diagrammes Di d'intérêt d'une catégorie C.
Les flèches entre les diagrammes sont des bouquets perceptifs."""
def __init__(self,categorie,representant="Categorie fleurie"):
Categorie.__init__(self,representant)
self.categorie_initiale = categorie
# on ajoute tous les diagrammes constants
self.diagrammes_constants = dict() #{obj:Δ(obj)}
self.cat_cones_cocones = {} #{diagramme:{"cat_cones":CategorieCones,"cat_cocones":CategorieCocones}}
for obj in categorie.objets:
diag_constant = DiagrammeObjets(categorie,[obj])
diag_constant.representant = "C("+str(obj)+")"
self.diagrammes_constants[obj] = diag_constant
self.ajouter_diagramme_interet(diag_constant)
if TOUJOURS_VERIFIER_COHERENCE:
self.verifier_coherence2()
def verifier_coherence2(self):
for A,B,C in itertools.product(self.objets,repeat=3):
for morph1 in self.fleches_elem(A,B,inclure_id=False):
for morph2 in self.fleches_elem(B,C,inclure_id=False):
if Composition(morph1,morph2) not in self.Composee.loi_de_composition:
raise Exception("Incohérence CategorieFleurie : les morphismes "+str(morph1)+" et "+str(morph2)+" n'ont pas de composée dans la loi de composition")
def ajouter_objet(self,objet):
Categorie.ajouter_objet(self,objet)
cat_cones = CategorieCones(objet)
cat_cocones = CategorieCocones(objet)
self.cat_cones_cocones[objet] = {"cat_cones":cat_cones,"cat_cocones":cat_cocones}
def ajouter_diagramme_interet(self,diagramme):
if diagramme.cat_cible != self.categorie_initiale:
raise Exception("Incohérence CategorieFleurie : tentative d'ajout d'un diagramme d'interet qui n'a pas pour cible la meme categorie initiale que les autres diagrammes."+str(diagramme))
self.ajouter_objet(diagramme)
for obj in self.objets:
bouquets = self.chercher_bouquets(obj,diagramme)
self.ajouter_morphismes(bouquets)
if obj != diagramme: #on a déjà fait les flèches de diag vers diag
bouquets = self.chercher_bouquets(diagramme,obj)
self.ajouter_morphismes(bouquets)
for A,B,C in itertools.product(self.objets,repeat=3):
for morph1 in self.fleches_elem(A,B,False):
for morph2 in self.fleches_elem(B,C,False):
composee = CompositionBouquets(morph1,morph2)
for fleche in self.morphismes:
if fleche == composee:
composee = fleche
break
else:
raise Exception("Composition des bouquets n'est pas un bouquet "+str(morph1)+" "+str(morph2)+" "+str(composee)+"\n"+str(self.morphismes))
diagramme = Triangle(self,[A,B,C],[morph1,morph2,composee])
diagramme.faire_commuter()
def chercher_bouquets(self,source,cible):
raise NotImplementedError("Les classes filles doivent implementer la méthode chercher_bouquets")
class CategorieFleurie(CategorieFleurieAbstraite):
"""Catégorie fleurie où les morphismes sont des bouquets"""
def chercher_bouquets(self,source,cible):
return Bouquets(source,cible,self.cat_cones_cocones[source]["cat_cones"],self.cat_cones_cocones[cible]["cat_cones"],
self.cat_cones_cocones[source]["cat_cocones"], self.cat_cones_cocones[cible]["cat_cocones"])
class CategorieFleuriePerceptive(CategorieFleurieAbstraite):
"""Catégorie fleurie où les morphismes sont des bouquets perceptifs"""
def __init__(self,categorie,representant="Categorie fleurie perceptive"):
CategorieFleurieAbstraite.__init__(self,categorie,representant)
def chercher_bouquets(self,source,cible):
return BouquetsPerceptifs(source,cible,self.cat_cones_cocones[source]["cat_cones"],self.cat_cones_cocones[cible]["cat_cones"])
class CategorieFleurieActive(CategorieFleurieAbstraite):
"""Catégorie fleurie où les morphismes sont des bouquets actifs"""
def __init__(self,categorie,representant="Categorie fleurie active"):
CategorieFleurieAbstraite.__init__(self,categorie,representant)
def chercher_bouquets(self,source,cible):
return BouquetsActifs(source,cible,self.cat_cones_cocones[source]["cat_cocones"],self.cat_cones_cocones[cible]["cat_cocones"])
def main():
import CategorieAleatoire
import random
import Diagramme
# random.seed(1918652)
# cat = CategorieAleatoire.CategorieAleaPreOrdre()
# cat.transformer_graphviz(afficher_identites=True)
# cat_f = CategorieFleurieAbstraite(cat)
# cat_f.transformer_graphviz(complet=True)
cat = Categorie("2")
cat.ajouter_objets("AB")
f,g = [Morphisme('A','B','f'),Morphisme('A','B','g')]
cat.ajouter_morphismes([f,g])
diag1 = Diagramme.Fleche(cat,f)
diag2 = Diagramme.Fleche(cat,g)
diag1.transformer_graphviz()
diag2.transformer_graphviz()
cat_fleurie = CategorieFleurieActive(cat)
cat_fleurie.transformer_graphviz(afficher_identites=True)
cat_fleurie.ajouter_diagramme_interet(diag1)
cat_fleurie.transformer_graphviz(afficher_identites=True)
cat_fleurie.ajouter_diagramme_interet(diag2)
cat_fleurie.transformer_graphviz(afficher_identites=True)
cat_fleurie.csv_loi_de_composition("lois de composition/loi1.csv",';')
if __name__ == '__main__':
main()
\ No newline at end of file
......@@ -25,8 +25,8 @@ class CategoriePreordreZigZag(CategoriePreordreEngendree):
objets_a_explorer = {source}
while len(objets_a_explorer) > 0:
explore = objets_a_explorer.pop()
objets_a_explorer |= {morph.cible for morph in self._categorie_initiale(explore,abs(self)) if morph.cible not in objets_atteints}
objets_a_explorer |= {morph.source for morph in self._categorie_initiale(abs(self),explore) if morph.source not in objets_atteints}
objets_a_explorer |= {morph.cible for morph in self._categorie_initiale({explore},abs(self)) if morph.cible not in objets_atteints}
objets_a_explorer |= {morph.source for morph in self._categorie_initiale(abs(self),{explore}) if morph.source not in objets_atteints}
objets_atteints |= objets_a_explorer
return cible in objets_atteints
......
from Categorie import Categorie
from Interaction import Interaction,CategorieInteractions
from Foncteur import Foncteur
from CommaCategorie import ObjetCommaCategorie,CategorieFSous
......@@ -5,7 +6,6 @@ from CategoriePreordreZigZag import CatPZigZag
from Interaction import CategorieInteractions
from config import *
class ProtoClusterActif(Interaction):
"""
Un proto-cluster actif ou simplement protocluster est une interaction G entre deux diagrammes D1:I->C et D2:J->C tel que :
......@@ -15,194 +15,127 @@ class ProtoClusterActif(Interaction):
4) Pour toute flèche h:i'->i dans I et <i,g,j> \in G(i), on a <i',g@h,j> \in G(i')
"""
def __init__(self, D1:Foncteur, D2:Foncteur, composantes:set):
"""composantes est un ensemble d'objets de la comma-catégorie (D1|D2)"""
Interaction.__init__(self,D1, D2, composantes)
if TOUJOURS_VERIFIER_COHERENCE:
ProtoClusterActif.verifier_coherence(self)
def verifier_coherence(self):
D1,D2 = self.source,self.cible
Interaction.verifier_coherence(self)
def verifier_struct(interaction:Interaction) -> tuple:
'''Renvoie (True,None) si la structure de cluster est vérifiée par l'`interaction`, (False,Exception) sinon.'''
D1,D2 = interaction.source,interaction.cible
# contrainte 1) au moins une flèche part de chacun des objets de D1
for e in D1.source.objets:
for composante in self:
for composante in interaction:
if composante.e == e:
break
else:
raise Exception("Incoherence ProtoClusterActif : l'objet "+str(e)+" de l'index de D1 n'a pas de de composante associée.")
return False,Exception("Incoherence ProtoClusterActif : l'objet "+str(e)+" de l'index de D1 n'a pas de de composante associée.")
# contrainte 2) les composantes qui sortent d'un objet D1(i) mènent à des objets D2(j_i) reliés par un zig zag dans la comma catégorie (D1(i)|D2)
for i in D1.source.objets:
G_i = {compo for compo in self if compo.e == i}
G_i = {compo for compo in interaction if compo.e == i}
comma_categorie = CategorieFSous(D2,D1(i))
cat_cc = CatPZigZag(comma_categorie)
# on vérifie que tous les E(e) sont isomorphes dans la catégorie des composantes connexes de la catégorie sous D(d)
composante_reference = G_i.pop()
for composante in G_i:
if not cat_cc.existe_morphisme(composante,composante_reference):
raise Exception("Incoherence ProtoClusterActif : la composante"+str(composante)+" n'est pas dans la même composante connexe que "+str(composante_reference))
return False,Exception("Incoherence ProtoClusterActif : la composante"+str(composante)+" n'est pas dans la même composante connexe que "+str(composante_reference))
# contrainte 3) hog = g'
for composante in self:
for h in D2.source(abs(D2.source),abs(D2.source)):
if ObjetCommaCategorie(composante.e,D2(h)@composante.f,h.cible) not in self:
raise Exception("Incoherence ProtoClusterActif : la composee de la composante "+str(composante)+" avec la fleche "+str(D2(h))+" de D2 n'est pas dans le cluster.")
for composante in interaction:
for h in D2.source({composante.d},abs(D2.source)):
if ObjetCommaCategorie(composante.e,D2(h)@composante.f,h.cible) not in interaction:
return False,Exception("Incoherence ProtoClusterActif : la composee de la composante "+str(composante)+" avec la fleche "+str(D2(h))+" de D2 n'est pas dans le cluster.")
# contrainte 4) goh = g'
for composante in self:
for h in D1.source(abs(D1.source),abs(D1.source)):
if ObjetCommaCategorie(h.source,composante.f@D1(h),composante.d) not in self:
raise Exception("Incoherence ProtoClusterActif : la composee de la fleche "+str(D1(h))+" de D1 avec la composante "+str(composante)+" n'est pas dans le cluster")
for composante in interaction:
for h in D1.source(abs(D1.source),{composante.e}):
if ObjetCommaCategorie(h.source,composante.f@D1(h),composante.d) not in interaction:
return False,Exception("Incoherence ProtoClusterActif : la composee de la fleche "+str(D1(h))+" de D1 avec la composante "+str(composante)+" n'est pas dans le cluster")
return True,None
def __init__(self, D1:Foncteur, D2:Foncteur, composantes:set):
"""composantes est un ensemble d'objets de la comma-catégorie (D1|D2)"""
Interaction.__init__(self,D1, D2, composantes)
if TOUJOURS_VERIFIER_COHERENCE:
ProtoClusterActif.verifier_coherence(self)
class Cluster()
def verifier_coherence(self):
Interaction.verifier_coherence(self)
coherence,exception_levee = ProtoClusterActif.verifier_struct(self)
if not coherence:
raise exception_levee
class CategorieClusters(CategorieInteractions):
"""
CategorieClusters est une catégorie d'organisations où les intéractions sont des clusters.
"""
def __init__(self, univers:Categorie ,objets:set = set(), nom:str = None):
CategorieInteractions.__init__(self,univers,objets,"Catégorie des diagrammes et clusters sur "+str(univers) if nom == None else nom)
def __identite__(self,objet:Diagramme) -> ProtoClusterActif:
class ProtoClustersActifs:
def __init__(self, foncteur1, foncteur2):
self.foncteur1 = foncteur1
self.foncteur2 = foncteur2
if self.foncteur1.cat_cible != self.foncteur2.cat_cible:
raise Exception("Incoherence ClustersActifs : les deux foncteurs n'ont pas la meme image.")
self.categorie = self.foncteur1.cat_cible
self.clusters_actifs = []
# on énumère toutes les flèches de D1 à D2
objets_comma_category = {(i,j):self.categorie.enumerer_composees(self.foncteur1(i),self.foncteur2(j))\
for i in self.foncteur1.source.objets for j in self.foncteur2.source.objets}
fleches = [e for liste in objets_comma_category.values() for e in liste]
cat_cc = {d:CategorieComposantesConnexes(CategorieFSous(self.foncteur2, self.foncteur1(d))) for d in self.foncteur1.cat_source.objets}
# on énumère toutes les interactions de D1 à D2
for nb_fleches in range(1,len(fleches)+1):
for interaction in itertools.combinations(fleches,nb_fleches):
ajouter_cluster = True
# contrainte 1) au moins une flèche part de chacun des objets de D1
for d in self.foncteur1.cat_source.objets:
for composante in interaction:
if composante.source == self.foncteur1(d):
break
else:
ajouter_cluster = False #raise Exception("Incoherence ProtoClusterActif : l'objet "+str(self.foncteur1(d))+" de D1 n'a pas de d'image par le cluster")
if not ajouter_cluster:
continue
# contrainte 2) les composantes qui sortent d'un objet d de D1 mènent à des objets e de D2 reliés par un zig zag dans la catégorie sous d
for d in self.foncteur1.cat_source.objets:
E_e = [] #les images des composantes
for composante in interaction:
if composante.source == self.foncteur1(d):
E_e += [composante]
# on vérifie que tous les E(e) sont isomorphes dans la catégorie des composantes connexes de la catégorie sous D(d)
for e in E_e[1:]: #todo corriger tout ça !!!
for obj1 in cat_cc[d].objets: #todo corriger tout ça !!!
if obj1.f == e:
for obj2 in cat_cc[d].objets:
if obj2.f == E_e[0]:
if cat_cc[d].existe_composee(obj1,obj2) != None:
break
else:
continue
break
else:
ajouter_cluster = False #raise Exception("Incoherence ProtoClusterActif : l'objet "+str(E_e[0])+" n'est pas dans la même composante connexe que "+str(e))
break
else:
continue
break
if not ajouter_cluster:
continue
# contrainte 3) eog = g'
for composante in interaction:
for e in self.foncteur2.cat_source.objets:
if self.foncteur2(e) == composante.cible:
for eps in self.foncteur2.cat_source.morph_sortants[e]:
composee = self.categorie.Composee(composante,self.foncteur2(eps))
if composee not in interaction:
ajouter_cluster = False #raise Exception("Incoherence ProtoClusterActif : la composee de la composante "+str(composante)+" avec la fleche "+str(self.foncteur2(eps))+" de D2 n'est pas dans le cluster")
break
else:
continue
break
def __init__(self, univers:Categorie ,diagrammes:set = set(), nom:str = None):
"""
CategorieClusters est la catégorie dont les objets sont des diagrammes de cible `univers` et les morphismes sont des clusters.
Par défaut, on considère pour chaque objet O de l'`univers` le diagramme 1_O qui associe à un objet l'objet O.
On retrouve ainsi l'`univers` dans la catégorie des clusters.
`diagrammes` est un ensemble de diagrammes d'intérêts à ajouter à la catégorie.
"""
CategorieInteractions.__init__(self,univers,diagrammes,"Catégorie des diagrammes et clusters sur "+str(univers) if nom == None else nom)
def identite(self,objet:Foncteur) -> ProtoClusterActif:
interactions = sorted(CategorieInteractions.__call__(self,{objet},{objet}),key=len,reverse=True)
identite_candidate = None
for interact in interactions:
if ProtoClusterActif.verifier_struct(interact)[0]:
if identite_candidate != None:
if len(interact) < identite_candidate:
return identite_candidate
else:
continue
break
if not ajouter_cluster:
continue
# contrainte 4) god = g'
for composante in interaction:
for d in self.foncteur1.cat_source.objets:
if self.foncteur1(d) == composante.source:
for delta in self.foncteur1.cat_source.morph_entrants[d]:
composee = self.categorie.Composee(self.foncteur1(delta),composante)
if composee not in interaction:
ajouter_cluster = False #raise Exception("Incoherence ProtoClusterActif : la composee de la fleche "+str(self.foncteur1(delta))+" de D1 avec la composante "+str(composante)+" n'est pas dans le cluster")
break
raise Exception("Plusieurs identites possibles pour "+str(objet)+" :\n"+str(identite_candidate)+"\n"+str(interact))
else:
continue
identite_candidate = interact
if identite_candidate == None:
raise Exception("Pas d'identite trouvee pour "+str(objet))
return identite_candidate
def __call__(self, sources:set, cibles:set) -> set:
result = set()
for source in sources:
for cible in cibles:
interactions = sorted(CategorieInteractions.__call__(self,{source},{cible}),key=len,reverse=True)
proto_cluster_maximaux = []
for interact in interactions:
if len(proto_cluster_maximaux) > 0 and len(interact) < len(proto_cluster_maximaux[0]):
# on a trouvé des proto-clusters et on examine maintenant des proto-clusters plus petits (qui ne seront pas maximaux)
break
else:
continue
break
if not ajouter_cluster:
continue
self.clusters_actifs += [ProtoClusterActif(self.foncteur1,self.foncteur2,interaction)]
if ProtoClusterActif.verifier_struct(interact)[0]:
proto_cluster_maximaux += [interact]
result |= set(proto_cluster_maximaux)
return result
def transformer_graphviz(self):
for cluster in self.clusters_actifs:
cluster.transformer_graphviz()
def __getitem__(self,key):
return self.clusters_actifs[key]
def __iter__(self):
for cluster in self.clusters_actifs:
yield cluster
def __len__(self):
return len(self.clusters_actifs)
def main():
from GrapheDeComposition import GC,MGC
from Diagramme import DiagrammeObjets,Fleche
gc = GC()
gc |= {'A','B','C'}
morphismes = [MGC('A','B','f'),MGC('B','C','g'),MGC('A','C','h')]
gc |= morphismes
gc.transformer_graphviz()
c_i = CategorieClusters(gc)
c_i.transformer_graphviz(afficher_identites=True)
def main():
from Categorie import Categorie
from Morphisme import Morphisme
from Foncteur import Foncteur
cat = Categorie()
cat.ajouter_objets("ABCDO")
f,g,h,i,j,k,l,m = [Morphisme('O','A','f'),Morphisme('O','B','g'),Morphisme('A','B','h'),Morphisme('O','C','i'),Morphisme('O','D','j'),Morphisme('C','D','k'),Morphisme('B','C','l'),Morphisme('A','D','m')]
cat.ajouter_morphismes([f,g,h,i,j,k,l,m])
from CategoriePreordre import CategoriePreordre
cat2 = CategoriePreordre(cat)
n,o = [Morphisme('O','A','n'),Morphisme('O','B','o')]
cat2.ajouter_morphismes([n,o])
cat2.transformer_graphviz()
cat_fleche = Categorie()
cat_fleche.ajouter_objets("AB")
a = Morphisme('A','B','a')
cat_fleche.ajouter_morphismes([a])
fonct1 = Foncteur(cat_fleche,cat2,{'A':'A','B':'B'},{a:h})
fonct2 = Foncteur(cat_fleche,cat2,{'A':'C','B':'D'},{a:k})
fonct1.transformer_graphviz()
fonct2.transformer_graphviz()
cluster = ClusterActif(fonct1,fonct2)
cluster.transformer_graphviz()
c_i |= {DiagrammeObjets(gc,{'A','B'})}
c_i.transformer_graphviz(afficher_identites=True)
c_i |= {Fleche(gc,morphismes[0])}
c_i.transformer_graphviz(afficher_identites=True)
c_i.identite(Fleche(gc,morphismes[0])).transformer_graphviz(afficher_identites=True)
for cluster in c_i({DiagrammeObjets(gc,{'A','B'})},{DiagrammeObjets(gc,{'C'})}):
cluster.transformer_graphviz(afficher_identites=True)
if __name__ == '__main__':
main()
\ No newline at end of file
from config import *
if GRAPHVIZ_ENABLED:
from graphviz import Digraph
class Cocone():