2017-05-17 6 views
1

Je souhaite conserver les propriétés externes pour les sommets et les arêtes d'un graphe adjacency_list (et pour les groupes de sommets). Je dois pouvoir accéder aux vertices par leurs propriétés. Par exemple, je voudrais parcourir tous les sommets affectés d'un poids et obtenir leurs bords sortants.ids de sommets constants dans adjacency_list

Cependant, j'ai aussi besoin que mon conteneur vertex soit défini. Dans ce conteneur, ajouter \ supprimer un sommet peut invalider les descripteurs de sommet.

Le problème est que les propriétés externes peuvent maintenant être mappées à vertex_descriptors invalides.

class manage_data { 
... 
    auto get_interesting(int weight) { 
     return ver_by_weight.equal_range(weight); 
    } 
    void do_stuff (...) { 
     auto for_later_use = get_interesting(); 
     ... 
     boost::remove_vertex(unrelated_vertex, graph_); 
     ... 
     use_vec(for_later_use.front()); //bug 
    } 
    } 

Une approche semble être d'ajouter une propriété vertex_index. Cela ne fonctionne pas, car il est un directionnel - vous pouvez obtenir le vertex_index via le vertex_descriptor, mais pas l'inverse. Cela signifie que je ne peux pas ajouter d'arête entre deux sommets dont je connais seulement l'index.

Une autre solution prometteuse était l'utilisation d'un graphe marqué. Ce graphique ne peut ajouter des arêtes que par des étiquettes. J'aurais pu aller assez loin en stockant des données externes avec un identifiant d'étiquette. Malheureusement, toute l'interface adjacency_list n'est pas réimplémentée en utilisant des étiquettes - par ex. out_edges. Cela signifie que je dois toujours être en mesure d'accéder au descripteur de vertex, et il est impossible (en un temps raisonnable) d'utiliser uniquement l'étiquette, comme on peut le voir here

Une solution encore meilleure serait de combiner les deux - avoir une propriété vertex_label. Cela semble trop complexe, et cela ne fonctionne pas (exemple ci-dessus).

Ne devrait-il pas être courant que les sommets se rapportent à des données externes? Comment peux-tu le faire?

+0

"tous les sommets ont un poids" - vouliez-vous dire les bords? – sehe

+0

non, comme dans l'exemple de code - ver_by_weight.equal_range (weight). – bravesirrobin

Répondre

0

Vous pouvez utiliser un mappage bidirectionnel du descripteur de vertex vers votre propre ID. Maintenant, tant que vous utilisez un sélecteur de conteneur basé sur un nœud pour le conteneur vertex, vous êtes tous définis.

Jetez un oeil à BiMap et peut-être transform_value_property_map pour un confort maximum (bien que vous pourriez ne pas exiger que toutes les fantaisies surtout si le graphique est en lecture seule la plupart du temps - ou réduire uniquement par exemple)

Voir aussi

+0

Comment puis-je utiliser un mappage bidirectionnel lorsque le descripteur de vertex devient invalide? Je ne peux utiliser que des propriétés internes, donc la classe graphique mettra à jour mon descripteur de vertex. Est-ce que BGL a une propriété bidirectionnelle interne? – bravesirrobin

+0

Qu'est-ce qu'un sélecteur de conteneur basé sur un nœud? :) – bravesirrobin

+0

Le nœud est basé lorsque l'allocation de la structure de données utilise des nœuds. Donc, 'listS' ou' setS' ferait l'affaire. "quand le descripteur de vertex devient invalide" - ils ne le sont pas lors de l'utilisation de ces conteneurs à base de nœuds. (¹ Seuls les descripteurs réellement effacés deviennent invalides) – sehe