示例#1
0
 internal static double[] GetExpectations(Graph graph,/*int[] sources,*/ HSet targets, int nStates)
 {
     double[] ret = ValueIteration(graph, targets, nStates); //ValueIteration(graph,sources,targets,nStates);
     if(ret==null)
     return graph.GetDistancesToAcceptingStates(targets.ToArray(typeof(int))as int[]);
         //return graph.GetDistancesToAcceptingStates(sources,targets.ToArray(typeof(int))as int[]);
       else
     return ret;
 }
示例#2
0
        /// <summary>
        /// Get all states in the given finite automaton from which no accepting state is reachable.
        /// </summary>
        /// <param name="fa">given finite automaton</param>
        /// <returns>all dead states in the finite automaton</returns>
        public static Set <Term> GetDeadStates(FSM fa)
        {
            //build a graph from fa
            Dictionary <Term, int> stateToVertexMap = new Dictionary <Term, int>();

            stateToVertexMap[fa.InitialState] = 0;
            int i = 1;

            foreach (Term state in fa.States.Remove(fa.InitialState))
            {
                stateToVertexMap[state] = i++;
            }

            //create edges that correspond to the transitions
            GraphTraversals.Edge[] edges = new GraphTraversals.Edge[fa.Transitions.Count];
            Triple <Term, CompoundTerm, Term>[] transitions = new Triple <Term, CompoundTerm, Term> [fa.Transitions.Count];
            i = 0;
            foreach (Triple <Term, CompoundTerm, Term> trans in fa.Transitions)
            {
                edges[i] = new GraphTraversals.Edge(stateToVertexMap[trans.First],
                                                    stateToVertexMap[trans.Third], i);
                transitions[i++] = trans;
            }

            GraphTraversals.Graph g =
                new GraphTraversals.Graph(0, edges, new GraphTraversals.Edge[] { },
                                          GraphTraversals.WeakClosureEnum.DoNotClose);

            int[] acceptingVertices = new int[fa.AcceptingStates.Count];
            i = 0;
            foreach (Term accState in fa.AcceptingStates)
            {
                acceptingVertices[i++] = stateToVertexMap[accState];
            }

            GraphTraversals.HSet deadVertices = g.DeadStates(acceptingVertices);

            return(fa.States.Select(delegate(Term state)
                                    { return deadVertices.Contains(stateToVertexMap[state]); }));
        }
示例#3
0
        /// <summary>
        /// Get all states in the given finite automaton from which no accepting state is reachable.
        /// </summary>
        /// <param name="fa">given finite automaton</param>
        /// <returns>all dead states in the finite automaton</returns>
        public static Set<Term> GetDeadStates(FSM fa)
        {
            //build a graph from fa
            Dictionary<Term, int> stateToVertexMap = new Dictionary<Term, int>();
            stateToVertexMap[fa.InitialState] = 0;
            int i = 1;
            foreach (Term state in fa.States.Remove(fa.InitialState))
                stateToVertexMap[state] = i++;

            //create edges that correspond to the transitions
            GraphTraversals.Edge[] edges = new GraphTraversals.Edge[fa.Transitions.Count];
            Triple<Term, CompoundTerm, Term>[] transitions = new Triple<Term, CompoundTerm, Term>[fa.Transitions.Count];
            i = 0;
            foreach (Triple<Term, CompoundTerm, Term> trans in fa.Transitions)
            {
                edges[i] = new GraphTraversals.Edge(stateToVertexMap[trans.First],
                    stateToVertexMap[trans.Third], i);
                transitions[i++] = trans;
            }

            GraphTraversals.Graph g =
                new GraphTraversals.Graph(0, edges, new GraphTraversals.Edge[] { },
                                          GraphTraversals.WeakClosureEnum.DoNotClose);

            int[] acceptingVertices = new int[fa.AcceptingStates.Count];
            i = 0;
            foreach (Term accState in fa.AcceptingStates)
                acceptingVertices[i++] = stateToVertexMap[accState];

            GraphTraversals.HSet deadVertices = g.DeadStates(acceptingVertices);

            return fa.States.Select(delegate(Term state)
                 { return deadVertices.Contains(stateToVertexMap[state]); });
        }
