GraphTraversal_CTU.cs 4.2 KB
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace TheMachine
{
    public class GraphTraversal_CTU
    {
        public List<Point_CTU> PointCodes = new List<Point_CTU>();
        // 用于存储单向联通的边  
        public List<(Point_CTU, Point_CTU)> oneWayEdges = new List<(Point_CTU, Point_CTU)>();
        // 用于存储双向联通的边  
        public List<(Point_CTU, Point_CTU)> twoWayEdges = new List<(Point_CTU, Point_CTU)>();

        public void Traverse(Point_CTU start)
        {
            Stack<Point_CTU> stack = new Stack<Point_CTU>();
            stack.Push(start);

            while (stack.Count > 0)
            {
                Point_CTU current = stack.Pop();

                if (current.Visited)
                    continue;

                current.Visited = true;

                var up = ComputeCTUPoint(current, current.Up, "Up");    // 上  
                var down = ComputeCTUPoint(current, current.Down, "Down");    // 上  
                var left = ComputeCTUPoint(current, current.Left, "Left");    // 上  
                var right = ComputeCTUPoint(current, current.Right, "Right");    // 上  
                if (up != null)
                {
                    current.Up.X = up.X;
                    current.Up.Y = up.Y;
                }
                if (down != null)
                {
                    current.Down.X = down.X;
                    current.Down.Y = down.Y;
                }
                if (left != null)
                {
                    current.Left.X = left.X;
                    current.Left.Y = left.Y;
                }
                if (right != null)
                {
                    current.Right.X = right.X;
                    current.Right.Y = right.Y;
                }
                // 将未访问的邻近点压入栈中  
                if (current.Up != null && !current.Up.Visited)
                    stack.Push(current.Up);
                if (current.Down != null && !current.Down.Visited)
                    stack.Push(current.Down);
                if (current.Left != null && !current.Left.Visited)
                    stack.Push(current.Left);
                if (current.Right != null && !current.Right.Visited)
                    stack.Push(current.Right);
            }
        }

        private Point_CTU ComputeCTUPoint(Point_CTU from, Point_CTU to, string angle)
        {

            if (to == null)
                return null;
            //if (to.Id == 1709)
            //{
            //    int tt = 1;
            //}
            Point_CTU point_CTU = new Point_CTU(from.X, from.Y, to.Id);
            if (angle == "Up")
            {
                point_CTU.Y = point_CTU.Y + from.UpDistance;
                PointCodes.Add(point_CTU);
                to = point_CTU;
            }
            else if (angle == "Down")
            {
                point_CTU.Y = point_CTU.Y - from.DownDistance;
                PointCodes.Add(point_CTU);
                to = point_CTU;
            }
            else if (angle == "Left")
            {
                point_CTU.X = point_CTU.X - from.LeftDistance;
                PointCodes.Add(point_CTU);
                to = point_CTU;
            }
            else if (angle == "Right")
            {
                point_CTU.X = point_CTU.X + from.RightDistance;
                PointCodes.Add(point_CTU);
                to = point_CTU;
            }
            //if (point_CTU.Id == 1707)
            //{
            //    int yy = 1;
            //}
            return to;
        }
        // 添加边到对应的列表中  
        private void AddEdges(Point_CTU from, Point_CTU to)
        {
            if (to == null)
                return;

            // 单向联通  
            if (from.Up == to || from.Down == to || from.Left == to || from.Right == to)
                oneWayEdges.Add((from, to));

            // 双向联通(如果两个点都互相指向对方)  
            if ((to.Up == from || to.Down == from || to.Left == from || to.Right == from) &&
                !twoWayEdges.Contains((to, from))) // 避免重复添加  
            {
                twoWayEdges.Add((from, to));
            }
        }


    }
}