Roomba Controller Dashboard 1
A GUI and TCP client application that is used to control a Roomba for Computer Engineering 2880 @ Iowa State
Loading...
Searching...
No Matches
Graph.cpp
Go to the documentation of this file.
1//
2// Created by caleb on 11/9/21.
3//
4
5#include "Graph.hpp"
6
7#include <iostream>
8#include <queue>
9#include <cstdlib>
10#include <ctime>
11#include "limits.h"
12
13template<typename V>
15 std::vector<double> temp;
16 temp.push_back(0);
17 temp.push_back(0);
18 matrix.push_back(temp);
19 matrix.push_back(temp);
20}
21
22/*
23template<typename V>
24void Graph<V>::playGround() {
25 Node<V> *tempNode = new Node<V>(0);
26 addNode(tempNode);
27 // srand(time(0));
28
29 addNode(new Node<V>(1), nodes[0], 2);
30 addNode(new Node<V>(2), nodes[1], 1);
31 addNode(new Node<V>(3), nodes[2], 3);
32 addNode(new Node<V>(4), nodes[0], 2);
33 addConnection(nodes[4], nodes[2], 3);
34 addNode(new Node<V>(5), nodes[1], 2);
35 addNode(new Node<V>(6), nodes[1], 1);
36 addConnection(nodes[5], nodes[3], 7);
37 addNode(new Node<V>(7), nodes[2], 5);
38 addNode(new Node<V>(8), nodes[6], 5);
39 addConnection(nodes[8], nodes[3], 3);
40 addNode(new Node<V>(9), nodes[8], 1);
41 addConnection(nodes[9], nodes[7], 8);
42
43
44 head = nodes[0];
45
46
47 // printOut();
48
49 printAdjacent(head);
50
51 std::cout << std::endl;
52
53 std::vector<Node<V>*> path = Dijkstra(nodes[7]);
54
55 std::cout << "goal: " << nodes[7]->getData() << std::endl;
56
57 std::cout << "\n\n\n Path: ";
58 if (!path.empty()) {
59 for (int looper = 0; looper < path.size(); looper++) {
60 if (looper != path.size() - 1) {
61 std::cout << nodeMap.at(path[looper]) << "->";
62 } else {
63 std::cout << nodeMap.at(path[looper]);
64 }
65 }
66 std::cout << std::endl;
67 }
69/* std::cout << "\n\n\n Vals: " << std::endl;
70 for (int i = 0; i < nodes.size(); i++) {
71 std::cout << i << " -> " << nodes[i] << std::endl;
72 }*/
73
74
75// }
76
77
78template<typename V>
80 matrix.resize(nodes.size());
81 for (std::vector<double>& looper : matrix) {
82 looper.resize(nodes.size());
83 }
84}
85
86template<typename V>
87bool Graph<V>::contains(Node<V>* node, std::vector<Node<V>*> listOfNodes) {
88 for (int looper = 0; looper < listOfNodes.size(); looper++) {
89 if (node == listOfNodes[looper]) {
90 return true;
91 }
92 }
93 return false;
94}
95
96template<typename V>
97std::vector<Node<V>*> Graph<V>::getNodes() {
98 return this->nodes;
99}
100
101template<typename V>
103 if (contains(newNode, nodes)) {return;}
104 head = newNode;
105 nodes.push_back(newNode);
106 nodeMap[newNode] = nodes.size() - 1;
107 resize();
108}
109
110template<typename V>
111void Graph<V>::addNode(Node<V>* nextNode, std::vector<Node<V>*> adjacentNodes, double weight) {
112 addNode(nextNode);
113 for (int looper = 0; looper < adjacentNodes.size(); looper++) {
114 if (!contains(adjacentNodes[looper], nodes)) {
115 nodes.push_back(adjacentNodes[looper]);
116 nodeMap[adjacentNodes[looper]] = nodes.size() - 1;
118 resize();
119 int currNodeNum = nodeMap.at(nextNode);
120 int nextNodeNum = nodeMap.at(adjacentNodes[looper]);
121 matrix[currNodeNum][nextNodeNum] = weight;
122 matrix[nextNodeNum][currNodeNum] = weight;
123 }
124}
126template<typename V>
127void Graph<V>::addNode(Node<V> *nextNode, std::vector<Node<V>*> adjacentNodes) {
128 addNode(nextNode, adjacentNodes, 1);
129}
130
131template<typename V>
132void Graph<V>::addNode(Node<V> *nextNode, Node<V> *nodeITSLATE) {
133 std::vector<Node<V>*> adj;
134 adj.push_back(nodeITSLATE);
135 addNode(nextNode, adj);
136}
137
139template<typename V>
140void Graph<V>::printOut() {
141 for (int looper = 0; looper < nodes.size(); looper++) {
142 if (looper != nodes.size() - 1) {
143 std::cout << nodes[looper]->getData() << ", ";
144 }
145 else {
146 std::cout << nodes[looper]->getData();
148 }
149 std::cout << std::endl;
150
151 for (int anotherLoop = 0; anotherLoop < nodes.size(); anotherLoop++) {
152 std::cout << "-";
153 }
154 std::cout << std::endl;
155
156 for (int i = 0; i < matrix.size(); i++) {
157 for (int ii = 0; ii < matrix[i].size(); ii++) {
158 if (ii != matrix.size() - 1) {
159 std::cout << matrix[i][ii] << ", ";
160 }
161 else {
162 std::cout << matrix[i][ii];
163 }
164 }
165 std::cout << std::endl;
166 }
167 std::cout << "\n\n\n" << std::endl;
168}
169*/
170
171template<typename V>
172std::vector<Node<V>*> Graph<V>::getAdj(Node<V>* next) {
173 std::vector<Node<V>*> adjacent;
174 int index = nodeMap.at(next);
175
176 for (int looper = 0; looper < matrix.size(); looper++) {
177 if (matrix[index][looper] != 0) {
178 adjacent.push_back(nodes[looper]);
179 }
180 }
181 return adjacent;
182}
183
184template<typename V>
185void Graph<V>::setHead(int index) {
186 head = getNodes()[index];
187}
188
189
190template<typename V>
191std::vector<Node<V>*> Graph<V>::Dijkstra(Node<V>* from, Node<V>* find) {
192 std::vector<Node<V>*> thing;
193 if (from == find) {
194 // std::cout << "was head" << std::endl;
195 return thing;
196 }
197 std::vector<bool> visited;
198 visited.resize(nodes.size());
199 double distances[nodes.size()];
200
201 for(int filler = 0; filler < nodes.size(); filler++) {
202 visited[filler] = 0;
203 distances[filler] = UINT_MAX;
204 }
205 distances[0] = 0;
206
207 std::priority_queue<pair, std::vector<pair>, CustomCompare> queue;
208 std::vector<Node<V>*> temp;
209 temp.push_back(from);
210 queue.push(std::pair<double, std::vector<Node<V>*>>(0, temp));
211 uint64_t iterations = 0;
212
213 while (!queue.empty()) {
214 iterations++;
215
216 std::vector<Node<V>*> path = queue.top().second;
217 Node<V> *curr = path[path.size() - 1];
218 double currentDistance = queue.top().first;
219 queue.pop();
220
221 visited[nodeMap.at(curr)] = 1;
222
223 if (find == curr) {
224 // std::cout << "\n\nDistance: " << currentDistance << std::endl;
225 std::cout << iterations << std::endl;
226 return path;
227 }
228
229 std::vector<Node<V>*> adj = getAdj(curr);
230
231 for (int looper = 0; looper < adj.size(); looper++) {
232 std::vector<Node<V>*> possiblePath;
233 for (int i = 0; i < path.size(); i++) {
234 possiblePath.push_back(path[i]);
235 }
236 // printAdjacent(curr);
237 if (!visited[nodeMap.at(adj[looper])] && currentDistance + matrix[nodeMap.at(curr)][nodeMap.at(adj[looper])] < distances[nodeMap.at(adj[looper])]) {
238 distances[nodeMap.at(adj[looper])] = currentDistance + matrix[nodeMap.at(curr)][nodeMap.at(adj[looper])];
239 possiblePath.push_back(adj[looper]);
240 queue.push(std::pair<double, std::vector<Node<V>*>>(currentDistance + matrix[nodeMap.at(curr)][nodeMap.at(adj[looper])], possiblePath));
241 }
242 }
243 thing = path;
244 }
245
246 // std::cout << "ATTEMPT TO RETURN SIZE: " << thing.size() << std::endl;
247 // delete queue;
248 // delete[] distances;
249 std::cout << iterations << std::endl;
250 return thing;
251}
252
253template<typename V>
255 // delete all connections and nodes
256 for (Node<V>* node : nodes) {
257 delete node;
258 }
259}
260
261template<typename V>
262std::vector<std::vector<double>> Graph<V>::getAdjacencyList() {
263 return matrix;
264}
265
266template<typename V>
267void Graph<V>::addConnection(Node<V> *one, Node<V> *two, double weight) {
268 int oneIndex = nodeMap.at(one);
269 int twoIndex = nodeMap.at(two);
270
271 matrix[oneIndex][twoIndex] = weight;
272 matrix[twoIndex][oneIndex] = weight;
273
274}
275
276template<typename V>
278 addConnection(one, two, 1);
279}
280
281template<typename V>
282void Graph<V>::addNode(Node<V> *nextNode, Node<V> *nodeITSLATE, double weight) {
283 std::vector<Node<V>*> adj;
284 adj.push_back(nodeITSLATE);
285 addNode(nextNode, adj, weight);
286}
287
288template<typename V>
289int Graph<V>::numVisited(std::vector<bool> listOfBools) {
290 int counter = 0;
291 for (int i = 0; i < listOfBools.size(); i++) {
292 if (listOfBools[i]) {
293 counter++;
294 }
295 }
296 return counter;
297}
298
299/*
300template<typename V>
301void Graph<V>::printAdjacent(Node<V>* next) {
302 std::vector<Node<V>*> list = getAdj(next);
303 std::cout << "current: " << next->getData() << std::endl;
304
305 std::cout << "Adjacent nodes: ";
306 for (int looper = 0; looper < list.size(); looper++) {
307 std::cout << nodeMap.at(list[looper]);
308 if (looper != list.size() - 1) {
309 std::cout << ", ";
310 }
311 }
312 std::cout << std::endl;
313}
314*/
315/*
316template<typename V>
317std::vector<Node<V>*> Graph<V>::FrugalKugel(Node<V>* find, unsigned int steps) {
318 std::vector<Node<V>*> toReturn;
319 if (head == find) {
320 return toReturn;
321 }
322 std::vector<bool> visited;
323 visited.resize(nodes.size());
324 unsigned int distances[nodes.size()];
325
326 // set distances except for the first one to infinity
327 for (int filler = 1; filler < nodes.size(); filler++) {
328 distances[filler] = UINT_MAX;
329 }
330 distances[0] = 0;
331
332 // setup a prioirty queue
333 std::priority_queue<pair, std::vector<pair>, CustomCompare> queue;
334 std::vector<Node<V>*> temp;
335 temp.push_back(head);
336 queue.push(std::pair<unsigned int, std::vector<Node<V>*>>(0, temp));
337
338 while (!queue.empty()) {
339 // get the path from the top of the queue
340 std::vector<Node<V>*> path = queue.top().second;
341 // get the most recent item added to the path
342 Node<V>* curr = path[path.size() - 1];
343 unsigned int currentDistance = queue.top().first;
344 // remove the current path from the PQ
345 queue.pop();
346
347 visited[nodeMap.at(curr)] = 1;
348
349 // found the goal node
350 if (find == curr) {
351 std::cout << "\nDistance: " << currentDistance << std::endl;
352 return path;
353 }
354
355 std::vector<Node<V>*>& adj = nodes[nodeMap.at(curr)];
356
357 for (int looper = 0; looper < adj.size(); looper++) {
358 if (adj[looper] != 0) {
359 std::vector<Node<V>*> possiblePath;
360 // copy over every element from path
361 for (int i = 0; i < path.size(); i++) {
362 possiblePath.push_back(path[i]);
363 }
364 // print the adjacent nodes
365 printAdjacent(curr);
366 // cache the index
367 int index = nodeMap.at(adj[looper]);
368 // the weight between the current node and the node we ate checking
369 double tempDistance = ((path.size() < 2) ? INT_MAX : matrix[nodeMap.at(curr)][index]);
370 double sumDistance = tempDistance + currentDistance;
371 // checks if we have visited the node we are inspecting, the distance is less than the cirrent distance, and
372 if (!visited[index] && sumDistance < distances[index]) {
373 distances[index] = sumDistance;
374 possiblePath.push_back(adj[looper]);
375 queue.push(std::pair<unsigned int, std::vector<Node<V>*>>(sumDistance, possiblePath));
376 }
377 }
378 }
379 toReturn = path;
380 }
381 delete queue;
382 delete[] distances;
383 return toReturn;
384}
385
386*/
387
388
389template<typename V>
390void Graph<V>::removeNode(size_t index) {
391 if (index >= nodes.size()) {
392 return;
393 }
394 delete nodes.at(index);
395 nodes.erase(nodes.begin() + index);
396 resize();
397}
~Graph()
Definition Graph.cpp:254
Graph()
Definition Graph.cpp:14
void removeNode(size_t index)
Definition Graph.cpp:390
void addConnection(Node< V > *one, Node< V > *two, double weight)
Definition Graph.cpp:267
std::vector< std::vector< double > > getAdjacencyList()
Definition Graph.cpp:262
std::vector< Node< V > * > getAdj(Node< V > *next)
Definition Graph.cpp:172
void setHead(int index)
Definition Graph.cpp:185
void addNode(Node< V > *newNode)
Definition Graph.cpp:102
void resize()
Definition Graph.cpp:79
std::vector< Node< V > * > Dijkstra(Node< V > *from, Node< V > *find)
Definition Graph.cpp:191
int numVisited(std::vector< bool > listOfBools)
Definition Graph.cpp:289
std::vector< Node< V > * > getNodes()
Definition Graph.cpp:97
bool contains(Node< V > *node, std::vector< Node< V > * > listOfNodes)
Definition Graph.cpp:87
Definition Node.hpp:17