예제 #1
0
		/// <summary>
		/// Computes a set of eulerian trail, starting at <paramref name="s"/>
		/// that spans the entire graph.
		/// </summary>
		/// <remarks>
		/// <para>
		/// This method computes a set of eulerian trail starting at <paramref name="s"/>
		/// that spans the entire graph.The algorithm outline is as follows:
		/// </para>
		/// <para>
		/// The algorithms iterates throught the Eulerian circuit of the augmented
		/// graph (the augmented graph is the graph with additional edges to make
		/// the number of odd vertices even).
		/// </para>
		/// <para>
		/// If the current edge is not temporary, it is added to the current trail.
		/// </para>
		/// <para>
		/// If the current edge is temporary, the current trail is finished and
		/// added to the trail collection. The shortest path between the 
		/// start vertex <paramref name="s"/> and the target vertex of the
		/// temporary edge is then used to start the new trail. This shortest
		/// path is computed using the <see cref="BreadthFirstSearchAlgorithm"/>.
		/// </para>
		/// </remarks>
		/// <param name="s">start vertex</param>
		/// <returns>eulerian trail set, all starting at s</returns>
		/// <exception cref="ArgumentNullException">s is a null reference.</exception>
		/// <exception cref="Exception">Eulerian trail not computed yet.</exception>
		public EdgeCollectionCollection Trails(IVertex s)
		{
			if (s==null)
				throw new ArgumentNullException("s");
			if (this.Circuit.Count==0)
				throw new Exception("Circuit is empty");

			// find the first edge in the circuit.
			int i=0;
			for(i=0;i<this.Circuit.Count;++i)
			{
				IEdge e = this.Circuit[i];
				if (TemporaryEdges.Contains(e))
					continue;
				if (e.Source == s)
					break;
			}
			if (i==this.Circuit.Count)
				throw new Exception("Did not find vertex in eulerian trail?");

			// create collections
			EdgeCollectionCollection trails = new EdgeCollectionCollection();
			EdgeCollection trail = new EdgeCollection();
			BreadthFirstSearchAlgorithm bfs =
				new BreadthFirstSearchAlgorithm(VisitedGraph);
			PredecessorRecorderVisitor vis = new PredecessorRecorderVisitor();
			bfs.RegisterPredecessorRecorderHandlers(vis);
			bfs.Compute(s);

			// go throught the edges and build the predecessor table.
			int start = i;
			for (;i<this.Circuit.Count;++i)
			{
				IEdge e = this.Circuit[i];
				if (TemporaryEdges.Contains(e))
				{
					// store previous trail and start new one.
					if(trail.Count != 0)
						trails.Add(trail);
					// start new trail
					// take the shortest path from the start vertex to
					// the target vertex
					trail = vis.Path(e.Target);
				}
				else
					trail.Add(e);
			}

			// starting again on the circuit
			for (i=0;i<start;++i)
			{
				IEdge e = this.Circuit[i];
				if (TemporaryEdges.Contains(e))
				{
					// store previous trail and start new one.
					if(trail.Count != 0)
						trails.Add(trail);
					// start new trail
					// take the shortest path from the start vertex to
					// the target vertex
					trail = vis.Path(e.Target);
				}
				else
					trail.Add(e);
			}

			// adding the last element
			if (trail.Count!=0)
				trails.Add(trail);
		
			return trails;
		}
        /// <summary>
        /// Remove the edge (u,v) from the graph. 
        /// If the graph allows parallel edges this remove all occurrences of 
        /// (u,v).
        /// </summary>
        /// <param name="u">source vertex</param>
        /// <param name="v">target vertex</param>
        public override void RemoveEdge(IVertex u, IVertex v)
        {
            if (u == null)
                throw new ArgumentNullException("source vertex");
            if (v == null)
                throw new ArgumentNullException("targetvertex");

            EdgeCollection outEdges = VertexOutEdges[u];
            EdgeCollection inEdges = VertexInEdges[v];
            // marking edges to remove
            EdgeCollection removedEdges = new EdgeCollection();
            foreach(IEdge e in outEdges)
            {
                if (e.Target == v)
                    removedEdges.Add(e);
            }
            foreach(IEdge e in inEdges)
            {
                if (e.Source == u)
                    removedEdges.Add(e);
            }

            //removing edges
            foreach(IEdge e in removedEdges)
                RemoveEdge(e);
        }
