use range based for loops to traverse graphs

This commit is contained in:
Dennis Luxen 2014-05-13 16:56:30 +02:00
parent 9b68821f05
commit e769821e0f
13 changed files with 70 additions and 80 deletions

View File

@ -94,7 +94,7 @@ template <typename GraphT> class BFSComponentExplorer
const NodeID to_node_of_only_restriction =
m_restriction_map.CheckForEmanatingIsOnlyTurn(u, v);
for (auto e2 = m_graph.BeginEdges(v); e2 < m_graph.EndEdges(v); ++e2)
for (auto e2 : m_graph.GetAdjacentEdgeRange(v))
{
const NodeID w = m_graph.GetTarget(e2);

View File

@ -283,8 +283,7 @@ class TarjanSCC
++index;
// Traverse outgoing edges
EdgeID end_edge = m_node_based_graph->EndEdges(v);
for (auto e2 = m_node_based_graph->BeginEdges(v); e2 < end_edge; ++e2)
for (auto e2 : m_node_based_graph->GetAdjacentEdgeRange(v))
{
const TarjanDynamicGraph::NodeIterator vprime =
m_node_based_graph->GetTarget(e2);
@ -357,8 +356,7 @@ class TarjanSCC
for (NodeID u = 0; u < last_u_node; ++u)
{
p.printIncrement();
EdgeID last_edge = m_node_based_graph->EndEdges(u);
for (auto e1 = m_node_based_graph->BeginEdges(u); e1 < last_edge; ++e1)
for (auto e1 : m_node_based_graph->GetAdjacentEdgeRange(u))
{
if (!m_node_based_graph->GetEdgeData(e1).reversedEdge)
{

View File

@ -340,10 +340,7 @@ class Contractor
for (unsigned i = 0; i < contractor_graph->GetNumberOfNodes(); ++i)
{
const NodeID start = i;
auto last_edge = contractor_graph->EndEdges(start);
for (auto current_edge = contractor_graph->BeginEdges(start);
current_edge < last_edge;
++current_edge)
for (auto current_edge : contractor_graph->GetAdjacentEdgeRange(start))
{
ContractorGraph::EdgeData &data =
contractor_graph->GetEdgeData(current_edge);
@ -531,8 +528,7 @@ class Contractor
for (NodeID node = 0; node < number_of_nodes; ++node)
{
p.printStatus(node);
auto endEdges = contractor_graph->EndEdges(node);
for (auto edge = contractor_graph->BeginEdges(node); edge < endEdges; ++edge)
for (auto edge : contractor_graph->GetAdjacentEdgeRange(node))
{
const NodeID target = contractor_graph->GetTarget(edge);
const ContractorGraph::EdgeData &data = contractor_graph->GetEdgeData(edge);
@ -634,8 +630,7 @@ class Contractor
}
// iterate over all edges of node
auto end_edges = contractor_graph->EndEdges(node);
for (auto edge = contractor_graph->BeginEdges(node); edge != end_edges; ++edge)
for (auto edge : contractor_graph->GetAdjacentEdgeRange(node))
{
const ContractorEdgeData &data = contractor_graph->GetEdgeData(edge);
if (!data.forward)
@ -698,8 +693,7 @@ class Contractor
int inserted_edges_size = data->inserted_edges.size();
std::vector<ContractorEdge> &inserted_edges = data->inserted_edges;
auto end_in_edges = contractor_graph->EndEdges(node);
for (auto in_edge = contractor_graph->BeginEdges(node); in_edge != end_in_edges; ++in_edge)
for (auto in_edge : contractor_graph->GetAdjacentEdgeRange(node))
{
const ContractorEdgeData &in_data = contractor_graph->GetEdgeData(in_edge);
const NodeID source = contractor_graph->GetTarget(in_edge);
@ -719,9 +713,7 @@ class Contractor
int max_distance = 0;
unsigned number_of_targets = 0;
auto end_out_edges = contractor_graph->EndEdges(node);
for (auto out_edge = contractor_graph->BeginEdges(node); out_edge != end_out_edges;
++out_edge)
for (auto out_edge : contractor_graph->GetAdjacentEdgeRange(node))
{
const ContractorEdgeData &out_data = contractor_graph->GetEdgeData(out_edge);
if (!out_data.forward)
@ -746,10 +738,7 @@ class Contractor
{
Dijkstra(max_distance, number_of_targets, 2000, data, node);
}
for (auto out_edge = contractor_graph->BeginEdges(node),
endOutEdges = contractor_graph->EndEdges(node);
out_edge != endOutEdges;
++out_edge)
for (auto out_edge : contractor_graph->GetAdjacentEdgeRange(node))
{
const ContractorEdgeData &out_data = contractor_graph->GetEdgeData(out_edge);
if (!out_data.forward)
@ -835,7 +824,7 @@ class Contractor
neighbours.clear();
// find all neighbours
for (auto e = contractor_graph->BeginEdges(node); e < contractor_graph->EndEdges(node); ++e)
for (auto e : contractor_graph->GetAdjacentEdgeRange(node))
{
const NodeID u = contractor_graph->GetTarget(e);
if (u != node)
@ -862,8 +851,7 @@ class Contractor
neighbours.clear();
// find all neighbours
auto end_edges = contractor_graph->EndEdges(node);
for (auto e = contractor_graph->BeginEdges(node); e < end_edges; ++e)
for (auto e : contractor_graph->GetAdjacentEdgeRange(node))
{
const NodeID u = contractor_graph->GetTarget(e);
if (u == node)
@ -895,7 +883,7 @@ class Contractor
std::vector<NodeID> &neighbours = data->neighbours;
neighbours.clear();
for (auto e = contractor_graph->BeginEdges(node); e < contractor_graph->EndEdges(node); ++e)
for (auto e : contractor_graph->GetAdjacentEdgeRange(node))
{
const NodeID target = contractor_graph->GetTarget(e);
if (node == target)
@ -924,8 +912,7 @@ class Contractor
// examine all neighbours that are at most 2 hops away
for (const NodeID u : neighbours)
{
auto end_edges = contractor_graph->EndEdges(u);
for (auto e = contractor_graph->BeginEdges(u); e < end_edges; ++e)
for (auto e : contractor_graph->GetAdjacentEdgeRange(u))
{
const NodeID target = contractor_graph->GetTarget(e);
if (node == target)

View File

@ -438,9 +438,7 @@ void EdgeBasedGraphFactory::RenumberEdges()
for (NodeID current_node = 0; current_node < m_node_based_graph->GetNumberOfNodes();
++current_node)
{
for (EdgeID current_edge = m_node_based_graph->BeginEdges(current_node);
current_edge < m_node_based_graph->EndEdges(current_node);
++current_edge)
for (EdgeID current_edge : m_node_based_graph->GetAdjacentEdgeRange(current_node))
{
EdgeData &edge_data = m_node_based_graph->GetEdgeData(current_edge);
if (!edge_data.forward)
@ -483,10 +481,7 @@ void EdgeBasedGraphFactory::GenerateEdgeExpandedNodes()
BOOST_ASSERT(u != SPECIAL_NODEID);
BOOST_ASSERT(u < m_node_based_graph->GetNumberOfNodes());
p.printIncrement();
for (EdgeID e1 = m_node_based_graph->BeginEdges(u),
last_edge = m_node_based_graph->EndEdges(u);
e1 < last_edge;
++e1)
for (EdgeID e1 : m_node_based_graph->GetAdjacentEdgeRange(u))
{
const EdgeData &edge_data = m_node_based_graph->GetEdgeData(e1);
if (edge_data.edgeBasedNodeID == SPECIAL_NODEID)
@ -552,10 +547,7 @@ EdgeBasedGraphFactory::GenerateEdgeExpandedEdges(const std::string &original_edg
for (NodeID u = 0, end = m_node_based_graph->GetNumberOfNodes(); u < end; ++u)
{
for (EdgeID e1 = m_node_based_graph->BeginEdges(u),
last_edge_u = m_node_based_graph->EndEdges(u);
e1 < last_edge_u;
++e1)
for (EdgeID e1 : m_node_based_graph->GetAdjacentEdgeRange(u))
{
if (!m_node_based_graph->GetEdgeData(e1).forward)
{
@ -568,10 +560,7 @@ EdgeBasedGraphFactory::GenerateEdgeExpandedEdges(const std::string &original_edg
m_restriction_map->CheckForEmanatingIsOnlyTurn(u, v);
const bool is_barrier_node = (m_barrier_nodes.find(v) != m_barrier_nodes.end());
for (EdgeID e2 = m_node_based_graph->BeginEdges(v),
last_edge_v = m_node_based_graph->EndEdges(v);
e2 < last_edge_v;
++e2)
for (EdgeID e2 : m_node_based_graph->GetAdjacentEdgeRange(v))
{
if (!m_node_based_graph->GetEdgeData(e2).forward)
{

View File

@ -31,6 +31,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include "../DataStructures/DeallocatingVector.h"
#include <boost/assert.hpp>
#include <boost/range/irange.hpp>
#include <cstdint>
@ -41,6 +42,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
template <typename EdgeDataT> class DynamicGraph
{
public:
typedef decltype(boost::irange(0u,0u)) EdgeRange;
typedef EdgeDataT EdgeData;
typedef unsigned NodeIterator;
typedef unsigned EdgeIterator;
@ -133,6 +135,11 @@ template <typename EdgeDataT> class DynamicGraph
return EdgeIterator(m_nodes[n].firstEdge + m_nodes[n].edges);
}
EdgeRange GetAdjacentEdgeRange(const NodeID node) const
{
return boost::irange(BeginEdges(node), EndEdges(node));
}
// adds an edge. Invalidates edge iterators for the source node
EdgeIterator InsertEdge(const NodeIterator from, const NodeIterator to, const EdgeDataT &data)
{

View File

@ -55,8 +55,7 @@ void RestrictionMap::FixupArrivingTurnRestriction(const NodeID u, const NodeID v
// it is more efficent to get a (small) list of potential start edges
// than iterating over all buckets
std::vector<NodeID> predecessors;
for (EdgeID current_edge_id = m_graph->BeginEdges(u); current_edge_id < m_graph->EndEdges(u);
++current_edge_id)
for (EdgeID current_edge_id : m_graph->GetAdjacentEdgeRange(u))
{
const EdgeData &edge_data = m_graph->GetEdgeData(current_edge_id);
const NodeID target = m_graph->GetTarget(current_edge_id);

View File

@ -33,6 +33,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include "../Util/SimpleLogger.h"
#include "../typedefs.h"
#include <boost/range/irange.hpp>
#include <algorithm>
#include <limits>
#include <vector>
@ -40,6 +42,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
template <typename EdgeDataT, bool UseSharedMemory = false> class StaticGraph
{
public:
typedef decltype(boost::irange(0u,0u)) EdgeRange;
typedef NodeID NodeIterator;
typedef NodeID EdgeIterator;
typedef EdgeDataT EdgeData;
@ -62,7 +65,7 @@ template <typename EdgeDataT, bool UseSharedMemory = false> class StaticGraph
struct NodeArrayEntry
{
// index of the first edge
EdgeIterator firstEdge;
EdgeIterator first_edge;
};
struct EdgeArrayEntry
@ -71,6 +74,11 @@ template <typename EdgeDataT, bool UseSharedMemory = false> class StaticGraph
EdgeDataT data;
};
EdgeRange GetAdjacentEdgeRange(const NodeID node) const
{
return boost::irange(BeginEdges(node), EndEdges(node));
}
StaticGraph(const int nodes, std::vector<InputEdge> &graph)
{
std::sort(graph.begin(), graph.end());
@ -81,18 +89,20 @@ template <typename EdgeDataT, bool UseSharedMemory = false> class StaticGraph
EdgeIterator position = 0;
for (NodeIterator node = 0; node <= number_of_nodes; ++node)
{
EdgeIterator lastEdge = edge;
EdgeIterator last_edge = edge;
while (edge < number_of_edges && graph[edge].source == node)
{
++edge;
node_array[node].firstEdge = position; //=edge
position += edge - lastEdge; // remove
}
node_array[node].first_edge = position; //=edge
position += edge - last_edge; // remove
}
edge_array.resize(position); //(edge)
edge = 0;
for (NodeIterator node = 0; node < number_of_nodes; ++node)
{
EdgeIterator e = node_array[node + 1].firstEdge;
for (EdgeIterator i = node_array[node].firstEdge; i != e; ++i)
EdgeIterator e = node_array[node + 1].first_edge;
for (EdgeIterator i = node_array[node].first_edge; i != e; ++i)
{
edge_array[i].target = graph[edge].target;
edge_array[i].data = graph[edge].data;
@ -115,10 +125,10 @@ template <typename EdgeDataT, bool UseSharedMemory = false> class StaticGraph
Percent p(GetNumberOfNodes());
for (unsigned u = 0; u < GetNumberOfNodes(); ++u)
{
for (unsigned eid = BeginEdges(u); eid < EndEdges(u); ++eid)
for (auto eid : GetAdjacentEdgeRange(u))
{
unsigned v = GetTarget(eid);
EdgeData &data = GetEdgeData(eid);
const unsigned v = GetTarget(eid);
const EdgeData &data = GetEdgeData(eid);
if (data.shortcut)
{
const EdgeID first_edge_id = FindEdgeInEitherDirection(u, data.id);
@ -144,7 +154,7 @@ template <typename EdgeDataT, bool UseSharedMemory = false> class StaticGraph
#endif
}
unsigned GetNumberOfNodes() const { return number_of_nodes; }
unsigned GetNumberOfNodes() const { return number_of_nodes -1; }
unsigned GetNumberOfEdges() const { return number_of_edges; }
@ -161,12 +171,12 @@ template <typename EdgeDataT, bool UseSharedMemory = false> class StaticGraph
EdgeIterator BeginEdges(const NodeIterator n) const
{
return EdgeIterator(node_array.at(n).firstEdge);
return EdgeIterator(node_array.at(n).first_edge);
}
EdgeIterator EndEdges(const NodeIterator n) const
{
return EdgeIterator(node_array.at(n + 1).firstEdge);
return EdgeIterator(node_array.at(n + 1).first_edge);
}
// searches for a specific edge
@ -174,7 +184,7 @@ template <typename EdgeDataT, bool UseSharedMemory = false> class StaticGraph
{
EdgeIterator smallest_edge = SPECIAL_EDGEID;
EdgeWeight smallest_weight = INVALID_EDGE_WEIGHT;
for (EdgeIterator edge = BeginEdges(from); edge < EndEdges(from); edge++)
for (auto edge : GetAdjacentEdgeRange(from))
{
const NodeID target = GetTarget(edge);
const EdgeWeight weight = GetEdgeData(edge).distance;

View File

@ -604,7 +604,7 @@ template <class DataFacadeT> class AlternativeRouting : private BasicRoutingInte
}
}
for (EdgeID edge = facade->BeginEdges(node); edge < facade->EndEdges(node); ++edge)
for (auto edge : facade->GetAdjacentEdgeRange(node))
{
const EdgeData &data = facade->GetEdgeData(edge);
const bool edge_is_forward_directed =

View File

@ -87,7 +87,7 @@ template <class DataFacadeT> class BasicRoutingInterface
}
// Stalling
for (EdgeID edge = facade->BeginEdges(node); edge < facade->EndEdges(node); ++edge)
for (auto edge : facade->GetAdjacentEdgeRange(node))
{
const EdgeData &data = facade->GetEdgeData(edge);
const bool reverse_flag = ((!forward_direction) ? data.forward : data.backward);
@ -108,9 +108,7 @@ template <class DataFacadeT> class BasicRoutingInterface
}
}
for (EdgeID edge = facade->BeginEdges(node), end_edge = facade->EndEdges(node);
edge < end_edge;
++edge)
for (auto edge : facade->GetAdjacentEdgeRange(node))
{
const EdgeData &data = facade->GetEdgeData(edge);
bool forward_directionFlag = (forward_direction ? data.forward : data.backward);
@ -167,9 +165,7 @@ template <class DataFacadeT> class BasicRoutingInterface
// The above explanation unclear? Think!
EdgeID smaller_edge_id = SPECIAL_EDGEID;
int edge_weight = INT_MAX;
for (EdgeID edge_id = facade->BeginEdges(edge.first);
edge_id < facade->EndEdges(edge.first);
++edge_id)
for (auto edge_id : facade->GetAdjacentEdgeRange(edge.first))
{
const int weight = facade->GetEdgeData(edge_id).distance;
if ((facade->GetTarget(edge_id) == edge.second) && (weight < edge_weight) &&
@ -181,9 +177,7 @@ template <class DataFacadeT> class BasicRoutingInterface
}
if (SPECIAL_EDGEID == smaller_edge_id)
{
for (EdgeID edge_id = facade->BeginEdges(edge.second);
edge_id < facade->EndEdges(edge.second);
++edge_id)
for (auto edge_id : facade->GetAdjacentEdgeRange(edge.second))
{
const int weight = facade->GetEdgeData(edge_id).distance;
if ((facade->GetTarget(edge_id) == edge.first) && (weight < edge_weight) &&
@ -323,9 +317,7 @@ template <class DataFacadeT> class BasicRoutingInterface
EdgeID smaller_edge_id = SPECIAL_EDGEID;
int edge_weight = INT_MAX;
for (EdgeID edge_id = facade->BeginEdges(edge.first);
edge_id < facade->EndEdges(edge.first);
++edge_id)
for (auto edge_id : facade->GetAdjacentEdgeRange(edge.first))
{
const int weight = facade->GetEdgeData(edge_id).distance;
if ((facade->GetTarget(edge_id) == edge.second) && (weight < edge_weight) &&
@ -338,9 +330,7 @@ template <class DataFacadeT> class BasicRoutingInterface
if (SPECIAL_EDGEID == smaller_edge_id)
{
for (EdgeID edge_id = facade->BeginEdges(edge.second);
edge_id < facade->EndEdges(edge.second);
++edge_id)
for (auto edge_id : facade->GetAdjacentEdgeRange(edge.second))
{
const int weight = facade->GetEdgeData(edge_id).distance;
if ((facade->GetTarget(edge_id) == edge.first) && (weight < edge_weight) &&

View File

@ -38,10 +38,14 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include "../../Util/StringUtil.h"
#include "../../typedefs.h"
#include <boost/range/irange.hpp>
#include <osrm/Coordinate.h>
#include <string>
typedef decltype(boost::irange(0u,0u)) EdgeRange;
template <class EdgeDataT> class BaseDataFacade
{
public:
@ -67,6 +71,8 @@ template <class EdgeDataT> class BaseDataFacade
virtual EdgeID EndEdges(const NodeID n) const = 0;
virtual EdgeRange GetAdjacentEdgeRange(const NodeID node) const = 0;
// searches for a specific edge
virtual EdgeID FindEdge(const NodeID from, const NodeID to) const = 0;

View File

@ -309,6 +309,8 @@ template <class EdgeDataT> class InternalDataFacade : public BaseDataFacade<Edge
EdgeID EndEdges(const NodeID n) const { return m_query_graph->EndEdges(n); }
EdgeRange GetAdjacentEdgeRange(const NodeID node) const { return m_query_graph->GetAdjacentEdgeRange(node); };
// searches for a specific edge
EdgeID FindEdge(const NodeID from, const NodeID to) const
{

View File

@ -254,6 +254,8 @@ template <class EdgeDataT> class SharedDataFacade : public BaseDataFacade<EdgeDa
EdgeID EndEdges(const NodeID n) const { return m_query_graph->EndEdges(n); }
EdgeRange GetAdjacentEdgeRange(const NodeID node) const { return m_query_graph->GetAdjacentEdgeRange(node); };
// searches for a specific edge
EdgeID FindEdge(const NodeID from, const NodeID to) const
{

View File

@ -392,24 +392,24 @@ int main(int argc, char *argv[])
SimpleLogger().Write() << "Building node array";
StaticGraph<EdgeData>::EdgeIterator edge = 0;
StaticGraph<EdgeData>::EdgeIterator position = 0;
StaticGraph<EdgeData>::EdgeIterator lastEdge = edge;
StaticGraph<EdgeData>::EdgeIterator last_edge = edge;
for (StaticGraph<EdgeData>::NodeIterator node = 0; node < max_used_node_id; ++node)
{
lastEdge = edge;
last_edge = edge;
while ((edge < contracted_edge_count) && (contracted_edge_list[edge].source == node))
{
++edge;
}
node_array[node].firstEdge = position; //=edge
position += edge - lastEdge; // remove
node_array[node].first_edge = position; //=edge
position += edge - last_edge; // remove
}
for (unsigned sentinel_counter = max_used_node_id; sentinel_counter != node_array.size();
++sentinel_counter)
{
// sentinel element, guarded against underflow
node_array[sentinel_counter].firstEdge = contracted_edge_count;
node_array[sentinel_counter].first_edge = contracted_edge_count;
}
unsigned node_array_size = node_array.size();