英文:
How to write GraphML file to Boost Graph with custom graph_bundle Property?
问题
我无法编译以下代码,我想使用boost图形库的graph_bundle属性。
struct VertexProps
{
std::string VertexName;
};
struct EdgeProps
{
std::string edgeName;
};
struct GraphProps
{
std::string name;
};
boost::adjacency_list<boost::vecS, boost::vecS, boost::bidirectionalS, VertexProps, EdgeProps, GraphProps> g;
g[boost::graph_bundle].name = "myGraphName";
boost::dynamic_properties dp;
dp.property("name", get(&GraphProps::name, g)); // 在这一行出现编译错误
std::ofstream xmlFile("output.graphml");
boost::write_graphml(xmlFile, g, dp, true);
xmlFile.close();
我遇到以下编译错误:
<>/boost/graph/detail/adjacency_list.hpp:2646:29: 错误:形成对void的引用
2646 | typedef value_type& reference;
| ^~~~~~~~~
<>/boost/graph/detail/adjacency_list.hpp:2647:35: 错误:形成对void的引用
2647 | typedef const value_type& const_reference;
| ^~~~~~~~~~~~~~~
<>/boost/graph/detail/adjacency_list.hpp:2651:13: 错误:形成对void的引用
2651 | type;
| ^~~~
<>/boost/graph/detail/adjacency_list.hpp:2654:13: 错误:形成对void的引用
2654 | const_type;
| ^~~~~~~~~~
test.cpp: 在函数‘void writeGraph()’中:
test.cpp:310:49: 错误:没有匹配的函数调用‘get(std::string GraphProps::*, Graph&)’
310 | dp.property("name", get(&GraphProps::name, g));
| ^
似乎boost图形库不支持自定义属性名,可以使用dynamic_properties
来将其写入graphml
。
英文:
I am not able to compile below , where I want to use graph_bundle property of boost graph.
struct VertexProps
{
std::string VertexName;
};
struct EdgeProps
{
std::string edgeName;
};
struct GraphProps
{
std::string name;
};
boost::adjacency_list<boost::vecS, boost::vecS, boost::bidirectionalS, VertexProps, EdgeProps, GraphProps> g;
g[boost::graph_bundle].name = "myGraphName";
boost::dynamic_properties dp;
dp.property("name", get(&GraphProps::name, g)); //compile error on this line
std::ofstream xmlFile("output.graphml");
boost::write_graphml(xmlFile, g, dp, true);
xmlFile.close();
I am getting beloe compile error:
<>/boost/graph/detail/adjacency_list.hpp:2646:29: error: forming reference to void
2646 | typedef value_type& reference;
| ^~~~~~~~~
<>/boost/graph/detail/adjacency_list.hpp:2647:35: error: forming reference to void
2647 | typedef const value_type& const_reference;
| ^~~~~~~~~~~~~~~
<>/boost/graph/detail/adjacency_list.hpp:2651:13: error: forming reference to void
2651 | type;
| ^~~~
<>/boost/graph/detail/adjacency_list.hpp:2654:13: error: forming reference to void
2654 | const_type;
| ^~~~~~~~~~
test.cpp: In function ‘void writeGraph()’:
test.cpp:310:49: error: no matching function for call to ‘get(std::string GraphProps::*, Graph&)’
310 | dp.property("name", get(&GraphProps::name, g));
| ^
It seems , boost graph library can't support custom property name , which can be used dynamic_properties for writing in graphml.
答案1
得分: 1
图属性在属性映射中文档不够详细。公平地说,它们的用途也有限。
您需要创建一个关联属性映射,键类型为 G*
(其中 G
表示您的图类型)。
最简单的方法是使用 make_constant_property_map
:
dp.property("name", boost::make_constant_property<G*>(get_property(g).name));
请参阅 Live On Coliru
#include <boost/graph/adjacency_list.hpp>
#include <boost/graph/graphml.hpp>
struct VertexProps { std::string VertexName; };
struct EdgeProps { std::string edgeName; };
struct GraphProps { std::string name; };
int main() {
using G = boost::adjacency_list<boost::vecS, boost::vecS, boost::bidirectionalS, VertexProps,
EdgeProps, GraphProps>;
G g;
auto& gp = get_property(g);
g[boost::graph_bundle].name = "myGraphName"; // or gp.name = "myGraphName"
boost::dynamic_properties dp;
dp.property("name", boost::make_constant_property<G*>(get_property(g).name));
boost::write_graphml(std::cout, g, dp, true);
}
打印
<?xml version="1.0" encoding="UTF-8"?>
<graphml xmlns="http://graphml.graphdrawing.org/xmlns" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://graphml.graphdrawing.org/xmlns http://graphml.graphdrawing.org/xmlns/1.0/graphml.xsd">
<key id="key0" for="graph" attr.name="name" attr.type="string" />
<graph id="G" edgedefault="directed" parse.nodeids="canonical" parse.edgeids="canonical" parse.order="nodesfirst">
<data key="key0">myGraphName</data>
</graph>
</graphml>
英文:
Graph properties in property maps are poorly documented. In fairness, they're also of limited use.
You need to make an associative property map with key type G*
(where G
denotes your graph type).
The simplest way would be to use make_constant_property_map
:
dp.property("name", boost::make_constant_property<G*>(get_property(g).name));
See it Live On Coliru
#include <boost/graph/adjacency_list.hpp>
#include <boost/graph/graphml.hpp>
struct VertexProps { std::string VertexName; };
struct EdgeProps { std::string edgeName; };
struct GraphProps { std::string name; };
int main() {
using G = boost::adjacency_list<boost::vecS, boost::vecS, boost::bidirectionalS, VertexProps,
EdgeProps, GraphProps>;
G g;
auto& gp = get_property(g);
g[boost::graph_bundle].name = "myGraphName"; // or gp.name = "myGraphName"
boost::dynamic_properties dp;
dp.property("name", boost::make_constant_property<G*>(get_property(g).name));
boost::write_graphml(std::cout, g, dp, true);
}
Printing
<?xml version="1.0" encoding="UTF-8"?>
<graphml xmlns="http://graphml.graphdrawing.org/xmlns" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://graphml.graphdrawing.org/xmlns http://graphml.graphdrawing.org/xmlns/1.0/graphml.xsd">
<key id="key0" for="graph" attr.name="name" attr.type="string" />
<graph id="G" edgedefault="directed" parse.nodeids="canonical" parse.edgeids="canonical" parse.order="nodesfirst">
<data key="key0">myGraphName</data>
</graph>
</graphml>
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论