Index: branches/RoutePlanning/HeuristicLab.Algorithms.GraphRouting/3.3/BidirectionalDijkstraAlgorithm.cs
===================================================================
--- branches/RoutePlanning/HeuristicLab.Algorithms.GraphRouting/3.3/BidirectionalDijkstraAlgorithm.cs	(revision 8423)
+++ branches/RoutePlanning/HeuristicLab.Algorithms.GraphRouting/3.3/BidirectionalDijkstraAlgorithm.cs	(revision 8423)
@@ -0,0 +1,149 @@
+﻿
+using System;
+using System.Collections.Generic;
+using HeuristicLab.Problems.RoutePlanning.Graph;
+namespace HeuristicLab.Algorithms.GraphRouting {
+  public class BidrectionalDijkstraAlgorithm : IRouter {
+    private Graph graph;
+
+    private HashSet<long> visitedNodesForward;
+    private HashSet<long> visitedNodesBackward;
+    private HashSet<long> unvisitedNodesForward;
+    private HashSet<long> unvisitedNodesBackward;
+    private Dictionary<long, float> distancesForward;
+    private Dictionary<long, long> predecessorsForward;
+    private Dictionary<long, float> distancesBackward;
+    private Dictionary<long, long> predecessorsBackward;
+
+    public BidrectionalDijkstraAlgorithm(Graph graph) {
+      this.graph = graph;
+    }
+
+    #region IRouter Members
+
+    public long[] Calculate(long sourceNodeId, long targetNodeId) {
+      visitedNodesForward = new HashSet<long>();
+      visitedNodesBackward = new HashSet<long>();
+
+      unvisitedNodesForward = new HashSet<long>();
+      unvisitedNodesBackward = new HashSet<long>();
+
+      distancesForward = new Dictionary<long, float>();
+      predecessorsForward = new Dictionary<long, long>();
+
+      distancesBackward = new Dictionary<long, float>();
+      predecessorsBackward = new Dictionary<long, long>();
+
+      List<long> resultRouteForward = new List<long>();
+      List<long> resultRouteBackward = new List<long>();
+
+      if (sourceNodeId == targetNodeId) {
+        resultRouteForward.Add(sourceNodeId);
+        return resultRouteForward.ToArray();
+      }
+
+      long currentNodeForward = sourceNodeId;
+      distancesForward.Add(currentNodeForward, 0);
+      unvisitedNodesForward.Add(currentNodeForward);
+
+      long currentNodeBackward = targetNodeId;
+      distancesBackward.Add(currentNodeBackward, 0);
+      unvisitedNodesBackward.Add(currentNodeBackward);
+
+      while (unvisitedNodesForward.Count > 0 && unvisitedNodesBackward.Count > 0) {
+        currentNodeForward = GetMinimumDistance(distancesForward, unvisitedNodesForward);
+        visitedNodesForward.Add(currentNodeForward);
+        unvisitedNodesForward.Remove(currentNodeForward);
+
+        currentNodeBackward = GetMinimumDistance(distancesBackward, unvisitedNodesBackward);
+        visitedNodesBackward.Add(currentNodeBackward);
+        unvisitedNodesBackward.Remove(currentNodeBackward);
+
+        if (visitedNodesForward.Contains(currentNodeBackward)) {
+          return GetRoute(currentNodeBackward).ToArray();
+        }
+
+        if (visitedNodesBackward.Contains(currentNodeForward)) {
+          return GetRoute(currentNodeForward).ToArray();
+        }
+
+        FindMinimalWeightForward(currentNodeForward);
+        FindMinimalWeightBackward(currentNodeBackward);
+      }
+
+      throw new Exception(string.Format("No route found from {0} to {1}", sourceNodeId, targetNodeId));
+    }
+
+    #endregion
+
+    private long GetMinimumDistance(Dictionary<long, float> distances, HashSet<long> nodeIds) {
+      long minimum = -1;
+      foreach (long id in nodeIds) {
+        if (minimum == -1) minimum = id;
+        else {
+          if (GetDistance(distances, id) < GetDistance(distances, minimum)) {
+            minimum = id;
+          }
+        }
+      }
+      return minimum;
+    }
+
+    private float GetDistance(Dictionary<long, float> distances, long id) {
+      float d;
+      if (distances.TryGetValue(id, out d)) {
+        return d;
+      } else { return float.MaxValue; }
+    }
+
+    private void FindMinimalWeightForward(long nodeId) {
+      Dictionary<long, float> currentNeighbors = graph.GetNeighbors(nodeId);
+      foreach (KeyValuePair<long, float> neighbor in currentNeighbors) {
+        // update relax
+        float totalWeight = GetDistance(distancesForward, nodeId) + neighbor.Value;
+        if (GetDistance(distancesForward, neighbor.Key) > totalWeight) {
+          distancesForward[neighbor.Key] = totalWeight;
+          predecessorsForward[neighbor.Key] = nodeId;
+          unvisitedNodesForward.Add(neighbor.Key);
+        }
+      }
+    }
+
+    private void FindMinimalWeightBackward(long nodeId) {
+      Dictionary<long, float> currentNeighbors = graph.GetNeighborsReversed(nodeId);
+      foreach (KeyValuePair<long, float> neighbor in currentNeighbors) {
+        // update relax
+        float totalWeight = GetDistance(distancesBackward, nodeId) + neighbor.Value;
+        if (GetDistance(distancesBackward, neighbor.Key) > totalWeight) {
+          distancesBackward[neighbor.Key] = totalWeight;
+          predecessorsBackward[neighbor.Key] = nodeId;
+          unvisitedNodesBackward.Add(neighbor.Key);
+        }
+      }
+    }
+
+    private List<long> GetRoute(long nodeId) {
+      List<long> route = new List<long>();
+      long current = nodeId;
+      long next;
+
+      if (!predecessorsForward.TryGetValue(current, out next)) {
+        return null;
+      }
+      route.Add(current);
+      while (predecessorsForward.TryGetValue(current, out next)) {
+        current = predecessorsForward[current];
+        route.Add(current);
+      }
+      route.Reverse();
+
+      current = nodeId;
+      while (predecessorsBackward.TryGetValue(current, out next)) {
+        current = predecessorsBackward[current];
+        route.Add(current);
+      }
+
+      return route;
+    }
+  }
+}
Index: branches/RoutePlanning/HeuristicLab.Algorithms.GraphRouting/3.3/HeuristicLab.Algorithms.GraphRouting.csproj
===================================================================
--- branches/RoutePlanning/HeuristicLab.Algorithms.GraphRouting/3.3/HeuristicLab.Algorithms.GraphRouting.csproj	(revision 8408)
+++ branches/RoutePlanning/HeuristicLab.Algorithms.GraphRouting/3.3/HeuristicLab.Algorithms.GraphRouting.csproj	(revision 8423)
@@ -59,4 +59,5 @@
     <Compile Include="AStarAlgorithm.cs" />
     <Compile Include="AStarAlgorithmV2.cs" />
