您的位置:首页 > 其它

闭环最短路径算法

2015-06-11 14:47 218 查看
适用于闭环状态下各节点间距相等,计算从其中一个节点去1个或多个目标节点的最短路径,最短路径可以折返取得。

下面是一个有着10000个节点的闭环,从其中一个节点去往9个目标节点的示例。

static void Main(string[] args)
{
int x = 3;//起点
int[] arr = { 2, 2000, 4900, 9990, 6001, 200, 400, 80, 60 };//目的地
int pe = 10000;//全周总步进
int[] pathArr = ShortestPath(x, arr, pe);
Console.WriteLine(string.Join(",",pathArr));
}

static int[] ShortestPath(int x, int[] goalArr, int perim)
{
    List<int> aList = goalArr.Where(p => p != x && p >= 1 && p <= perim).ToList();
    if (!aList.Any()) return null;
    //最大折返步进数(折返步进数的3倍小于等于1/2总周步进,折返才可能存在最优路径。)
    int bl = (int)Math.Floor(perim / 6m);
    int a = x;
    int b = x;
    int c = x - bl < 1 ? perim + x - bl : x - bl;
    int d = x + bl > perim ? x + bl - perim : x + bl;         

    IEnumerable<int> aIE = new int[] { x };
    IEnumerable<int> bIE = new int[] { x };
    IEnumerable<int> cIE = new int[] { };
    IEnumerable<int> dIE = new int[] { };
    //如在双向最大折返步进内存在目的地,取双向最远折返点到起点之间的步进
    for (int i = 0; i < bl ; i++)
    {
        if (cIE.Any() || aList.Contains(c)) cIE = (new int[] { c }).Concat(cIE);
        if (dIE.Any() || aList.Contains(d)) dIE = (new int[] { d }).Concat(dIE);
        c = c + 1 > perim ? 1 : c + 1;
        d = d - 1 < 1 ? perim : d - 1;
    }
    cIE = (new int[] { x }).Concat(cIE);
    dIE = (new int[] { x }).Concat(dIE);
    c = cIE.Last();
    d = dIE.Last();

    List<int> cList = aList.Where(p => !cIE.Contains(p)).ToList();
    if (!cList.Any()) return cIE.ToArray();
    List<int> dList = aList.Where(p => !dIE.Contains(p)).ToList();
    if (!dList.Any()) return dIE.ToArray();
    List<int> bList = aList.GetRange(0, aList.Count);

    for (int i = 1; i < perim; i++)
    {
        a = a + 1 > perim ? 1 : a + 1;
        b = b - 1 < 1 ? perim : b - 1;
        c = c + 1 > perim ? 1 : c + 1;
        d = d - 1 < 1 ? perim : d - 1;
        aIE = aIE.Concat(new int[] { a });
        if (aList.Contains(a))
        {
            aList.Remove(a);
            if (!aList.Any()) return aIE.ToArray();
        }
        bIE = bIE.Concat(new int[] { b });
        if (bList.Contains(b))
        {
            bList.Remove(b);
            if (!bList.Any()) return bIE.ToArray();
        }

        if (cList.Any()) cIE = cIE.Concat(new int[] { c });
        if (cList.Contains(c)) cList.Remove(c);
        if (!cList.Any() && cIE.Count() < dIE.Count()) return cIE.ToArray();

        if (dList.Any()) dIE = dIE.Concat(new int[] { d });
        if (dList.Contains(d)) dList.Remove(d);
        if (!dList.Any() && dIE.Count() < cIE.Count()) return dIE.ToArray();
    }
    return null;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: