Further refinements to A*
This commit is contained in:
parent
f2ab1c0598
commit
b56a53dc81
@ -33,30 +33,38 @@ namespace TrueCraft.Core.AI
|
|||||||
// Thanks to www.redblobgames.com/pathfinding/a-star/implementation.html
|
// Thanks to www.redblobgames.com/pathfinding/a-star/implementation.html
|
||||||
|
|
||||||
var parents = new Dictionary<Coordinates3D, Coordinates3D>();
|
var parents = new Dictionary<Coordinates3D, Coordinates3D>();
|
||||||
var costs = new Dictionary<Coordinates3D, int>();
|
var costs = new Dictionary<Coordinates3D, double>();
|
||||||
var frontier = new PriorityQueue<Coordinates3D>();
|
var openset = new PriorityQueue<Coordinates3D>();
|
||||||
|
var closedset = new HashSet<Coordinates3D>();
|
||||||
|
|
||||||
frontier.Enqueue(start, 0);
|
openset.Enqueue(start, 0);
|
||||||
parents[start] = start;
|
parents[start] = start;
|
||||||
costs[start] = 0;
|
costs[start] = start.DistanceTo(goal);
|
||||||
|
|
||||||
while (frontier.Count > 0)
|
while (openset.Count > 0)
|
||||||
{
|
{
|
||||||
var current = frontier.Dequeue();
|
var current = openset.Dequeue();
|
||||||
if (current == goal)
|
if (current == goal)
|
||||||
return TracePath(start, goal, parents);
|
return TracePath(start, goal, parents);
|
||||||
|
|
||||||
|
closedset.Add(current);
|
||||||
|
|
||||||
for (int i = 0; i < Neighbors.Length; i++)
|
for (int i = 0; i < Neighbors.Length; i++)
|
||||||
{
|
{
|
||||||
var next = Neighbors[i] + current;
|
var next = Neighbors[i] + current;
|
||||||
|
if (closedset.Contains(next))
|
||||||
|
continue;
|
||||||
|
|
||||||
var id = world.GetBlockID(next);
|
var id = world.GetBlockID(next);
|
||||||
if (id != 0)
|
if (id != 0)
|
||||||
continue; // TODO: Make this more sophisticated
|
continue; // TODO: Make this more sophisticated
|
||||||
|
|
||||||
var cost = (int)(costs[current] + current.DistanceTo(next));
|
var cost = (int)(costs[current] + current.DistanceTo(next));
|
||||||
if (!costs.ContainsKey(next) || cost < costs[next])
|
if (!costs.ContainsKey(next) || cost < costs[next])
|
||||||
{
|
{
|
||||||
costs[next] = cost;
|
costs[next] = cost;
|
||||||
var priority = (int)(cost + next.DistanceTo(goal));
|
var priority = cost + next.DistanceTo(goal);
|
||||||
frontier.Enqueue(next, priority);
|
openset.Enqueue(next, priority);
|
||||||
parents[next] = current;
|
parents[next] = current;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -7,14 +7,14 @@ namespace TrueCraft.Core.AI
|
|||||||
// Thanks to www.redblobgames.com/pathfinding/a-star/implementation.html
|
// Thanks to www.redblobgames.com/pathfinding/a-star/implementation.html
|
||||||
public class PriorityQueue<T>
|
public class PriorityQueue<T>
|
||||||
{
|
{
|
||||||
private List<Tuple<T, int>> elements = new List<Tuple<T, int>>();
|
private List<Tuple<T, double>> elements = new List<Tuple<T, double>>();
|
||||||
|
|
||||||
public int Count
|
public int Count
|
||||||
{
|
{
|
||||||
get { return elements.Count; }
|
get { return elements.Count; }
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Enqueue(T item, int priority)
|
public void Enqueue(T item, double priority)
|
||||||
{
|
{
|
||||||
elements.Add(Tuple.Create(item, priority));
|
elements.Add(Tuple.Create(item, priority));
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user