您的位置:首页 > 编程语言 > Go语言

Dijkstra Algorithm 实现

2016-01-23 12:39 393 查看
using UnityEngine;
using System;
using System.Collections;
using System.Collections.Generic;

public class DijkstraAlgorithm : MonoBehaviour
{
public string StartPos = "a";
public string TargetPos = "e";
public bool CalculateAgain = false;

// 顶点集
private List<string> VertexSet = new List<string>(){"a", "b", "c", "d", "e"};
// 路径值
private Dictionary<string, int> valueMap = new Dictionary<string, int>();

//已处理顶点
private List<string> _AfterCalculate = new List<string>();
//未处理顶点
private List<string> _NotCalculte = new List<string>();

// 顶点权值记录
private Dictionary<string, int> vertexValue = new Dictionary<string, int>();
// 第一个是目标节点,后面是路径
private Dictionary<string, string> PathRecord = new Dictionary<string, string>();

private void DijkstraAlgo(string startVertex, string targetVertex)
{
// 清除掉所有信息
vertexValue.Clear();
PathRecord.Clear();
_NotCalculte.Clear();
_AfterCalculate.Clear();
valueMap.Clear();

// 初始化路径图数据
InitPathValue();
InitVertexValue();

// 设置起点的路径值为0
vertexValue[startVertex] =  0;
PathRecord.Add(startVertex, startVertex);

// 设置未处理的顶点列表为所有的顶点
_NotCalculte.AddRange(VertexSet);

while(_NotCalculte.Count > 0)
{
// 找到权值最小的作为起点
// 找到最小权值顶点
string minVertex = _NotCalculte[0];
int minVertexValue = vertexValue[minVertex];
for(int index = 0, imax = _NotCalculte.Count; index < imax; index++)
{
string crtVertex = _NotCalculte[index];
int crtVertexValue = vertexValue[crtVertex];

if(minVertexValue > crtVertexValue)
{
minVertex = crtVertex;
minVertexValue = crtVertexValue;
}
}

string tempStart = minVertex;

// 以起点开始,计算其它顶点的权值
for(int index = 0, imax = _NotCalculte.Count; index < imax; index++)
{
string targetPos = _NotCalculte[index];

// 查看当前点到每个点的路径值
int pathValue = GetPathValue(tempStart, targetPos);
if(pathValue == int.MaxValue)
{
continue;
}

// 在有路径的情况下,比较当前的顶点权值
// 当前点的路径权值直接从记录中查找,新的权值等于开始点的权值+ 路径权值
int crtValue = vertexValue[targetPos];
int preVextex = vertexValue[tempStart];
if(crtValue > preVextex + pathValue)
{
vertexValue[targetPos] = preVextex + pathValue;

// 记录其路径
if(PathRecord.ContainsKey(targetPos))
{
PathRecord.Remove(targetPos);
}

// 路径等于前一节点 + 当前节点
string crtPath = PathRecord[tempStart] + targetPos;
PathRecord.Add(targetPos, crtPath);
}
}

// 将最小权值点移动到已处理顶点列表中
_AfterCalculate.Add(tempStart);
_NotCalculte.Remove(tempStart);
}

PrintMinPathRecord(targetVertex);
}

void Update()
{
if(CalculateAgain)
{
CalculateAgain = false;
DijkstraAlgo(StartPos, TargetPos);
}
}

private void InitPathValue()
{
valueMap.Add("ab", 3);
valueMap.Add("ac", 2);
valueMap.Add("bc", 2);
valueMap.Add("cd", 1);
valueMap.Add("ce", 6);
valueMap.Add("de", 1);
}

private void InitVertexValue()
{
for(int index = 0, imax = VertexSet.Count; index < imax; index++)
{
string vertex = VertexSet[index];
vertexValue.Add(vertex, int.MaxValue);
}
}

private void PrintVertexValue()
{
foreach(var key in vertexValue.Keys)
{
Debug.Log(key + " = " + vertexValue[key]);
}
}

private void PrintMinPathRecord(string targetPos)
{
string minPath;
if(PathRecord.TryGetValue(targetPos, out minPath))
{
Debug.Log("PATH = " + minPath);
}
}

private void PrintMinPathRecord()
{
Debug.Log("************Min PATH *****************");
foreach(var key in PathRecord.Keys)
{
Debug.Log(key + " = " + PathRecord[key]);
}

Debug.Log("************End PATH *****************");
}

private string GetVertexMinPath(string vertex)
{
string minPath;
if(!PathRecord.TryGetValue(vertex,out minPath))
{
return null;
}
return minPath;
}

private int GetPathValue(string s, string d)
{
foreach(var key in valueMap.Keys)
{
string tempS = key.Substring(0, 1);
string tempD = key.Substring(1, 1);

if(tempS == s && tempD == d)
{
return valueMap[key];
}
}

return int.MaxValue;
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: