예제 #1
0
        /// <summary>
        /// 计算图中自环的个数(自环就是边连到自己形成的环)
        /// </summary>
        /// <returns>自环的个数</returns>
        public static int SelfLoopCount(this IGraph graph)
        {
            int cnt = 0;

            for (int vertex = 0; vertex < graph.VertexCount; vertex++)
            {
                cnt += graph.Adjacent(vertex).Count(v => v == vertex);
            }

            return(cnt / 2); // 每条边都会被计算两次,所以要除以2
        }
예제 #2
0
 private void SearchC(int v)
 {
     order[v] = counter++;
     foreach (int adj in g.Adjacent(v))
     {
         if (order[adj] == -1)
         {
             SearchC(adj);
         }
     }
 }
예제 #3
0
        public List <IVertex> GetWay()
        {
            Open  = new PriorityQueue();
            Close = new List <IVertex>();
            var s = new List <IVertex>();

            s.Add(start);
            Open.Add(FFunction(s), s);
            while (Open.Count != 0)
            {
                // Выбираем наилучший путь из очереди
                var p = Open.First();
                Open.RemoveFirst();
                // Рассматриваем его последнюю вершину
                var x = p.Last();
                // Если она уже была посещена, отбрасываем этот путь
                if (Close.Contains(x))
                {
                    continue;
                }
                // Если это целевая вершина, сохраним стоимость пути и вернем его
                if (x.Equals(goal))
                {
                    currentPathLength = 0;
                    for (int i = 1; i < p.Count; i++)
                    {
                        currentPathLength += graph.Cost(p[i], p[i - 1]);
                    }
                    firstRun = false;
                    return(p);
                }
                // Отмечаем текущую вершину как посещенную
                Close.Add(x);
                // Раскрываем непосещенные смежные вершины
                foreach (var y in graph.Adjacent(x))
                {
                    if (!Close.Contains(y))
                    {
                        var newPath = new List <IVertex>(p);
                        newPath.Add(y);
                        // Если это первый запуск, то алгоритм работает, как стандартный алгоритм А*
                        // Иначе отбрасываем потенциальные пути, для которых допустимая функция дает оценку, большую, чем стоимость последнего найденного пути
                        if (firstRun || FAccessibleFunction(newPath) < currentPathLength)
                        {
                            Open.Add(FFunction(newPath), newPath);
                        }
                    }
                }
            }
            // Если путь не нашелся, выбрасываем исключение
            throw new Exception();
        }
예제 #4
0
        private void DFS(IGraph graph, int vertex)
        {
            isConnected[vertex] = true;

            foreach (var v in graph.Adjacent(vertex))
            {
                if (!isConnected[v])
                {
                    edgeTo[v] = vertex;
                    DFS(graph, v);
                }
            }
        }
예제 #5
0
        private void DFS(IGraph g, int v)
        {
            _marked[v] = true;
            _id[v]     = Count;

            foreach (var w in g.Adjacent(v))
            {
                if (!_marked[w])
                {
                    DFS(g, w);
                }
            }
        }
예제 #6
0
        private void DFS(IGraph graph, int vertex)
        {
            isConnected[vertex] = true;
            id[vertex]          = count;

            foreach (var v in graph.Adjacent(vertex))
            {
                if (!isConnected[v])
                {
                    DFS(graph, v);
                }
            }
        }
예제 #7
0
        protected virtual void DFS(IGraph graph, int vertex)
        {
            isConnected[vertex] = true;
            count++;

            foreach (var v in graph.Adjacent(vertex))
            {
                if (!isConnected[v])
                {
                    DFS(graph, v);
                }
            }
        }
예제 #8
0
        public UnionFindSearch(IGraph graph, int vertex)
        {
            vertexCount = graph.VertexCount;
            uf          = new UnionFind(vertexCount);
            start       = vertex;

            for (int from = 0; from < vertexCount; from++)
            {
                foreach (int to in graph.Adjacent(from))
                {
                    uf.Union(from, to);
                }
            }
        }
예제 #9
0
        public void AdjacentTest()
        {
            IGraph <int> graph = GraphMap.New <int>();

            for (int i = 1; i <= 5; i++)
            {
                graph.Add(i);
            }
            graph.Add(1, 5);
            graph.Add(2, 5);
            graph.Add(3, 5);
            graph.Add(4, 5);
            Assert.IsTrue(graph.Adjacent(1, 5));
        }
예제 #10
0
        /// <summary>
        /// 在控制台打印出图的顶点以及边的信息
        /// </summary>
        public static void Print(this IGraph graph)
        {
            Console.WriteLine("打印图");
            Console.WriteLine(graph.VertexCount + "个顶点  " + graph.EdgeCount + "条边");

            for (int i = 0; i < graph.EdgeCount; i++)
            {
                Console.Write(i + ": ");

                foreach (var vertex in graph.Adjacent(i))
                {
                    Console.Write(vertex + " ");
                }

                Console.WriteLine();
            }
        }
