I have a boost graph with custom properties.
I want to make a copy of it. I tried it by following way.
using BGType = boost::adjacency_list<boost::vecS, boost::vecS, boost::bidirectionalS,
// Vertex Properties...
vertexProps,
// Edge Propereties...
edgeProps,
// Graph Properties
graphProps>;
vertexProps.h
class vertexProps {
public:
explicit vertexProps(const std::string *moduleName = nullptr, const std::string *name = nullptr,
long refPtr = 0 )
: _refPtr(refPtr),
{
_moduleName = moduleName ? *moduleName : "";
_name = name ? *name : "";
};
std::string _moduleName;
std::string _name;
BGType *_subGraph = nullptr;
BGType *_graph = nullptr;
}
struct CustomVertexCopy {
BGType const &g1;
BGType &g2;
void operator()(BGType::vertex_descriptor v1, BGType::vertex_descriptor v2) const
{
schVertexProps const &p1 = g1[v1];
schVertexProps &p2 = g2[v2];
p2._subGraph = p1._subGraph;
p2._graph = p1._graph;
p2._moduleName = p1._moduleName;
p2._name = p1._name;
}
};
edgeProps.h
class edgeProps {
public:
explicit edgeProps(std::string name = "")
: _name(name){};
std::string _name;
};
struct CustomEdgeCopy {
BGType const &g1;
BGType &g2;
void operator()(BGType::edge_descriptor e1, BGType::edge_descriptor e2) const { g2[e2]._name = g1[e1]._name; }
};
schGraphProps.h
class schGraphProps {
public:
explicit schGraphProps(std::string *name = nullptr) { _name = name ? *name : ""; };
std::string _name;
std::map<std::string, std::vector<std::string>> _altNames;
std::map<std::string, schSymbol> _modSymbol;
std::shared_ptr<vertexProps> _vertexPtr = nullptr; // ****want to deep copy this property*******
}
someFunction.cpp
OnClick(BGType* bgNew)
{
// some code
BGType* oldBg = new BGType;
boost::copy_graph(
*bgNew, *oldBg,
boost::vertex_copy(CustomVertexCopy{*bgNew, *oldBg}).edge_copy(CustomEdgeCopy{*bgNew, *oldBg}));
boost::get_property(*oldBg) = boost::get_property(*bgNew);
// Copying graph properties
DeepCopyOfBG(bgNew, oldBg);
}
DeepCopyOfBG(BGType *bGraph, BGType *oldBg)
{
boost::copy_graph(
*bGraph, *oldBg,
boost::vertex_copy(CustomVertexCopy{*bGraph, *oldBg}).edge_copy(CustomEdgeCopy{*bGraph, *oldBg}));
boost::get_property(*oldBg) = boost::get_property(*bGraph);
// Deep copy _altNames map
for (auto entry : (*bGraph)[boost::graph_bundle]._altNames) {
std::vector<std::string> deepCopyValues(entry.second.begin(), entry.second.end());
(*oldBg)[boost::graph_bundle]._altNames[entry.first] = deepCopyValues;
// Deep copy _modSymbol map
for (auto entry : (*bGraph)[boost::graph_bundle]._modSymbol) {
(*oldBg)[boost::graph_bundle]._modSymbol[entry.first] = entry.second;
}
// Want to copy std::shared_ptr<schVertexProps> _vertexPtr = nullptr
}
I want to deep copy of following property but could not do it.
std::shared_ptr<vertexProps> _vertexPtr = nullptr
I am stuck because of shared_ptr concept.
How to do deep copy of shared_ptr concept ?
My first response is: don't use
shared_ptrwhen you want value semantics.That's precisely why I showed you
value_ptrin my previous answer. That way, Rule-Of-Zero applies and the language automatically behaves exactly like you want it to.If you must have shared pointers and still have them deep-cloning, you can copy that
value_ptrand make it contain ashared_ptrinstead ofunique_ptr.If you don't want that, or have some other "force-of-nature" reason why you can't (???) you can always ... just copy the object manually. In general, with any unique-pointer behaves conceptually like a pointer.
I hope you spot the pattern? A deep-copy is basically just invoking the copy-constructor of
*p: whateverppoints to. It doesn't even matter what kind of (smart) pointer you have.The Specific Question Code
Regarding the code, you have more problems, because you're running
copy_graphmultiple times on the same objects. You also run the following assignment twice:That assignment ALREADY copies all the graph properties (the
schGraphPropsobject).Now, C++ allows you to customize the behavior of such a copy, by supplying a user-defined copy constructor. In your case you can e.g. make it:
Remembering to fix the pointer misuse in the constructor as I've shown you several times before, you get the following class:
Live Demo
I'm not in the mood to create a full demo again, because I keep fixing the bugs and unncessary complexity that you keep re-introducing. So I'll focus on just the graph properties.
Live On Coliru
Prints e.g.
and all the asserts pass, proving the deep-copy.