示例#4
0
        public static Sequence<Sequence<CompoundTerm>> GenerateTestSequences(FSM fa)
        {
            //Eliminate dead states from the fa
            Set<Term> deadStates = GetDeadStates(fa);
            Set<Term> aliveStates = fa.States.Difference(deadStates);
            Set<Triple<Term, CompoundTerm, Term>> aliveTransitions =
                fa.Transitions.Select(delegate(Triple<Term, CompoundTerm, Term> trans)
                {
                    return aliveStates.Contains(trans.First) &&
                           aliveStates.Contains(trans.Third);
                });
            if (aliveTransitions.IsEmpty) //test suite cannot be generated
                return Sequence<Sequence<CompoundTerm>>.EmptySequence;

            //Build a graph from the alive transitions
            Term[] states = new Term[aliveStates.Count];
            Dictionary<Term, int> stateToVertexMap = new Dictionary<Term, int>();
            states[0] = fa.InitialState;
            stateToVertexMap[fa.InitialState] = 0;
            int i = 1;
            foreach (Term state in aliveStates.Remove(fa.InitialState))
            {
                states[i] = state;
                stateToVertexMap[state] = i++;
            }

            //create edges that must be traversed
            GraphTraversals.Edge[] mustEdges = new GraphTraversals.Edge[aliveTransitions.Count];
            Triple<Term, CompoundTerm, Term>[] mustTransitions = new Triple<Term, CompoundTerm, Term>[aliveTransitions.Count];
            i = 0;
            foreach (Triple<Term, CompoundTerm, Term> trans in aliveTransitions)
            {
                GraphTraversals.Edge edge = new GraphTraversals.Edge(stateToVertexMap[trans.First],
                    stateToVertexMap[trans.Third], i);
                mustEdges[i] = edge;
                mustTransitions[i++] = trans;
            }

            //add an optional edge with label -1 from every accepting state
            //to the initial state, this corresponds to a reset action
            GraphTraversals.Edge[] optionalEdges =
                new GraphTraversals.Edge[fa.AcceptingStates.Count];
            i = 0;
            foreach (Term accState in fa.AcceptingStates)
            {
                int accVertex = stateToVertexMap[accState];
                optionalEdges[i++] = new GraphTraversals.Edge(accVertex, 0, -1); //-1 = reset
            }

            //at this point it is known that g is strongly connected and has no dead states
            //so a postman tour exists, compute a postman tour
            GraphTraversals.Graph g =
                new GraphTraversals.Graph(0, mustEdges, optionalEdges,
                                          GraphTraversals.WeakClosureEnum.DoNotClose);
            List<GraphTraversals.Edge> postmanTour =
                new List<GraphTraversals.Edge>(g.GetRuralChinesePostmanTour());

            #region normalize the tour so that it ends in an accepting state and has a reset at the end as a "watchdog"
            //if the last edge has not label -1, i.e. the edge leading back
            //to the initial state is not a reset edge from an accepting state
            //and the last state is not an accepting state
            //then extend the path to an accepting state, from the beginning of the path
            //notice that there must be at least one accepting state, so such an extesion
            //is indeed possible
            GraphTraversals.Edge lastEdge = postmanTour[postmanTour.Count - 1];
            if (lastEdge.label >= 0) //if the last edge is a reset, we are done
            {
                //the last edge leads back to the initial state, because this is a tour
                if (fa.AcceptingStates.Contains(fa.InitialState))
                    postmanTour.Add(new GraphTraversals.Edge(0, 0, -1)); //add a watchdog
                else
                {
                    //create an extesion to the tour from the initial state to the first accepting state
                    List<GraphTraversals.Edge> extension = new List<GraphTraversals.Edge>();
                    foreach (GraphTraversals.Edge edge in postmanTour)
                    {
                        extension.Add(edge);
                        if (fa.AcceptingStates.Contains(states[edge.target]))
                        {
                            //the end state of the edge is accepting, so we are done
                            extension.Add(new GraphTraversals.Edge(0, 0, -1)); //add a watchdog
                            break;
                        }

                    }
                    postmanTour.AddRange(extension);
                }
            }
            #endregion

            #region break up the tour into sequences of transition ids separated by the reset edge
            List<List<int>> paths = new List<List<int>>();
            List<int> path = new List<int>();
            for (int k = 0; k < postmanTour.Count; k++)
            {
                //presense of the watchdog at the end of the tour is assumed here
                GraphTraversals.Edge edge = postmanTour[k];
                if (edge.label < 0) //encountered reset, end of path
                {
                    paths.Add(path);
                    path = new List<int>();
                }
                else
                {
                    path.Add(edge.label);
                }
            }
            #endregion

            #region map the paths into action sequences
            Sequence<Sequence<CompoundTerm>> res = Sequence<Sequence<CompoundTerm>>.EmptySequence;
            foreach (List<int> path1 in paths)
            {
                Sequence<CompoundTerm> transSeq = Sequence<CompoundTerm>.EmptySequence;
                foreach (int transId in path1)
                    transSeq = transSeq.AddLast(mustTransitions[transId].Second);
                res = res.AddLast(transSeq);
            }
            #endregion

            return res;
        }
示例#5
0
文件: graph.cs 项目: juhan/NModel
        /// <summary>
        /// Creates a graph from a file.
        /// </summary>
        /// <param name="fileName"></param>
        /// <returns></returns>
        internal static Graph CreateFromFile(string fileName)
        {
            StreamReader sr=new StreamReader(fileName);

              if(sr.BaseStream.CanRead==false)
            {
              sr.Close();
              return null;
            }

              sr.ReadLine(); //swallow start vertex

              int initVertex= Int32.Parse(sr.ReadLine());

              ArrayList must=new ArrayList();
              sr.ReadLine();//swallow "must"

              RBMap edgeProbs=new RBMap();

              string s=sr.ReadLine();
              while(s!="optional"){

            //string [] split=s.Split(' ');

            must.Add(ReadEdge(s,edgeProbs));

            s=sr.ReadLine();

              }

              //"optional" has been swallowed already

              s=sr.ReadLine();
              ArrayList opt=new ArrayList();

              while(s.StartsWith("nond vertices")==false){

            opt.Add(ReadEdge(s,edgeProbs));

            s=sr.ReadLine();

              }

              string [] spl=s.Split(' ');
              ArrayList nondVertices=new ArrayList();

              for(int i=2;i<spl.Length;i++){
                if(!String.IsNullOrEmpty(spl[i]))
                    nondVertices.Add(Int32.Parse(spl[i]));
              }

              Graph g=new Graph(initVertex,must.ToArray(typeof(Edge)) as Edge[],
                        opt.ToArray(typeof(Edge)) as Edge[],
                        nondVertices.ToArray(typeof(int)) as int[],WeakClosureEnum.DoNotClose);

              g.edgeProbabilities=edgeProbs;
              return g;
        }
示例#6
0
文件: graph.cs 项目: juhan/NModel
 internal Pred(Graph g,int v)
 {
     this.graph=g;
     this.vert=v;
 }
示例#7
0
        public static Sequence <Sequence <CompoundTerm> > GenerateTestSequences(FSM fa)
        {
            //Eliminate dead states from the fa
            Set <Term> deadStates  = GetDeadStates(fa);
            Set <Term> aliveStates = fa.States.Difference(deadStates);
            Set <Triple <Term, CompoundTerm, Term> > aliveTransitions =
                fa.Transitions.Select(delegate(Triple <Term, CompoundTerm, Term> trans)
            {
                return(aliveStates.Contains(trans.First) &&
                       aliveStates.Contains(trans.Third));
            });

            if (aliveTransitions.IsEmpty) //test suite cannot be generated
            {
                return(Sequence <Sequence <CompoundTerm> > .EmptySequence);
            }

            //Build a graph from the alive transitions
            Term[] states = new Term[aliveStates.Count];
            Dictionary <Term, int> stateToVertexMap = new Dictionary <Term, int>();

            states[0] = fa.InitialState;
            stateToVertexMap[fa.InitialState] = 0;
            int i = 1;

            foreach (Term state in aliveStates.Remove(fa.InitialState))
            {
                states[i] = state;
                stateToVertexMap[state] = i++;
            }

            //create edges that must be traversed
            GraphTraversals.Edge[] mustEdges = new GraphTraversals.Edge[aliveTransitions.Count];
            Triple <Term, CompoundTerm, Term>[] mustTransitions = new Triple <Term, CompoundTerm, Term> [aliveTransitions.Count];
            i = 0;
            foreach (Triple <Term, CompoundTerm, Term> trans in aliveTransitions)
            {
                GraphTraversals.Edge edge = new GraphTraversals.Edge(stateToVertexMap[trans.First],
                                                                     stateToVertexMap[trans.Third], i);
                mustEdges[i]         = edge;
                mustTransitions[i++] = trans;
            }

            //add an optional edge with label -1 from every accepting state
            //to the initial state, this corresponds to a reset action
            GraphTraversals.Edge[] optionalEdges =
                new GraphTraversals.Edge[fa.AcceptingStates.Count];
            i = 0;
            foreach (Term accState in fa.AcceptingStates)
            {
                int accVertex = stateToVertexMap[accState];
                optionalEdges[i++] = new GraphTraversals.Edge(accVertex, 0, -1); //-1 = reset
            }

            //at this point it is known that g is strongly connected and has no dead states
            //so a postman tour exists, compute a postman tour
            GraphTraversals.Graph g =
                new GraphTraversals.Graph(0, mustEdges, optionalEdges,
                                          GraphTraversals.WeakClosureEnum.DoNotClose);
            List <GraphTraversals.Edge> postmanTour =
                new List <GraphTraversals.Edge>(g.GetRuralChinesePostmanTour());

            #region normalize the tour so that it ends in an accepting state and has a reset at the end as a "watchdog"
            //if the last edge has not label -1, i.e. the edge leading back
            //to the initial state is not a reset edge from an accepting state
            //and the last state is not an accepting state
            //then extend the path to an accepting state, from the beginning of the path
            //notice that there must be at least one accepting state, so such an extesion
            //is indeed possible
            GraphTraversals.Edge lastEdge = postmanTour[postmanTour.Count - 1];
            if (lastEdge.label >= 0) //if the last edge is a reset, we are done
            {
                //the last edge leads back to the initial state, because this is a tour
                if (fa.AcceptingStates.Contains(fa.InitialState))
                {
                    postmanTour.Add(new GraphTraversals.Edge(0, 0, -1)); //add a watchdog
                }
                else
                {
                    //create an extesion to the tour from the initial state to the first accepting state
                    List <GraphTraversals.Edge> extension = new List <GraphTraversals.Edge>();
                    foreach (GraphTraversals.Edge edge in postmanTour)
                    {
                        extension.Add(edge);
                        if (fa.AcceptingStates.Contains(states[edge.target]))
                        {
                            //the end state of the edge is accepting, so we are done
                            extension.Add(new GraphTraversals.Edge(0, 0, -1)); //add a watchdog
                            break;
                        }
                    }
                    postmanTour.AddRange(extension);
                }
            }
            #endregion

            #region break up the tour into sequences of transition ids separated by the reset edge
            List <List <int> > paths = new List <List <int> >();
            List <int>         path  = new List <int>();
            for (int k = 0; k < postmanTour.Count; k++)
            {
                //presense of the watchdog at the end of the tour is assumed here
                GraphTraversals.Edge edge = postmanTour[k];
                if (edge.label < 0) //encountered reset, end of path
                {
                    paths.Add(path);
                    path = new List <int>();
                }
                else
                {
                    path.Add(edge.label);
                }
            }
            #endregion

            #region map the paths into action sequences
            Sequence <Sequence <CompoundTerm> > res = Sequence <Sequence <CompoundTerm> > .EmptySequence;
            foreach (List <int> path1 in paths)
            {
                Sequence <CompoundTerm> transSeq = Sequence <CompoundTerm> .EmptySequence;
                foreach (int transId in path1)
                {
                    transSeq = transSeq.AddLast(mustTransitions[transId].Second);
                }
                res = res.AddLast(transSeq);
            }
            #endregion

            return(res);
        }
示例#8
0
        internal static EdgesAndExpectations GetStaticStrategy(Graph graph,
            int[] sources,
            HSet targets,
            int nStates,
            int resetCost,
            int []deadStates)
        {
            foreach(int t in targets){
            foreach(Edge l in graph.EdgesAtVertex(t))
              l.weight=0;
              }

              //fix the edges weights
              foreach(Edge l in graph.MustEdges){
            if(l.target>=nStates)
              l.weight=0;
              }
              foreach(Edge l in graph.OptionalEdges)
            l.weight=resetCost;

              if(graph.NumberOfVertices>1000){//Value iteration becomes too slow
            return graph.GetStaticStrategyWithDistancesToAcceptingStates(sources, targets.ToArray(typeof(int)) as int[]);
              }

              HSet deadStatesSet=new HSet(deadStates);

              //create reachableGraph
              bool []reachableVerts=new bool[graph.NumberOfVertices];

              //we have to walk backwards from the targets avoiding dead states
              graph.InitBackwardEdges();

              foreach(int i in targets)
            reachableVerts[i]=true;

              System.Collections.Queue queue=new System.Collections.Queue(targets);

              while(queue.Count>0)
            {
              int i=(int)queue.Dequeue();
              foreach(int v in graph.Pred(i))
            {
              if(!reachableVerts[v] && !deadStatesSet.Contains(v))
                {
                  queue.Enqueue(v);
                  reachableVerts[v]=true;
                }

            }
            }

              int numberOfReachableVerts=0;
              foreach(bool b in reachableVerts)
            if(b)
              numberOfReachableVerts++;

              Edge[] strategyEdges;
              double [] expectations;

              if(numberOfReachableVerts==graph.NumberOfVertices)
            {
              expectations=GetExpectations(graph,/* sources,*/targets,nStates);

              if(expectations==null)
            return new EdgesAndExpectations();

              strategyEdges=new Edge[nStates];

              for(int i=0;i<nStates&&i<graph.NumberOfVertices;i++){

            if(targets.Contains(i)||deadStatesSet.Contains(i))
              continue;

            double min=Single.MaxValue;

            Edge stEdge=null;

            foreach(Edge l in graph.EdgesAtVertex(i)){
              int j=l.target;
              if(expectations[j]<min){
                min=expectations[j];

                stEdge=l;
              }
            }

            strategyEdges[i]=stEdge;
              }

            }
              else
            { //numberOfReachableVerts<graph.NumberOfVertices)

              int [] graphToRG=new int[graph.NumberOfVertices];
              //reachable graph to graph
              int [] rGToGraph=new int[numberOfReachableVerts];

              int count=0;
              int rNStates=0;
              for(int i=0;i<reachableVerts.Length;i++)
            if(reachableVerts[i])
              {
                graphToRG[i]=count;
                rGToGraph[count]=i;
                count++;
                if(i<nStates)
                  rNStates++;
              }

              System.Collections.ArrayList mustEdges=new System.Collections.ArrayList();

              foreach(Edge l in graph.MustEdges)
            {
              if( reachableVerts[l.source]&& reachableVerts[l.target])
                {
                  Edge ml=new Edge(graphToRG[l.source],graphToRG[l.target], l.label,l.weight);
                  mustEdges.Add(ml);
                }
            }

              System.Collections.ArrayList nondVerts=new System.Collections.ArrayList();

              for(int i=nStates;i<graph.NumberOfVertices;i++)
            {
              if(reachableVerts[i])
                nondVerts.Add(graphToRG[i]);
            }

              Graph rGraph=new Graph(0,mustEdges.ToArray(typeof(Edge)) as Edge[],new Edge[0],
                                 nondVerts.ToArray(typeof(int)) as int[],true,WeakClosureEnum.DoNotClose);

              int []rSources=new int[sources.Length];
              int c=0;
              foreach(int s in sources)
            {
              rSources[c++]=graphToRG[s];
            }

              HSet rTargets=new HSet();

              foreach(int s in targets)
            {
              if( reachableVerts[s])
                {
                  rTargets.Insert(graphToRG[s]);
                }
            }

              double []rExpectations=GetExpectations(rGraph,/*rSources,*/ rTargets,rNStates);

              if(rExpectations==null)
            return new EdgesAndExpectations();

              strategyEdges=new Edge[nStates];

              for(int i=0;i<nStates;i++){

            if(!reachableVerts[i])
              continue;

            if(targets.Contains(i)||deadStatesSet.Contains(i))
              continue;

            double min=Single.MaxValue;

            Edge stEdge=null;

            foreach(Edge l in graph.EdgesAtVertex(i)){
              int j=l.target;

              if(reachableVerts[j])
                if(rExpectations[graphToRG[j]]<min){
                  min=rExpectations[graphToRG[j]];
                  stEdge=l;
                }
            }

            strategyEdges[i]=stEdge;
              }

              expectations=new double[graph.NumberOfVertices];
              if(expectations==null)
            return new EdgesAndExpectations();

              for(int i=0;i<expectations.Length;i++)
            expectations[i]=Int32.MaxValue;

              for(int i=0;i<rExpectations.Length;i++)
            expectations[rGToGraph[i]]=rExpectations[i];

            }

              graph.CleanTheStrategy(strategyEdges,sources);

              return new EdgesAndExpectations(strategyEdges, expectations);
        }