+    <Compile Include="BidirectionalDijkstraAlgorithm.cs" />
     <Compile Include="DijkstraAlgorithm.cs" />
     <Compile Include="GraphRoutingAlgorithm.cs" />
Index: branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning.Test/Program.cs
===================================================================
--- branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning.Test/Program.cs	(revision 8408)
+++ branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning.Test/Program.cs	(revision 8423)
@@ -26,12 +26,16 @@
       //Test(file6, 529102170, 1001363194, true, false); // inz - inz
 
-      IDataSource ds = TestLoad(file6);
-      Graph.Graph graph = new Graph.Graph(ds);
-      TestRouter(new AStarAlgorithm(graph), 529102170, 31372732, false); // inz - hgb
-      TestRouter(new AStarAlgorithmV2(graph), 529102170, 31372732, false); // inz - hgb
+      //IDataSource ds = TestLoad(file6);
+      //Graph.Graph graph = new Graph.Graph(ds);
+      //TestRouter(new AStarAlgorithm(graph), 529102170, 31372732, false); // inz - hgb
+      //TestRouter(new AStarAlgorithmV2(graph), 529102170, 31372732, false); // inz - hgb
 
       //TestLoadAndRouter(file6, typeof(DijkstraAlgorithm), 529102170, 31372732, false, false); // inz - hgb
       //TestLoadAndRouter(file6, typeof(AStarAlgorithm), 529102170, 31372732, false, false); // inz - hgb
       //TestLoadAndRouter(file6, typeof(AStarAlgorithmV2), 529102170, 31372732, false, false); // inz - hgb