예제 #3
0
		/// <summary>
		/// Merges the temporary circuit with the current circuit
		/// </summary>
		/// <returns>true if all the graph edges are in the circuit</returns>
		protected bool CircuitAugmentation()
		{
			EdgeCollection newC=new EdgeCollection();
			int i,j;

			// follow C until w is found
			for(i=0;i<Circuit.Count;++i)
			{
				IEdge e = Circuit[i];
				if (e.Source==CurrentVertex)
					break;
				newC.Add(e);
			}

			// follow D until w is found again
			for(j=0;j<TemporaryCircuit.Count;++j)
			{
				IEdge e = TemporaryCircuit[j];
				newC.Add(e);
				OnCircuitEdge(e);
				if (e.Target==CurrentVertex)
					break;
			}
			TemporaryCircuit.Clear();

			// continue C
			for(;i<Circuit.Count;++i)
			{
				IEdge e = Circuit[i];
				newC.Add(e);
			}

			// set as new circuit
			circuit = newC;

			// check if contains all edges
			if (Circuit.Count == VisitedGraph.EdgesCount)
				return true;

			return false;
		}
예제 #4
0
		/// <summary>
		/// Adds temporary edges to the graph to make all vertex even.
		/// </summary>
		/// <param name="g"></param>
		/// <returns></returns>
		public EdgeCollection AddTemporaryEdges(IMutableVertexAndEdgeListGraph g)
		{
			if (g==null)
				throw new ArgumentNullException("g");

			// first gather odd edges.
			VertexCollection oddVertices = AlgoUtility.OddVertices(g);

			// check that there are an even number of them
			if (oddVertices.Count%2!=0)
				throw new Exception("number of odd vertices in not even!");

			// add temporary edges to create even edges:
			EdgeCollection ec = new EdgeCollection();

			bool found,foundbe,foundadjacent;
			while (oddVertices.Count > 0)
			{
				IVertex u = oddVertices[0];
				// find adjacent odd vertex.
				found = false;
				foundadjacent = false;
				foreach(IEdge e in g.OutEdges(u))
				{
					IVertex v = e.Target;
					if (v!=u && oddVertices.Contains(v))
					{
						foundadjacent=true;
						// check that v does not have an out-edge towards u
						foundbe = false;
						foreach(IEdge be in g.OutEdges(v))
						{
							if (be.Target==u)
							{
								foundbe = true;
								break;
							}
						}
						if (foundbe)
							continue;
						// add temporary edge
						IEdge tempEdge = g.AddEdge(v,u);
						// add to collection
						ec.Add(tempEdge);
						// remove u,v from oddVertices
						oddVertices.Remove(u);
						oddVertices.Remove(v);
						// set u to null
						found = true;
						break;
					}
				}

				if (!foundadjacent)
				{
					// pick another vertex
					if (oddVertices.Count<2)
						throw new Exception("Eulerian trail failure");
					IVertex v = oddVertices[1];
					IEdge tempEdge = g.AddEdge(u,v);
					// add to collection
					ec.Add(tempEdge);
					// remove u,v from oddVertices
					oddVertices.Remove(u);
					oddVertices.Remove(v);
					// set u to null
					found = true;
					
				}

				if (!found)
				{
					oddVertices.Remove(u);
					oddVertices.Add(u);
				}
			}

			temporaryEdges = ec;

			return ec;			
		}
 public void AddReversedEdges()
 {
     if (this.Augmented)
     {
         throw new InvalidOperationException("Graph already augmented");
     }
     EdgeCollection edges = new EdgeCollection();
     IEdgeEnumerator enumerator = this.VisitedGraph.get_Edges().GetEnumerator();
     while (enumerator.MoveNext())
     {
         IEdge edge = enumerator.get_Current();
         if (!this.reversedEdges.Contains(edge))
         {
             IEdge edge2 = this.FindReversedEdge(edge);
             if (edge2 != null)
             {
                 this.reversedEdges.set_Item(edge, edge2);
                 if (!this.reversedEdges.Contains(edge2))
                 {
                     this.reversedEdges.set_Item(edge2, edge);
                 }
             }
             else
             {
                 edges.Add(edge);
             }
         }
     }
     EdgeCollection.Enumerator enumerator2 = edges.GetEnumerator();
     while (enumerator2.MoveNext())
     {
         IEdge edge3 = enumerator2.get_Current();
         if (!this.reversedEdges.Contains(edge3))
         {
             IEdge edge4 = this.FindReversedEdge(edge3);
             if (edge4 != null)
             {
                 this.reversedEdges.set_Item(edge3, edge4);
             }
             else
             {
                 edge4 = this.VisitedGraph.AddEdge(edge3.get_Target(), edge3.get_Source());
                 this.augmentedEgdes.Add(edge4);
                 this.reversedEdges.set_Item(edge3, edge4);
                 this.reversedEdges.set_Item(edge4, edge3);
                 this.OnReservedEdgeAdded(new EdgeEventArgs(edge4));
             }
         }
     }
     this.augmented = true;
 }
 public void RemoveInEdgeIf(IVertex u, IEdgePredicate pred)
 {
     if (u == null)
     {
         throw new ArgumentNullException("vertex u");
     }
     if (pred == null)
     {
         throw new ArgumentNullException("predicate");
     }
     EdgeCollection edges = this.VertexInEdges.get_Item(u);
     EdgeCollection edges2 = new EdgeCollection();
     EdgeCollection.Enumerator enumerator = edges.GetEnumerator();
     while (enumerator.MoveNext())
     {
         IEdge edge = enumerator.get_Current();
         if (pred.Test(edge))
         {
             edges2.Add(edge);
         }
     }
     EdgeCollection.Enumerator enumerator2 = edges2.GetEnumerator();
     while (enumerator2.MoveNext())
     {
         IEdge e = enumerator2.get_Current();
         this.RemoveEdge(e);
     }
 }
 public virtual void RemoveEdge(IVertex u, IVertex v)
 {
     if (u == null)
     {
         throw new ArgumentNullException("source vertex");
     }
     if (v == null)
     {
         throw new ArgumentNullException("targetvertex");
     }
     EdgeCollection edges = this.VertexOutEdges.get_Item(u);
     if (edges == null)
     {
         throw new EdgeNotFoundException();
     }
     EdgeCollection edges2 = new EdgeCollection();
     EdgeCollection.Enumerator enumerator = edges.GetEnumerator();
     while (enumerator.MoveNext())
     {
         IEdge edge = enumerator.get_Current();
         if (edge.get_Target() == v)
         {
             edges2.Add(edge);
         }
     }
     EdgeCollection.Enumerator enumerator2 = edges2.GetEnumerator();
     while (enumerator2.MoveNext())
     {
         IEdge edge2 = enumerator2.get_Current();
         edges.Remove(edge2);
     }
 }