示例#9
0
        //ValueIteration(Graph graph,int[] sources,HSet targets,int nStates)
        /*
          From "Play to test"
          Value iteration is the most widely used algorithm for solving discounted Markov decision
          problems (see e.g. [21]). Reachability games give rise to non-discounted Markov
          decision problems. Nevertheless the value iteration algorithm applies; this is a practical
          approach for computing strategies for transient test graphs. Test graphs, modified by inserting
          a zero-cost edge (0; 0), correspond to a subclass of negative stationary Markov
          decision processes (MDPs) with an infinite horizon, where rewards are negative and
          thus regarded as costs, strategies are stationary, i.e. time independent, and there is no
          finite upper bound on the number of steps in the process. The optimization criterion
          for our strategies corresponds to the expected total reward criterion, rather than the
          expected discounted reward criterion used in discounted Markov decision problems.
          Let G = (V;E; V a; V p; g; p; c) be a test graph modified by inserting a zero-cost
          edge (0; 0). The classical value iteration algorithm works as follows on G.

          Value iteration Let n = 0 and let M0 be the zero vector with coordinates V so that
          every M0[u] = 0. Given n and Mn, we compute Mn+1 (and then increment n):
          Mn+1[u] ={ min {c(u,v) +Mn[v]:(u,v) in E} if u is an active state}
          or sum {p(u,v)*(c(u,v) +Mn[v]); if u is a choice point

          Value iteration for negative MDPs with the expected total reward criterion, or negative
          Markov decision problems for short, does not in general converge to an optimal
          solution, even if one exists. However, if there exists a strategy for which the the expected
          cost is finite for all states [21, Assumption 7.3.1], then value iteration does converge for
          negative Markov decision problems [21, Theorem 7.3.10]. In light of lemmas 2 and 3,
          this implies that value iteration converges for transient test graphs. Let us make this
          more precise, as a corollary of Theorem 7.3.10 in [21].
        */
        //nStates marks the end of active states, choice points start after that
        static double[] ValueIteration(Graph graph, HSet targets, int nStates)
        {
            graph.InitEdgeProbabilities();

              double[]v0=new double[graph.NumberOfVertices];
              double[]v1=new double[graph.NumberOfVertices];
              double eps=1.0E-6;
              double delta;
              double[] v=v0;
              //double[] vnew=v1;

              //      CheckTransience(graph,targets);

              int nOfIter=0;
              do{

            delta=0;

            for(int i=0;i<nStates&&i<graph.NumberOfVertices;i++){

              if(targets.Contains(i))
            continue;

              double min=Double.MaxValue;

              foreach(Edge l in graph.EdgesAtVertex(i)){
            double r=((double)l.weight)+v[l.target];
            if(r<min)
              min=r;
              }
              if(min!=Double.MaxValue){
            v1[i]=min;
            if(delta<min-v[i])
              delta=min-v[i];
              }

            }

            for(int i=nStates;i<graph.NumberOfVertices;i++){
              if(targets.Contains(i))
            continue;

              double r=0;
              foreach(Edge l in graph.EdgesAtVertex(i))
            r+=graph.EdgeProbability(l)*(((double)l.weight)+v[l.target]);

              v1[i]=r;
              if(delta<r-v[i])
            delta=r-v[i];
            }

            nOfIter++;

            //swap v and v1
            double[] vtmp=v;
            v=v1;
            v1=vtmp;
              }
              while(delta>eps && nOfIter<10000);

              if(delta>eps){
            return null; //the result is erroneous
              }

              return v;
        }
示例#10
0
        static void CheckTransience(Graph graph,HSet targets)
        {
            Queue q=new Queue();
              bool[] reached=new bool[graph.NumberOfVertices];
              foreach(int v in targets){
            reached[v]=true;
            q.Enqueue(v);
              }
              while(q.Count>0){
            int v=(int)q.Dequeue();
            foreach(int u in new Pred(graph,v)){
              if(reached[u]==false){
            reached[u]=true;
            q.Enqueue(u);
              }
            }
              }

              foreach(bool b in reached)
            if(!b)
              throw new InvalidOperationException("some vertex has not been reached");
        }