Skip to content

Commit 4569d22

Browse files
authored
Convert raw pointers to smart pointers (#316)
* Change all the raw pointers in the library to smart pointers * Rewrite tests to use smart pointers * Finish converting tests to smart pointers * Add setter for nodes in Edge nodePair * Fix addition of edges and construction of adjacency matrix * Add overloads of algorithms which take raw pointers to mantain interface * Fix typos in tests * Change dynamic_casts into dynamic_pointer_casts * Decrease the number of random edges and nodes in RW and partition tests * Add overload of equality operators and hash functions for pointers of nodes * Implement new hash functions for pointers of nodes and edges * Increase number of nodes and edges in partition and RW tests * Fix typo * Use shared pointers in random node/edge generators * Convert pointers in TransitiveReductionTest.cpp * Add overload of addEdge for raw pointers * Fix typo * Fix edge insertion in FloydWarshall benchmark * Fix typo in benchmark * Remove all the calls to new in the tests * Fix typo in benchmark FloydWarshall Fix typo in benchmark FloydWarshall * Conversion of example codes
1 parent 5fc8449 commit 4569d22

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

55 files changed

+2182
-1327
lines changed

benchmark/FloydWarshall_BM.cpp

Lines changed: 18 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,12 @@
11
#include <benchmark/benchmark.h>
2+
#include <Edge/DirectedWeightedEdge.hpp>
3+
#include <memory>
24

35
#include "CXXGraph.hpp"
46
#include "Utilities.hpp"
57

8+
using std::make_shared;
9+
610
// https://en.wikipedia.org/wiki/Floyd%E2%80%93Warshall_algorithm#Example
711
static void BM_FWDirected(benchmark::State &state) {
812
CXXGraph::Node<int> node1("1", 1);
@@ -17,11 +21,11 @@ static void BM_FWDirected(benchmark::State &state) {
1721
CXXGraph::DirectedWeightedEdge<int> edge5(3, node2, node3, 3);
1822

1923
CXXGraph::T_EdgeSet<int> edgeSet;
20-
edgeSet.insert(&edge1);
21-
edgeSet.insert(&edge2);
22-
edgeSet.insert(&edge3);
23-
edgeSet.insert(&edge4);
24-
edgeSet.insert(&edge5);
24+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge1));
25+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge2));
26+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge3));
27+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge4));
28+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge5));
2529

2630
CXXGraph::Graph<int> graph(edgeSet);
2731
for (auto _ : state) {
@@ -39,9 +43,9 @@ static void BM_FWNegCycle(benchmark::State &state) {
3943
CXXGraph::DirectedWeightedEdge<int> edge2(2, node1, node2, 3);
4044
CXXGraph::DirectedWeightedEdge<int> edge3(3, node2, node0, -7);
4145
CXXGraph::T_EdgeSet<int> edgeSet;
42-
edgeSet.insert(&edge1);
43-
edgeSet.insert(&edge2);
44-
edgeSet.insert(&edge3);
46+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge1));
47+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge2));
48+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge3));
4549
CXXGraph::Graph<int> graph(edgeSet);
4650
for (auto _ : state) {
4751
CXXGraph::FWResult res = graph.floydWarshall();
@@ -59,9 +63,9 @@ static void BM_FWUndirectedWeighted(benchmark::State &state) {
5963
CXXGraph::DirectedWeightedEdge<int> edge2(2, node2, node3, 1);
6064
CXXGraph::UndirectedWeightedEdge<int> edge3(3, node1, node3, 6);
6165
CXXGraph::T_EdgeSet<int> edgeSet;
62-
edgeSet.insert(&edge1);
63-
edgeSet.insert(&edge2);
64-
edgeSet.insert(&edge3);
66+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge1));
67+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge2));
68+
edgeSet.insert(make_shared<CXXGraph::UndirectedWeightedEdge<int>>(edge3));
6569
CXXGraph::Graph<int> graph(edgeSet);
6670
for (auto _ : state) {
6771
CXXGraph::FWResult res = graph.floydWarshall();
@@ -79,9 +83,9 @@ static void BM_FWNoWeighted(benchmark::State &state) {
7983
CXXGraph::DirectedWeightedEdge<int> edge2(2, node2, node3, 1);
8084
CXXGraph::DirectedEdge<int> edge3(3, node1, node3);
8185
CXXGraph::T_EdgeSet<int> edgeSet;
82-
edgeSet.insert(&edge1);
83-
edgeSet.insert(&edge2);
84-
edgeSet.insert(&edge3);
86+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge1));
87+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge2));
88+
edgeSet.insert(make_shared<CXXGraph::DirectedEdge<int>>(edge3));
8589
CXXGraph::Graph<int> graph(edgeSet);
8690
for (auto _ : state) {
8791
CXXGraph::FWResult res = graph.floydWarshall();

examples/DialExample/dial_example.cpp

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,10 @@
11
#include <math.h>
2+
#include <memory>
23

34
#include <CXXGraph.hpp>
45

6+
using std::make_shared;
7+
58
typedef struct euclid_point {
69
double x;
710
double y;
@@ -49,11 +52,11 @@ int main() {
4952
points_vector.at(node2.getData())));
5053

5154
CXXGraph::T_EdgeSet<int> edgeSet;
52-
edgeSet.insert(&edge1);
53-
edgeSet.insert(&edge2);
54-
edgeSet.insert(&edge3);
55-
edgeSet.insert(&edge4);
56-
edgeSet.insert(&edge5);
55+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge1));
56+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge2));
57+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge3));
58+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge4));
59+
edgeSet.insert(make_shared<CXXGraph::DirectedWeightedEdge<int>>(edge5));
5760