예제 #11
0
        // Pathfinding
        public List <Vector3> GetWay()
        {
            Open  = new PriorityQueue();
            Close = new List <IVertex>();
            var s = new List <IVertex>();

            s.Add(start);
            Open.Add(FFunction(s), s);
            while (Open.Count != 0)
            {
                if (CheckForCancellationRequested())
                {
                    return(null);
                }
                var p = Open.First();
                Open.RemoveFirst();
                var x = p.Last();
                if (Close.Contains(x))
                {
                    continue;
                }
                if (x.Equals(goal))
                {
                    spaceManagerInstance.pathfindingThreadsCurCount--;
                    return(p.Select(el => SpaceGraph.GetCellCenterCoordFromIndexOnLevel(((Cube)el).index, pathfindingLevel)).ToList()); //converting List<IVertex> to Lis<Vector3>
                }
                Close.Add(x);
                foreach (var y in graph.Adjacent(x))
                {
                    if (CheckForCancellationRequested())
                    {
                        return(null);
                    }
                    if (!Close.Contains(y))
                    {
                        var newPath = new List <IVertex>(p);
                        newPath.Add(y);
                        Open.Add(FFunction(newPath), newPath);
                    }
                }
            }
            spaceManagerInstance.pathfindingThreadsCurCount--;
            return(null);
        }
예제 #12
0
 private bool SearchRec(int v, int w)
 {
     if (v == w)
     {
         return(true);
     }
     visited.Add(v);
     foreach (int i in graph.Adjacent(v))
     {
         if (!visited.Contains(i))
         {
             if (SearchRec(i, w))
             {
                 path.Add(i);
                 return(true);
             }
         }
     }
     return(false);
 }
예제 #13
0
        private void BFS(IGraph graph, int start)
        {
            Queue <int> queue = new Queue <int>();

            queue.Enqueue(start);
            isConnected[start] = true;

            while (queue.Count > 0)
            {
                int vertex = queue.Dequeue();

                foreach (var v in graph.Adjacent(vertex))
                {
                    if (!isConnected[v])
                    {
                        edgeTo[v] = vertex;
                        queue.Enqueue(v);
                        isConnected[v] = true;
                    }
                }
            }
        }
예제 #14
0
        public IEnumerator GetWay(RTWayInCubes ReturnWay)
        {
            Open  = new PriorityQueue();
            Close = new List <IVertex>();
            var s = new List <IVertex>();

            s.Add(start);
            Open.Add(FFunction(s), s);
            int cyclesCount = 0;

            while (Open.Count != 0)
            {
                // choosing the optimum path out of queue
                var p = Open.First();
                Open.RemoveFirst();
                //consideration of its last node
                var x = p.Last();
                //in case this node has been visited the path is rejected
                if (Close.Contains(x))
                {
                    continue;
                }
                //The path cost is saved and the path is returned if the node is the target point.
                if (x.Equals(goal))
                {
                    currentPathLength = 0;
                    for (int i = 1; i < p.Count; i++)
                    {
                        currentPathLength += graph.Cost(p[i], p[i - 1]);
                    }
                    firstRun = false;
                    ReturnWay(p);
                    break;
                }
                //Current node is marked as visited
                Close.Add(x);
                // Disclosure of unvisited adjacent nodes
                foreach (var y in graph.Adjacent(x))
                {
                    if (!Close.Contains(y))
                    {
                        var newPath = new List <IVertex>(p);
                        newPath.Add(y);
                        //During the first launch the algorithm works as a standard A* algorithm
                        //Otherwise, reject all potential paths if admissible function estimates their cost higher than the cost of the last found path
                        if (firstRun || FAccessibleFunction(newPath) < currentPathLength)
                        {
                            Open.Add(FFunction(newPath), newPath);
                        }
                    }
                }
                if (cyclesCount == 5)
                {
                    cyclesCount = 0;
                    yield return(null);
                }
                else
                {
                    cyclesCount++;
                }
            }
        }
예제 #15
0
        public List <City> Adjacent(City city)
        {
            var cityIdx = _cityIdxLookup[city];

            return(_cityGraph.Adjacent(cityIdx).ToList());
        }
예제 #16
0
 /// <summary>
 /// 计算图中某个顶点的度数
 /// </summary>
 /// <param name="vertex">要计算度数的顶点</param>
 /// <returns>顶点的度数</returns>
 public static int Degree(this IGraph graph, int vertex)
 {
     return(graph.Adjacent(vertex).Count());
 }