首先,您必须将属性映射传递给 dynamic_properties:
dpDual.property("Color_1", vOne); // or maaaaybe
dpDual.property("Color_1", boost::get(vertex_one, g));
其次,Graphviz 本质上是一种文本格式。您是否为Color* 定义了文本转换?如果没有,您希望如何呈现这些属性?
简单的解决方案
为什么是属性指针? Color* 比 Color 更浪费(int 可能比指针小)。
你可以抛开所有的生活问题,实现你的愿望:
inline static std::ostream& operator<<(std::ostream& os, Color color) {
return os << static_cast<int>(color);
}
inline static std::istream& operator>>(std::istream& is, Color& color) {
int dummy;
is >> dummy;
color = static_cast<Color>(dummy);
return is;
}
见Live On Coliru
#include <boost/graph/adjacency_list.hpp>
#include <boost/graph/graphviz.hpp>
#include <boost/graph/random.hpp>
#include <random>
#include <iostream>
typedef enum { UNSET = 0, RED = 1, GREEN = 2, BLUE = 3} Color;
enum vertex_one_t { vertex_one };
namespace boost { BOOST_INSTALL_PROPERTY(vertex, one); }
enum vertex_two_t { vertex_two };
namespace boost {
BOOST_INSTALL_PROPERTY(vertex, two);
}
enum vertex_three_t { vertex_three };
namespace boost {
BOOST_INSTALL_PROPERTY(vertex, three);
}
typedef boost::property< boost::vertex_index_t, int,
boost::property< vertex_one_t, Color,
boost::property< vertex_two_t, Color,
boost::property< vertex_three_t, Color > > > > DualVertexProperty;
inline static std::ostream& operator<<(std::ostream& os, Color color) {
return os << static_cast<int>(color);
}
inline static std::istream& operator>>(std::istream& is, Color& color) {
int dummy;
is >> dummy;
color = static_cast<Color>(dummy);
return is;
}
int main() {
using DualGraph = boost::adjacency_list< boost::vecS, boost::vecS, boost::directedS, DualVertexProperty, boost::no_property>;
boost::dynamic_properties dpDual;
DualGraph g;
std::mt19937 rng { std::random_device{}() };
boost::generate_random_graph(g, 5, 5, rng);
boost::property_map<DualGraph, boost::vertex_index_t>::type vIndex = boost::get(boost::vertex_index, g);
boost::property_map<DualGraph, vertex_one_t>::type vOne = boost::get(vertex_one, g);
dpDual.property("node_id", vIndex);
dpDual.property("Color_1", vOne);
boost::write_graphviz_dp(std::cout, g, dpDual);
}
更复杂
您可以(尝试)使指针可流式传输,但您必须想办法让生命周期和所有权变得有意义。
奖金:
考虑捆绑属性。除非您有非常具体的要求,否则无需像您的代码那样继续使用过时的内部属性。
Live On Coliru(编译超时)
#include <boost/graph/adjacency_list.hpp>
#include <boost/graph/graphviz.hpp>
#include <boost/graph/random.hpp>
#include <random>
#include <iostream>
typedef enum { UNSET = 0, RED = 1, GREEN = 2, BLUE = 3} Color;
struct DualVertexProperty {
Color one, two, three;
};
inline static std::ostream& operator<<(std::ostream& os, Color color) { return os << static_cast<int>(color); }
inline static std::istream& operator>>(std::istream& is, Color& color) { int dummy; is >> dummy; color = static_cast<Color>(dummy); return is; }
int main() {
using DualGraph = boost::adjacency_list< boost::vecS, boost::vecS, boost::directedS, DualVertexProperty, boost::no_property>;
boost::dynamic_properties dpDual;
DualGraph g;
std::mt19937 rng { std::random_device{}() };
boost::generate_random_graph(g, 5, 5, rng);
for (auto v: boost::make_iterator_range(boost::vertices(g)))
g[v] = DualVertexProperty { RED, GREEN, BLUE };
dpDual.property("node_id", boost::get(boost::vertex_index, g));
dpDual.property("Color_1", boost::get(&DualVertexProperty::one, g));
boost::write_graphviz_dp(std::cout, g, dpDual);
}
这在很多方面都简单得多!