forked from ZigRazor/CXXGraph
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathEulerianPath_impl.hpp
More file actions
76 lines (63 loc) · 2.66 KB
/
EulerianPath_impl.hpp
File metadata and controls
76 lines (63 loc) · 2.66 KB
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
/***********************************************************/
/*** ______ ____ ______ _ ***/
/*** / ___\ \/ /\ \/ / ___|_ __ __ _ _ __ | |__ ***/
/*** | | \ / \ / | _| '__/ _` | '_ \| '_ \ ***/
/*** | |___ / \ / \ |_| | | | (_| | |_) | | | | ***/
/*** \____/_/\_\/_/\_\____|_| \__,_| .__/|_| |_| ***/
/*** |_| ***/
/***********************************************************/
/*** Header-Only C++ Library for Graph ***/
/*** Representation and Algorithms ***/
/***********************************************************/
/*** Author: ZigRazor ***/
/*** E-Mail: zigrazor@gmail.com ***/
/***********************************************************/
/*** Collaboration: ----------- ***/
/***********************************************************/
/*** License: MPL v2.0 ***/
/***********************************************************/
#ifndef __CXXGRAPH_EULERIAN_PATH_IMPL_H__
#define __CXXGRAPH_EULERIAN_PATH_IMPL_H__
#pragma once
#include <memory>
#include <vector>
#include "CXXGraph/Graph/Graph_decl.h"
namespace CXXGraph {
template <typename T>
std::shared_ptr<std::vector<Node<T>>> Graph<T>::eulerianPath() const {
const auto nodeSet = Graph<T>::getNodeSet();
std::shared_ptr<std::vector<Node<T>>> eulerPath =
std::make_shared<std::vector<Node<T>>>();
// unused
// bool undirected = this->isUndirectedGraph();
std::vector<shared<const Node<T>>> currentPath;
// The starting node is the only node which has more outgoing than ingoing
// links
auto firstNodeIt = std::max_element(nodeSet.begin(), nodeSet.end(),
[this](auto n1, auto n2) {
return cachedAdjListOut->at(n1).size() <
cachedAdjListOut->at(n2).size();
});
auto currentNode = *(firstNodeIt);
currentPath.push_back(currentNode);
while (!currentPath.empty()) {
auto &edges = cachedAdjListOut->at(currentNode);
// we keep removing the edges that
// have been traversed from the adjacency list
if (edges.size()) {
auto firstEdge = edges.back().second;
shared<const Node<T>> nextNodeId;
nextNodeId = firstEdge->getOtherNode(currentNode);
currentPath.push_back(nextNodeId);
currentNode = nextNodeId;
edges.pop_back();
} else {
eulerPath->push_back(*currentNode);
currentNode = currentPath.back();
currentPath.pop_back();
}
}
return eulerPath;
}
} // namespace CXXGraph
#endif // __CXXGRAPH_EULERIAN_PATH_IMPL_H__