5861
// Can print out the edges for debugging
5962
std::cout << edge1 << "\n";
@@ -68,4 +71,4 @@ int main() {
6871
std::cout << "Dial Result: " << res.minDistanceMap.at(node3.getId()) << ", "
6972
<< res.success << "\n";
7073
return 0;
71-
}
74+
}

examples/DijkstraExample/dijkstra_example.cpp

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,9 @@
11
#include <CXXGraph.hpp>
22

3+
#include <memory>
4+
5+
using std::make_shared;
6+
37
int main() {
48
CXXGraph::Node<int> node0("0", 0);
59
CXXGraph::Node<int> node1("1", 1);
@@ -12,10 +16,10 @@ int main() {
1216
CXXGraph::UndirectedWeightedEdge<int> edge4(4, node0, node3, 1.0);
1317

1418
CXXGraph::T_EdgeSet<int> edgeSet;
15-
edgeSet.insert(&edge1);
16-
edgeSet.insert(&edge2);
17-
edgeSet.insert(&edge3);
18-
edgeSet.insert(&edge4);
19+
edgeSet.insert(make_shared<CXXGraph::UndirectedWeightedEdge<int>>(edge1));
20+
edgeSet.insert(make_shared<CXXGraph::UndirectedWeightedEdge<int>>(edge2));
21+
edgeSet.insert(make_shared<CXXGraph::UndirectedWeightedEdge<int>>(edge3));
22+
edgeSet.insert(make_shared<CXXGraph::UndirectedWeightedEdge<int>>(edge4));
1923

2024
// Can print out the edges for debugging
2125
std::cout << edge1 << "\n";
@@ -29,4 +33,4 @@ int main() {
2933
std::cout << "Dijkstra Result: " << res.result << "\n";
3034

3135
return 0;
32-
}
36+
}

include/Edge/DirectedEdge.hpp

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,15 @@
2525
#include "Edge.hpp"
2626

2727
namespace CXXGraph {
28+
// Smart pointers alias
29+
template <typename T>
30+
using unique = std::unique_ptr<T>;
31+
template <typename T>
32+
using shared= std::shared_ptr<T>;
33+
34+
using std::make_unique;
35+
using std::make_shared;
36+
2837
template <typename T>
2938
class UndirectedEdge;
3039

@@ -38,8 +47,12 @@ class DirectedEdge : public Edge<T> {
3847
public:
3948
DirectedEdge(const unsigned long id, const Node<T> &node1,
4049
const Node<T> &node2);
50+
DirectedEdge(const unsigned long id, shared<const Node<T>> node1,
51+
shared<const Node<T>> node2);
4152
DirectedEdge(const unsigned long id,
4253
const std::pair<const Node<T> *, const Node<T> *> &nodepair);
54+
DirectedEdge(const unsigned long id,
55+
const std::pair<shared<const Node<T>>, shared<const Node<T>>> &nodepair);
4356
DirectedEdge(const Edge<T> &edge);
4457
virtual ~DirectedEdge() = default;
4558
const Node<T> &getFrom() const;
@@ -60,12 +73,22 @@ DirectedEdge<T>::DirectedEdge(const unsigned long id, const Node<T> &node1,
6073
const Node<T> &node2)
6174
: Edge<T>(id, node1, node2) {}
6275

76+
template <typename T>
77+
DirectedEdge<T>::DirectedEdge(const unsigned long id, shared<const Node<T>> node1,
78+
shared<const Node<T>> node2) : Edge<T>(id, node1, node2) {}
79+
6380
template <typename T>
6481
DirectedEdge<T>::DirectedEdge(
6582
const unsigned long id,
6683
const std::pair<const Node<T> *, const Node<T> *> &nodepair)
6784
: Edge<T>(id, nodepair) {}
6885

86+
template <typename T>
87+
DirectedEdge<T>::DirectedEdge(
88+
const unsigned long id,
89+
const std::pair<shared<const Node<T>>, shared<const Node<T>>> &nodepair)
90+
: Edge<T>(id, nodepair) {}
91+
6992
template <typename T>
7093
DirectedEdge<T>::DirectedEdge(const Edge<T> &edge)
7194
: DirectedEdge(edge.getId(), *(edge.getNodePair().first),
@@ -99,4 +122,4 @@ std::ostream &operator<<(std::ostream &os, const DirectedEdge<T> &edge) {
99122
}
100123
} // namespace CXXGraph
101124

102-
#endif // __CXXGRAPH_DIRECTEDEDGE_H__
125+
#endif // __CXXGRAPH_DIRECTEDEDGE_H__

include/Edge/DirectedWeightedEdge.hpp

Lines changed: 30 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,15 @@
2525
#include "Weighted.hpp"
2626

2727
namespace CXXGraph {
28+
// Smart pointers alias
29+
template <typename T>
30+
using unique = std::unique_ptr<T>;
31+
template <typename T>
32+
using shared= std::shared_ptr<T>;
33+
34+
using std::make_unique;
35+
using std::make_shared;
36+
2837
// Foward Declaration
2938
template <typename T>
3039
class UndirectedWeightedEdge;
@@ -41,10 +50,16 @@ class DirectedWeightedEdge : public DirectedEdge<T>, public Weighted {
4150
public:
4251
DirectedWeightedEdge(const unsigned long id, const Node<T> &node1,
4352
const Node<T> &node2, const double weight);
53+
DirectedWeightedEdge(const unsigned long id, shared<const Node<T>> node1,
54+
shared<const Node<T>> node2, const double weight);
4455
DirectedWeightedEdge(
4556
const unsigned long id,
4657
const std::pair<const Node<T> *, const Node<T> *> &nodepair,
4758
const double weight);
59+
DirectedWeightedEdge(
60+
const unsigned long id,
61+
const std::pair<shared<const Node<T>>, shared<const Node<T>>> &nodepair,
62+
const double weight);
4863
DirectedWeightedEdge(const DirectedEdge<T> &edge, const double weight);
4964
DirectedWeightedEdge(const Edge<T> &edge, const double weight);
5065
DirectedWeightedEdge(const DirectedEdge<T> &edge);
@@ -69,13 +84,27 @@ DirectedWeightedEdge<T>::DirectedWeightedEdge(const unsigned long id,
6984
const double weight)
7085
: DirectedEdge<T>(id, node1, node2), Weighted(weight) {}
7186

87+
template <typename T>
88+
DirectedWeightedEdge<T>::DirectedWeightedEdge(const unsigned long id,
89+
shared<const Node<T>> node1,
90+
shared<const Node<T>> node2,
91+
const double weight)
92+
: DirectedEdge<T>(id, node1, node2), Weighted(weight) {}
93+
7294
template <typename T>
7395
DirectedWeightedEdge<T>::DirectedWeightedEdge(
7496
const unsigned long id,
7597
const std::pair<const Node<T> *, const Node<T> *> &nodepair,
7698
const double weight)
7799
: DirectedEdge<T>(id, nodepair), Weighted(weight) {}
78100

101+
template <typename T>
102+
DirectedWeightedEdge<T>::DirectedWeightedEdge(
103+
const unsigned long id,
104+
const std::pair<shared<const Node<T>>, shared<const Node<T>>> &nodepair,
105+
const double weight)
106+
: DirectedEdge<T>(id, nodepair), Weighted(weight) {}
107+
79108
template <typename T>
80109
DirectedWeightedEdge<T>::DirectedWeightedEdge(const DirectedEdge<T> &edge,
81110
const double weight)
@@ -115,4 +144,4 @@ std::ostream &operator<<(std::ostream &os,
115144

116145
} // namespace CXXGraph
117146

118-
#endif // __CXXGRAPH_DIRECTEDWEIGHTEDEDGE_H__
147+
#endif // __CXXGRAPH_DIRECTEDWEIGHTEDEDGE_H__

include/Edge/Edge.hpp

100644100755
Lines changed: 51 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -22,12 +22,22 @@
2222

2323
#pragma once
2424

25+
#include <memory>
2526
#include <optional>
2627
#include <utility>
2728

2829
#include "Node/Node.hpp"
2930

3031
namespace CXXGraph {
32+
// Smart pointers alias
33+
template <typename T>
34+
using unique = std::unique_ptr<T>;
35+
template <typename T>
36+
using shared = std::shared_ptr<T>;
37+
38+
using std::make_unique;
39+
using std::make_shared;
40+
3141
template <typename T>
3242
class Edge;
3343
// ostream operator
@@ -37,16 +47,21 @@ template <typename T>
3747
class Edge {
3848
private:
3949
unsigned long long id = 0;
40-
std::pair<const Node<T> *, const Node<T> *> nodePair;
50+
std::pair<shared<const Node<T>>, shared<const Node<T>>> nodePair;
4151

4252
public:
4353
Edge(const unsigned long long id, const Node<T> &node1, const Node<T> &node2);
54+
Edge(const unsigned long long id, shared<const Node<T>> node1, shared<const Node<T>> node2);
4455
Edge(const unsigned long long id,
4556
const std::pair<const Node<T> *, const Node<T> *> &nodepair);
57+
Edge(const unsigned long long id,
58+
const std::pair<shared<const Node<T>>, shared<const Node<T>>> &nodepair);
4659
virtual ~Edge() = default;
60+
void setFirstNode(shared<const Node<T>> node);
61+
void setSecondNode(shared<const Node<T>> node);
4762
const unsigned long long &getId() const;
48-
const std::pair<const Node<T> *, const Node<T> *> &getNodePair() const;
49-
const Node<T> *getOtherNode(const Node<T> *node) const;
63+
const std::pair<shared<const Node<T>>, shared<const Node<T>>> &getNodePair() const;
64+
shared<const Node<T>> getOtherNode(shared<const Node<T>> node) const;
5065
virtual const std::optional<bool> isDirected() const;
5166
virtual const std::optional<bool> isWeighted() const;
5267
// operator
@@ -61,31 +76,59 @@ class Edge {
6176

6277
template <typename T>
6378
Edge<T>::Edge(const unsigned long long id, const Node<T> &node1,
64-
const Node<T> &node2)
65-
: nodePair(&node1, &node2) {
79+
const Node<T> &node2) {
80+
this->nodePair.first = make_shared<const Node<T>>(node1);
81+
this->nodePair.second = make_shared<const Node<T>>(node2);
82+
this->id = id;
83+
}
84+
85+
template <typename T>
86+
Edge<T>::Edge(const unsigned long long id, shared<const Node<T>> node1, shared<const Node<T>> node2) {
87+
this->nodePair.first = node1;
88+
this->nodePair.second = node2;
89+
this->id = id;
90+
}
91+
92+
template <typename T>
93+
Edge<T>::Edge(const unsigned long long id,
94+
const std::pair<const Node<T> *, const Node<T> *> &nodepair) {
95+
this->nodePair.first = make_shared<const Node<T>>(*(nodepair.first));
96+
this->nodePair.second = make_shared<const Node<T>>(*(nodepair.second));
6697
this->id = id;
6798
}
6899

69100
template <typename T>
70101
Edge<T>::Edge(const unsigned long long id,
71-
const std::pair<const Node<T> *, const Node<T> *> &nodepair)
102+
const std::pair<shared<const Node<T>>, shared<const Node<T>>> &nodepair)
72103
: nodePair(nodepair) {
73104
this->id = id;
74105
}
75106

107+
template <typename T>
108+
void Edge<T>::setFirstNode(shared<const Node<T>> node) {
109+
/* this->nodePair = std::make_pair(node, this->nodePair.second); */
110+
this->nodePair.first = node;
111+
}
112+
113+
template <typename T>
114+
void Edge<T>::setSecondNode(shared<const Node<T>> node) {
115+
/* this->nodePair = std::make_pair(this->nodePair.first, node); */
116+
this->nodePair.second = node;
117+
}
118+
76119
template <typename T>
77120
const unsigned long long &Edge<T>::getId() const {
78121
return id;
79122
}
80123

81124
template <typename T>
82-
const std::pair<const Node<T> *, const Node<T> *> &Edge<T>::getNodePair()
125+
const std::pair<shared<const Node<T>>, shared<const Node<T>>> &Edge<T>::getNodePair()
83126
const {
84127
return nodePair;
85128
}
86129

87130
template <typename T>
88-
const Node<T> *Edge<T>::getOtherNode(const Node<T> *node) const {
131+
shared<const Node<T>> Edge<T>::getOtherNode(shared<const Node<T>> node) const {
89132
if (this->getNodePair().first == node) {
90133
return this->getNodePair().second;
91134
} else {

0 commit comments

Comments
 (0)