From 9afcf3fc5bab76de5b825cf143b2c514698f2054 Mon Sep 17 00:00:00 2001 From: Denes Matetelki Date: Thu, 18 Apr 2013 22:13:38 +0200 Subject: [PATCH] Edge iteragor advance works --- graph.h | 65 ++++++++++++++++++++++++++++++++++---------------------- main.cpp | 46 ++++++++++++++++++++++++++------------- 2 files changed, 71 insertions(+), 40 deletions(-) diff --git a/graph.h b/graph.h index a23cac2..291cb83 100644 --- a/graph.h +++ b/graph.h @@ -90,7 +90,7 @@ public: reference_self_type operator=(const_reference_self_type o) { if (this != &o) { m_it = o.m_it; } return *this; } - reference operator*() { return *((*m_it).m_data); } + pointer operator*() { return (*m_it).m_data; } pointer operator->() { return (*m_it).m_data; } self_type &operator++() { ++m_it; return *this; } @@ -137,12 +137,20 @@ public: self_type operator+(difference_type n) { self_type tmp(*this); tmp.pos_ += n; return tmp; } self_type &operator+=(difference_type n) { advance(n); return *this; } bool operator==(const_reference_self_type o) - { return m_vertex_it == o.m_vertex_it && m_edge_it == o.m_edge_it; } + { return (m_vertex_it == m_vertices.end() && o.m_vertex_it == o.m_vertices.end()) || + (m_vertex_it == o.m_vertex_it && m_edge_it == o.m_edge_it); } bool operator!=(const_reference_self_type o) { return !(*this == o); } private: - edge_iterator(std::vector vertices) - : m_vertices(vertices), m_vertex_it(m_vertices.begin()), m_edge_it(), m_edge(0) {} + edge_iterator(std::vector vertices, bool begin = true) + : m_vertices(vertices), m_vertex_it(), m_edge_it(), m_edge(0) { + if (begin) { + m_vertex_it = m_vertices.begin(); + if (!m_vertices.empty()) m_edge_it = (*m_vertex_it).m_edges.begin(); + } else { + m_vertex_it = m_vertices.end(); + } + } void resetEdge(); void advance(int n); @@ -154,7 +162,7 @@ public: }; edge_iterator edge_begin() { return edge_iterator(m_vertices); } - edge_iterator edge_end() { return edge_iterator(m_vertices); } + edge_iterator edge_end() { return edge_iterator(m_vertices, false); } private: @@ -214,37 +222,44 @@ void Graph::edge_iterator::resetEdge() { if (m_edge) delete m_edge; - if (m_vertex_it == m_vertices.end()) { + if (m_vertex_it == m_vertices.end() || + (*m_vertex_it).m_edges.empty()) { m_edge = 0; - } else { - m_edge = new Edge( (*m_vertex_it).m_data, (*m_edge_it).m_destination, (*m_edge_it).m_weight); + return; } + + pointer source = (*m_vertex_it).m_data; + pointer destination = (*m_edge_it).m_destination; + float weight = (*m_edge_it).m_weight; + + m_edge = new Edge(source, destination, weight); } template void Graph::edge_iterator::advance(int n) { - if (m_vertex_it == m_vertices.end()) - return; - - std::list::EdgeTo> edges = (*m_vertex_it).m_edges; - const int remaining = std::distance(m_edge_it, edges.end()); - if (remaining < n) { - std::advance(m_edge_it, n); - return; - } + if (m_vertex_it == m_vertices.end()) return; - int counter = n - remaining; - ++m_vertex_it; - while (counter > 0 && m_vertex_it != m_vertices.end()) { - const int number_of_edges = (*m_vertex_it).m_edges.size(); - if (counter < number_of_edges) { - m_edge_it = (*m_vertex_it).m_edges.begin(); - std::advance(m_edge_it, counter); + while (true) { + const int edgesAhead = std::distance(m_edge_it, (*m_vertex_it).m_edges.end()) - 1; + if (n <= edgesAhead) { + std::advance(m_edge_it, n); return; } - counter -= number_of_edges; + + if (edgesAhead > 0) + n -= edgesAhead; + ++m_vertex_it; + + if (m_vertex_it == m_vertices.end()) + return; + + m_edge_it = (*m_vertex_it).m_edges.begin(); + if (m_edge_it != (*m_vertex_it).m_edges.end()) + --n; + + if (n == 0) return; } } diff --git a/main.cpp b/main.cpp index 1f51abb..6530062 100644 --- a/main.cpp +++ b/main.cpp @@ -57,46 +57,62 @@ int main() int c = 13; int d = 1; - g.addVertex(d); + assert(g.numberOfVertices() == 2); g.addVertex(c); + g.addVertex(d); + assert(g.numberOfVertices() == 4); int vertices_array[] = {2, 5, 13, 1}; std::vector v(vertices_array, vertices_array + sizeof(vertices_array) / sizeof(int) ); Graph::vertex_iterator g_it; std::vector::iterator v_it; + for (g_it = g.vertex_begin(), v_it = v.begin(); g_it != g.vertex_end(); - g_it++, v_it++) - assert(*g_it == *v_it); + g_it++, v_it++) { + assert(**g_it == *v_it); + } assert(g.neighboursOf(5).size() == 0); Graph g2; - g.addVertex(1); - g.addVertex(2); - g.addVertex(3); - g.addVertex(4); + g2.addVertex(1); + g2.addVertex(2); + g2.addVertex(3); + g2.addVertex(4); int vertices_array2[] = {1, 2, 3, 4}; std::vector v2(vertices_array2, vertices_array2 + sizeof(vertices_array2) / sizeof(int) ); for (g_it = g2.vertex_begin(), v_it = v2.begin(); g_it != g2.vertex_end(); - g_it++, v_it++) - assert(*g_it == *v_it); + g_it++, v_it++) { + std::cout << "vector: " + << *g_it << " " + << **g_it + << std::endl; + assert(**g_it == *v_it); + } - assert(g.addEdge(b, c) == true); - assert(g.addEdge(a, d) == true); - std::vector::Edge> e = g.edges(); + assert(g2.addEdge(1, 2) == true); + assert(g2.addEdge(1, 3) == true); + assert(g2.addEdge(2, 4) == true); + std::vector::Edge> e = g2.edges(); assert(e.size() == 3); - for(Graph::edge_iterator edge_it = g.edge_begin(); edge_it != g.edge_end(); ++edge_it) { - std::cout << (*edge_it).getSource() << " " - << (*edge_it).getDestination() << " " + for(Graph::edge_iterator edge_it = g2.edge_begin(); + edge_it != g2.edge_end(); + ++edge_it) { + Graph::pointer source = (*edge_it).getSource(); + Graph::pointer destination = (*edge_it).getDestination(); + std::cout << "edge: " + << source << " " << *source << " " + << destination << " " << *destination << " " << (*edge_it).getWeight() << std::endl; } + std::cout << "frankon vege" << std::endl; return 0; }