I'm trying to delete an edge from edges_, which is stored in a Graph class Node struct as a std::set using std::shared_ptr<Edge>
:
template <typename N, typename E> class Graph {
private:
struct Node;
struct Edge;
struct Node {
N val_;
int numEdges_;
int numIncomingEdges_;
std::set<std::shared_ptr<Edge>> edges_;
std::set<std::shared_ptr<Edge>> incomingEdges_;
Node() {}
Node(const N x) : val_{x} { numEdges_=0; }
void printNode(N n);
~Node();
void update();
};
struct Edge {
std::weak_ptr<Node> orig;
std::weak_ptr<Node> dest;
E val_;
Edge(std::shared_ptr<Node> o, std::shared_ptr<Node> d, E x);
Edge() {};
void printEdge();
~Edge();
};
The following code is me trying to delete an edge from edges_
, but first I need to find the edge from edges_
before I can use the erase() method for the std::set
on it. However, the variable findEdge is equal to edges_.end()
, as the given edge was not found in the set based on my if-else check ("cannot find edge in edges_!!" was printed). To find an element, std::set
uses a Compare object whose type is defined via the second template parameter which I didn't specify, thus it's defaulting to std::less<std::shared_ptr<Edge>>
which in turn calls the operator<
of the shared pointer, which does not compare the objects but only the pointers. Therefore, if the pointers used for inserting and searching are not pointing to exactly the same (as in identical, not only "equal") object, it does not actually find the edge successfully.
auto findEdge = findLinkingNode1->second->edges_.find(edge);
// if can find edge in edges_
if (findEdge != findLinkingNode1->second->edges_.end()) {
std::cout << "can find edge in edges_ so erasing it!" << std::endl;
findLinkingNode1->second->edges_.erase(findEdge);
} else {
std::cout << "cannot find edge in edges_!!" << std::endl;
}
How an edge was inserted into edges_ is as follows, where the edge was made into a shared_ptr<Edge>
to put into the std::set
:
findOrig->second->edges_.insert(std::make_shared<Edge>(Edge (findOrig->second, findDest->second, val) ));
How do I implement a custom compare class for my set edges_ that compares the actual Edge objects, so findEdge can actually find the actual edge object needed?