forked from cme212/CME212_old
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Graph.hpp
439 lines (375 loc) · 12.4 KB
/
Graph.hpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
#ifndef CME212_GRAPH_HPP
#define CME212_GRAPH_HPP
/** @file Graph.hpp
* @brief An undirected graph type
*/
#include <algorithm>
#include <vector>
#include <cassert>
#include "CME212/Util.hpp"
#include "CME212/Point.hpp"
/** @class Graph
* @brief A template for 3D undirected graphs.
*
* Users can add and retrieve nodes and edges. Edges are unique (there is at
* most one edge between any pair of distinct nodes).
*/
class Graph {
private:
// HW0: YOUR CODE HERE
// Use this space for declarations of important internal types you need
// later in the Graph's definition.
// (As with all the "YOUR CODE HERE" markings, you may not actually NEED
// code here. Just use the space if you need it.)
public:
//
// PUBLIC TYPE DEFINITIONS
//
/** Type of this graph. */
using graph_type = Graph;
/** Predeclaration of Node type. */
class Node;
/** Synonym for Node (following STL conventions). */
using node_type = Node;
/** Predeclaration of Edge type. */
class Edge;
/** Synonym for Edge (following STL conventions). */
using edge_type = Edge;
/** Type of node iterators, which iterate over all graph nodes. */
class NodeIterator;
/** Synonym for NodeIterator */
using node_iterator = NodeIterator;
/** Type of edge iterators, which iterate over all graph edges. */
class EdgeIterator;
/** Synonym for EdgeIterator */
using edge_iterator = EdgeIterator;
/** Type of incident iterators, which iterate incident edges to a node. */
class IncidentIterator;
/** Synonym for IncidentIterator */
using incident_iterator = IncidentIterator;
/** Type of indexes and sizes.
Return type of Graph::Node::index(), Graph::num_nodes(),
Graph::num_edges(), and argument type of Graph::node(size_type) */
using size_type = unsigned;
//
// CONSTRUCTORS AND DESTRUCTOR
//
/** Construct an empty graph. */
Graph() {
// HW0: YOUR CODE HERE
}
/** Default destructor */
~Graph() = default;
//
// NODES
//
/** @class Graph::Node
* @brief Class representing the graph's nodes.
*
* Node objects are used to access information about the Graph's nodes.
*/
class Node {
public:
/** Construct an invalid node.
*
* Valid nodes are obtained from the Graph class, but it
* is occasionally useful to declare an @i invalid node, and assign a
* valid node to it later. For example:
*
* @code
* Graph::node_type x;
* if (...should pick the first node...)
* x = graph.node(0);
* else
* x = some other node using a complicated calculation
* do_something(x);
* @endcode
*/
Node() {
// HW0: YOUR CODE HERE
}
/** Return this node's position. */
const Point& position() const {
// HW0: YOUR CODE HERE
return Point();
}
/** Return this node's index, a number in the range [0, graph_size). */
size_type index() const {
// HW0: YOUR CODE HERE
return size_type(-1);
}
// HW1: YOUR CODE HERE
// Supply definitions AND SPECIFICATIONS for:
// node_value_type& value();
// const node_value_type& value() const;
// size_type degree() const;
// incident_iterator edge_begin() const;
// incident_iterator edge_end() const;
/** Test whether this node and @a n are equal.
*
* Equal nodes have the same graph and the same index.
*/
bool operator==(const Node& n) const {
// HW0: YOUR CODE HERE
(void) n; // Quiet compiler warning
return false;
}
/** Test whether this node is less than @a n in a global order.
*
* This ordering function is useful for STL containers such as
* std::map<>. It need not have any geometric meaning.
*
* The node ordering relation must obey trichotomy: For any two nodes x
* and y, exactly one of x == y, x < y, and y < x is true.
*/
bool operator<(const Node& n) const {
// HW0: YOUR CODE HERE
(void) n; // Quiet compiler warning
return false;
}
private:
// Allow Graph to access Node's private member data and functions.
friend class Graph;
// HW0: YOUR CODE HERE
// Use this space to declare private data members and methods for Node
// that will not be visible to users, but may be useful within Graph.
// i.e. Graph needs a way to construct valid Node objects
};
/** Return the number of nodes in the graph.
*
* Complexity: O(1).
*/
size_type size() const {
// HW0: YOUR CODE HERE
return 0;
}
/** Synonym for size(). */
size_type num_nodes() const {
return size();
}
/** Add a node to the graph, returning the added node.
* @param[in] position The new node's position
* @post new num_nodes() == old num_nodes() + 1
* @post result_node.index() == old num_nodes()
*
* Complexity: O(1) amortized operations.
*/
Node add_node(const Point& position) {
// HW0: YOUR CODE HERE
(void) position; // Quiet compiler warning
return Node(); // Invalid node
}
/** Determine if a Node belongs to this Graph
* @return True if @a n is currently a Node of this Graph
*
* Complexity: O(1).
*/
bool has_node(const Node& n) const {
// HW0: YOUR CODE HERE
(void) n; // Quiet compiler warning
return false;
}
/** Return the node with index @a i.
* @pre 0 <= @a i < num_nodes()
* @post result_node.index() == i
*
* Complexity: O(1).
*/
Node node(size_type i) const {
// HW0: YOUR CODE HERE
(void) i; // Quiet compiler warning
return Node(); // Invalid node
}
//
// EDGES
//
/** @class Graph::Edge
* @brief Class representing the graph's edges.
*
* Edges are order-insensitive pairs of nodes. Two Edges with the same nodes
* are considered equal if they connect the same nodes, in either order.
*/
class Edge {
public:
/** Construct an invalid Edge. */
Edge() {
// HW0: YOUR CODE HERE
}
/** Return a node of this Edge */
Node node1() const {
// HW0: YOUR CODE HERE
return Node(); // Invalid Node
}
/** Return the other node of this Edge */
Node node2() const {
// HW0: YOUR CODE HERE
return Node(); // Invalid Node
}
/** Test whether this edge and @a e are equal.
*
* Equal edges represent the same undirected edge between two nodes.
*/
bool operator==(const Edge& e) const {
(void) e; // Quiet compiler warning
return false;
}
/** Test whether this edge is less than @a e in a global order.
*
* This ordering function is useful for STL containers such as
* std::map<>. It need not have any interpretive meaning.
*/
bool operator<(const Edge& e) const {
(void) e; // Quiet compiler warning
return false;
}
private:
// Allow Graph to access Edge's private member data and functions.
friend class Graph;
// HW0: YOUR CODE HERE
// Use this space to declare private data members and methods for Edge
// that will not be visible to users, but may be useful within Graph.
// i.e. Graph needs a way to construct valid Edge objects
};
/** Return the total number of edges in the graph.
*
* Complexity: No more than O(num_nodes() + num_edges()), hopefully less
*/
size_type num_edges() const {
// HW0: YOUR CODE HERE
return 0;
}
/** Return the edge with index @a i.
* @pre 0 <= @a i < num_edges()
*
* Complexity: No more than O(num_nodes() + num_edges()), hopefully less
*/
Edge edge(size_type i) const {
// HW0: YOUR CODE HERE
(void) i; // Quiet compiler warning
return Edge(); // Invalid Edge
}
/** Test whether two nodes are connected by an edge.
* @pre @a a and @a b are valid nodes of this graph
* @return True if for some @a i, edge(@a i) connects @a a and @a b.
*
* Complexity: No more than O(num_nodes() + num_edges()), hopefully less
*/
bool has_edge(const Node& a, const Node& b) const {
// HW0: YOUR CODE HERE
(void) a; (void) b; // Quiet compiler warning
return false;
}
/** Add an edge to the graph, or return the current edge if it already exists.
* @pre @a a and @a b are distinct valid nodes of this graph
* @return an Edge object e with e.node1() == @a a and e.node2() == @a b
* @post has_edge(@a a, @a b) == true
* @post If old has_edge(@a a, @a b), new num_edges() == old num_edges().
* Else, new num_edges() == old num_edges() + 1.
*
* Can invalidate edge indexes -- in other words, old edge(@a i) might not
* equal new edge(@a i). Must not invalidate outstanding Edge objects.
*
* Complexity: No more than O(num_nodes() + num_edges()), hopefully less
*/
Edge add_edge(const Node& a, const Node& b) {
// HW0: YOUR CODE HERE
(void) a, (void) b; // Quiet compiler warning
return Edge(); // Invalid Edge
}
/** Remove all nodes and edges from this graph.
* @post num_nodes() == 0 && num_edges() == 0
*
* Invalidates all outstanding Node and Edge objects.
*/
void clear() {
// HW0: YOUR CODE HERE
}
//
// Node Iterator
//
/** @class Graph::NodeIterator
* @brief Iterator class for nodes. A forward iterator. */
class NodeIterator {
public:
// These type definitions let us use STL's iterator_traits.
using value_type = Node; // Element type
using pointer = Node*; // Pointers to elements
using reference = Node&; // Reference to elements
using difference_type = std::ptrdiff_t; // Signed difference
using iterator_category = std::input_iterator_tag; // Weak Category, Proxy
/** Construct an invalid NodeIterator. */
NodeIterator() {
}
// HW1 #2: YOUR CODE HERE
// Supply definitions AND SPECIFICATIONS for:
// Node operator*() const
// NodeIterator& operator++()
// bool operator==(const NodeIterator&) const
private:
friend class Graph;
// HW1 #2: YOUR CODE HERE
};
// HW1 #2: YOUR CODE HERE
// Supply definitions AND SPECIFICATIONS for:
// node_iterator node_begin() const
// node_iterator node_end() const
//
// Incident Iterator
//
/** @class Graph::IncidentIterator
* @brief Iterator class for edges incident to a node. A forward iterator. */
class IncidentIterator {
public:
// These type definitions let us use STL's iterator_traits.
using value_type = Edge; // Element type
using pointer = Edge*; // Pointers to elements
using reference = Edge&; // Reference to elements
using difference_type = std::ptrdiff_t; // Signed difference
using iterator_category = std::input_iterator_tag; // Weak Category, Proxy
/** Construct an invalid IncidentIterator. */
IncidentIterator() {
}
// HW1 #3: YOUR CODE HERE
// Supply definitions AND SPECIFICATIONS for:
// Edge operator*() const
// IncidentIterator& operator++()
// bool operator==(const IncidentIterator&) const
private:
friend class Graph;
// HW1 #3: YOUR CODE HERE
};
//
// Edge Iterator
//
/** @class Graph::EdgeIterator
* @brief Iterator class for edges. A forward iterator. */
class EdgeIterator {
public:
// These type definitions let us use STL's iterator_traits.
using value_type = Edge; // Element type
using pointer = Edge*; // Pointers to elements
using reference = Edge&; // Reference to elements
using difference_type = std::ptrdiff_t; // Signed difference
using iterator_category = std::input_iterator_tag; // Weak Category, Proxy
/** Construct an invalid EdgeIterator. */
EdgeIterator() {
}
// HW1 #5: YOUR CODE HERE
// Supply definitions AND SPECIFICATIONS for:
// Edge operator*() const
// EdgeIterator& operator++()
// bool operator==(const EdgeIterator&) const
private:
friend class Graph;
// HW1 #5: YOUR CODE HERE
};
// HW1 #5: YOUR CODE HERE
// Supply definitions AND SPECIFICATIONS for:
// edge_iterator edge_begin() const
// edge_iterator edge_end() const
private:
// HW0: YOUR CODE HERE
// Use this space for your Graph class's internals:
// helper functions, data members, and so forth.
};
#endif // CME212_GRAPH_HPP