+
+      //TestLoadAndRouter(file5, typeof(DijkstraAlgorithm), 529102170, 1001363194, true, false);
+      //TestLoadAndRouter(file5, typeof(BidrectionalDijkstraAlgorithm), 529102170, 1001363194, true, true);
+      TestLoadAndRouter(file6, typeof(BidrectionalDijkstraAlgorithm), 529102170, 31372732, false, true); // inz - hgb
 
       System.Console.Read();
Index: branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning/3.3/Graph/Graph.cs
===================================================================
--- branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning/3.3/Graph/Graph.cs	(revision 8408)
+++ branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning/3.3/Graph/Graph.cs	(revision 8423)
@@ -35,4 +35,20 @@
         foreach (Vertex<Node> neighbor in vertices) {
           if (edge.CanBeTraversed(vertex.Node, neighbor.Node)) {
+            float weight = GetWeight(edge, vertex, neighbor);
+            neighbors[neighbor.Node.Id] = weight;
+          }
+        }
+      }
+      return neighbors;
+    }
+
+    public Dictionary<long, float> GetNeighborsReversed(long id) {
+      Vertex<Node> vertex = GetVertex(id);
+      Dictionary<long, float> neighbors = new Dictionary<long, float>();
+      List<Way> edges = GetEdges(vertex);
+      foreach (Way edge in edges) {
+        List<Vertex<Node>> vertices = GetNeighborVerticesOnEdge(edge, vertex);
+        foreach (Vertex<Node> neighbor in vertices) {
+          if (edge.CanBeTraversed(neighbor.Node, vertex.Node)) {
             float weight = GetWeight(edge, vertex, neighbor);
             neighbors[neighbor.Node.Id] = weight;
Index: branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning/3.3/Osm/TagConstants.cs
===================================================================
--- branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning/3.3/Osm/TagConstants.cs	(revision 8408)
+++ branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning/3.3/Osm/TagConstants.cs	(revision 8423)
@@ -3,6 +3,9 @@
   public class TagConstants {
     public const string HighwayTagKey = "highway";
+    public const string JunctionTagKey = "junction";
     public const string OneWayTag = "oneway";
+    public const string RoundaboutValue = "roundabout";
     public const string YesValue = "yes";
+    public const string TrueValue = "true";
   }
 }
Index: branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning/3.3/Osm/Way.cs
===================================================================
--- branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning/3.3/Osm/Way.cs	(revision 8408)
+++ branches/RoutePlanning/HeuristicLab.Problems.RoutePlanning/3.3/Osm/Way.cs	(revision 8423)
@@ -73,5 +73,8 @@
         if (base.Tags.ContainsKey(TagConstants.OneWayTag)) {
           string value = base.Tags[TagConstants.OneWayTag];
-          return value.Equals(TagConstants.YesValue);
+          return value.Equals(TagConstants.YesValue) || value.Equals(TagConstants.TrueValue);
+        } else if (base.Tags.ContainsKey(TagConstants.JunctionTagKey)) {
+          string value = base.Tags[TagConstants.JunctionTagKey];
+          return value.Equals(TagConstants.RoundaboutValue);
         } else {
           return false;