예제 #8
0
        /// <summary>
        /// Remove all the edges from graph g for which the predicate pred
        /// returns true.
        /// </summary>
        /// <param name="pred">edge predicate</param>
        public virtual void RemoveEdgeIf(IEdgePredicate pred)
        {
            if (pred == null)
                throw new ArgumentNullException("predicate");

            // marking edge for removal
            EdgeCollection removedEdges = new EdgeCollection();
            foreach(IEdge e in Edges)
            {
                if (pred.Test(e))
                    removedEdges.Add(e);
            }

            // removing edges
            foreach(IEdge e in removedEdges)
                RemoveEdge(e);
        }
        /// <summary>
        /// Remove the edge (u,v) from the graph. 
        /// If the graph allows parallel edges this remove all occurrences of 
        /// (u,v).
        /// </summary>
        /// <param name="u">source vertex</param>
        /// <param name="v">target vertex</param>
        public virtual void RemoveEdge(Vertex u, Vertex v)
        {
            if (u == null)
                throw new ArgumentNullException("u");
            if (v == null)
                throw new ArgumentNullException("v");

            this.version++;
            // getting out-edges
            EdgeCollection outEdges = this.vertexOutEdges[u];

            // marking edges to remove
            EdgeCollection removedEdges = new EdgeCollection();
            foreach(Edge e in outEdges)
            {
                if (e.Target == v)
                    removedEdges.Add(e);
            }
            //removing out-edges
            foreach(Edge e in removedEdges)
                outEdges.Remove(e);

            removedEdges.Clear();
            EdgeCollection inEdges = this.vertexInEdges[v];
            foreach(Edge e in inEdges)
            {
                if (e.Source == u)
                    removedEdges.Add(e);
            }
            //removing in-edges
            foreach(Edge e in removedEdges)
                inEdges.Remove(e);
        }
        /// <summary>
        /// Remove all the out-edges of vertex u for which the predicate pred 
        /// returns true.
        /// </summary>
        /// <param name="u">vertex</param>
        /// <param name="pred">edge predicate</param>
        public void RemoveInEdgeIf(Vertex u, IEdgePredicate pred)
        {
            if (u==null)
                throw new ArgumentNullException("vertex u");
            if (pred == null)
                throw new ArgumentNullException("predicate");

            EdgeCollection edges = this.vertexInEdges[u];
            EdgeCollection removedEdges = new EdgeCollection();
            foreach(Edge e in edges)
            {
                if (pred.Test(e))
                    removedEdges.Add(e);
            }

            foreach(Edge e in removedEdges)
                this.RemoveEdge(e);
        }
 protected bool CircuitAugmentation()
 {
     EdgeCollection edges = new EdgeCollection();
     int num = 0;
     while (num < this.Circuit.Count)
     {
         IEdge edge = this.Circuit.get_Item(num);
         if (edge.get_Source() == this.CurrentVertex)
         {
             break;
         }
         edges.Add(edge);
         num++;
     }
     for (int i = 0; i < this.TemporaryCircuit.Count; i++)
     {
         IEdge e = this.TemporaryCircuit.get_Item(i);
         edges.Add(e);
         this.OnCircuitEdge(e);
         if (e.get_Target() == this.CurrentVertex)
         {
             break;
         }
     }
     this.TemporaryCircuit.Clear();
     while (num < this.Circuit.Count)
     {
         IEdge edge3 = this.Circuit.get_Item(num);
         edges.Add(edge3);
         num++;
     }
     this.circuit = edges;
     return (this.Circuit.Count == this.VisitedGraph.get_EdgesCount());
 }
 public EdgeCollectionCollection Trails(IVertex s)
 {
     if (s == null)
     {
         throw new ArgumentNullException("s");
     }
     if (this.Circuit.Count == 0)
     {
         throw new Exception("Circuit is empty");
     }
     int num = 0;
     num = 0;
     while (num < this.Circuit.Count)
     {
         IEdge edge = this.Circuit.get_Item(num);
         if (!this.TemporaryEdges.Contains(edge) && (edge.get_Source() == s))
         {
             break;
         }
         num++;
     }
     if (num == this.Circuit.Count)
     {
         throw new Exception("Did not find vertex in eulerian trail?");
     }
     EdgeCollectionCollection collections = new EdgeCollectionCollection();
     EdgeCollection edges = new EdgeCollection();
     BreadthFirstSearchAlgorithm algorithm = new BreadthFirstSearchAlgorithm(this.VisitedGraph);
     PredecessorRecorderVisitor vis = new PredecessorRecorderVisitor();
     algorithm.RegisterPredecessorRecorderHandlers(vis);
     algorithm.Compute(s);
     int num2 = num;
     while (num < this.Circuit.Count)
     {
         IEdge edge2 = this.Circuit.get_Item(num);
         if (this.TemporaryEdges.Contains(edge2))
         {
             if (edges.Count != 0)
             {
                 collections.Add(edges);
             }
             edges = vis.Path(edge2.get_Target());
         }
         else
         {
             edges.Add(edge2);
         }
         num++;
     }
     for (num = 0; num < num2; num++)
     {
         IEdge edge3 = this.Circuit.get_Item(num);
         if (this.TemporaryEdges.Contains(edge3))
         {
             if (edges.Count != 0)
             {
                 collections.Add(edges);
             }
             edges = vis.Path(edge3.get_Target());
         }
         else
         {
             edges.Add(edge3);
         }
     }
     if (edges.Count != 0)
     {
         collections.Add(edges);
     }
     return collections;
 }
 public EdgeCollection AddTemporaryEdges(IMutableVertexAndEdgeListGraph g)
 {
     if (g == null)
     {
         throw new ArgumentNullException("g");
     }
     VertexCollection vertexs = QuickGraph.Algorithms.AlgoUtility.OddVertices(g);
     if ((vertexs.Count % 2) != 0)
     {
         throw new Exception("number of odd vertices in not even!");
     }
     EdgeCollection edges = new EdgeCollection();
     while (vertexs.Count > 0)
     {
         IVertex vertex = vertexs.get_Item(0);
         bool flag = false;
         bool flag3 = false;
         IEdgeEnumerator enumerator = g.OutEdges(vertex).GetEnumerator();
         while (enumerator.MoveNext())
         {
             IVertex vertex2 = enumerator.get_Current().get_Target();
             if ((vertex2 != vertex) && vertexs.Contains(vertex2))
             {
                 flag3 = true;
                 bool flag2 = false;
                 IEdgeEnumerator enumerator2 = g.OutEdges(vertex2).GetEnumerator();
                 while (enumerator2.MoveNext())
                 {
                     if (enumerator2.get_Current().get_Target() == vertex)
                     {
                         flag2 = true;
                         break;
                     }
                 }
                 if (!flag2)
                 {
                     IEdge edge3 = g.AddEdge(vertex2, vertex);
                     edges.Add(edge3);
                     vertexs.Remove(vertex);
                     vertexs.Remove(vertex2);
                     flag = true;
                     break;
                 }
             }
         }
         if (!flag3)
         {
             if (vertexs.Count < 2)
             {
                 throw new Exception("Eulerian trail failure");
             }
             IVertex vertex3 = vertexs.get_Item(1);
             IEdge edge4 = g.AddEdge(vertex, vertex3);
             edges.Add(edge4);
             vertexs.Remove(vertex);
             vertexs.Remove(vertex3);
             flag = true;
         }
         if (!flag)
         {
             vertexs.Remove(vertex);
             vertexs.Add(vertex);
         }
     }
     this.temporaryEdges = edges;
     return edges;
 }
        /// <summary>
        /// Augments the <see cref="VisitedGraph"/> with reversed edges.
        /// </summary>
        /// <exception cref="InvalidOperationException">
        /// The graph has already been augmented.
        /// </exception>
        public void AddReversedEdges()
        {
            if (this.Augmented)
                throw new InvalidOperationException("Graph already augmented");
            // step 1, find edges that need reversing
            EdgeCollection notReversedEdges = new EdgeCollection();
            foreach (IEdge edge in this.VisitedGraph.Edges)
            {
                // if reversed already found, continue
                if (this.reversedEdges.Contains(edge))
                    continue;

                IEdge reversedEdge = this.FindReversedEdge(edge);
                if (reversedEdge != null)
                {
                    // setup edge
                    this.reversedEdges[edge] = reversedEdge;
                    // setup reversed if needed
                    if (!this.reversedEdges.Contains(reversedEdge))
                        this.reversedEdges[reversedEdge] = edge;
                    continue;
                }

                // this edge has no reverse
                notReversedEdges.Add(edge);
            }

            // step 2, go over each not reversed edge, add reverse
            foreach (IEdge edge in notReversedEdges)
            {
                if (this.reversedEdges.Contains(edge))
                    continue;

                // already been added
                IEdge reversedEdge = this.FindReversedEdge(edge);
                if (reversedEdge != null)
                {
                    this.reversedEdges[edge] = reversedEdge;
                    continue;
                }

                // need to create one
                reversedEdge = this.VisitedGraph.AddEdge(edge.Target, edge.Source);
                this.augmentedEgdes.Add(reversedEdge);
                this.reversedEdges[edge] = reversedEdge;
                this.reversedEdges[reversedEdge] = edge;
                this.OnReservedEdgeAdded(new EdgeEventArgs(reversedEdge));
            }

            this.augmented = true;
        }
 public virtual void RemoveEdgeIf(IEdgePredicate pred)
 {
     if (pred == null)
     {
         throw new ArgumentNullException("predicate");
     }
     EdgeCollection edges = new EdgeCollection();
     VertexEdgesEnumerator enumerator = this.Edges.GetEnumerator();
     while (enumerator.MoveNext())
     {
         IEdge edge = enumerator.get_Current();
         if (pred.Test(edge))
         {
             edges.Add(edge);
         }
     }
     EdgeCollection.Enumerator enumerator2 = edges.GetEnumerator();
     while (enumerator2.MoveNext())
     {
         IEdge e = enumerator2.get_Current();
         this.RemoveEdge(e);
     }
 }
예제 #16
0
        /// <summary>
        /// Remove the edge (u,v) from the graph. 
        /// If the graph allows parallel edges this remove all occurrences of 
        /// (u,v).
        /// </summary>
        /// <param name="u">source vertex</param>
        /// <param name="v">target vertex</param>
        public virtual void RemoveEdge(IVertex u, IVertex v)
        {
            if (u == null)
                throw new ArgumentNullException("source vertex");
            if (v == null)
                throw new ArgumentNullException("targetvertex");

            EdgeCollection edges = VertexOutEdges[u];
            if (edges==null)
                throw new EdgeNotFoundException();
            // marking edges to remove
            EdgeCollection removedEdges = new EdgeCollection();
            foreach(IEdge e in edges)
            {
                if (e.Target == v)
                    removedEdges.Add(e);
            }
            //removing edges
            foreach(IEdge e in removedEdges)
                edges.Remove(e);
        }
 public override void RemoveEdge(IVertex u, IVertex v)
 {
     if (u == null)
     {
         throw new ArgumentNullException("source vertex");
     }
     if (v == null)
     {
         throw new ArgumentNullException("targetvertex");
     }
     EdgeCollection edges = base.VertexOutEdges.get_Item(u);
     EdgeCollection edges2 = this.VertexInEdges.get_Item(v);
     EdgeCollection edges3 = new EdgeCollection();
     EdgeCollection.Enumerator enumerator = edges.GetEnumerator();
     while (enumerator.MoveNext())
     {
         IEdge edge = enumerator.get_Current();
         if (edge.get_Target() == v)
         {
             edges3.Add(edge);
         }
     }
     EdgeCollection.Enumerator enumerator2 = edges2.GetEnumerator();
     while (enumerator2.MoveNext())
     {
         IEdge edge2 = enumerator2.get_Current();
         if (edge2.get_Source() == u)
         {
             edges3.Add(edge2);
         }
     }
     EdgeCollection.Enumerator enumerator3 = edges3.GetEnumerator();
     while (enumerator3.MoveNext())
     {
         IEdge e = enumerator3.get_Current();
         this.RemoveEdge(e);
     }
 }
예제 #18
0
        /// <summary>
        /// Remove all the out-edges of vertex u for which the predicate pred 
        /// returns true.
        /// </summary>
        /// <param name="u">vertex</param>
        /// <param name="pred">edge predicate</param>
        public virtual void RemoveOutEdgeIf(IVertex u, IEdgePredicate pred)
        {
            if (u==null)
                throw new ArgumentNullException("vertex u");
            if (pred == null)
                throw new ArgumentNullException("predicate");

            EdgeCollection edges = VertexOutEdges[u];
            EdgeCollection removedEdges = new EdgeCollection();
            foreach(IEdge e in edges)
                if (pred.Test(e))
                    removedEdges.Add(e);

            foreach(IEdge e in removedEdges)
                RemoveEdge(e);
        }
        public void ClearVertex(IVertex v)
        {
            if (v==null)
                throw new ArgumentNullException("v");
            if (!this.ContainsVertex(v))
                throw new ArgumentException("v is not part of the graph");

            EdgeCollection edges = new EdgeCollection();
            foreach(IEdge e in this.VisitedGraph.OutEdges(v))
                edges.Add(e);
            foreach(IEdge e in this.VisitedGraph.InEdges(v))
                edges.Add(e);

            foreach(IEdge e in edges)
            {
                if (this.VisitedGraph.ContainsEdge(e))
                {
                    RemoveEdge(e);
                }
            }
        }