求二维数组最短路径c语言,发现在二维数组两点之间的最短路径

我不得不实施A *算法

PNwre.gif

export class PathFinder {

grid: Tile[][];

gridHeight: number;

gridWidth: number;

startTile: Tile;

endTile: Tile;

/** Array of the already checked tiles. */

closedList: List = new List();

openList: List = new List();

constructor(grid: Tile[][], gridHeight: number, gridWidth: number) {

this.grid = grid;

this.gridHeight = gridHeight;

this.gridWidth = gridWidth;

}

searchPath(start: Tile, end: Tile): Tile[] {

this.startTile = start;

this.endTile = end;

/** Path validation */

if (!start.walkable) {

console.log('The start tile in not walkable, choose different tile than', start.index);

return [];

}

if (!end.walkable) {

console.log('The end tile in not walkable, choose different tile than', end.index);

return [];

}

/** Start A* Algorithm */

/** Add the starting tile to the openList */

this.openList.push(start);

let currentTile;

/** While openList is not empty */

while (this.openList.length) {

//current node = node for open list with the lowest cost.

currentTile = this.getTileWithLowestTotal(this.openList);

//if the currentTile is the endTile, then we can stop searching

if(JSON.stringify(currentTile.index) === JSON.stringify(end.index)){

this.startTile.setBackgroundColor("rgba(255, 45, 45, .8)");

this.endTile.setBackgroundColor("rgba(255, 45, 45, .8)");

return this.shortestPath();

}

else {

//move the current tile to the closed list and remove it from the open list.

this.openList.remove(currentTile);

this.closedList.push(currentTile);

// //Get all adjacent Tiles

let adjacentTiles = this.getAdjacentTiles(currentTile);

for (let adjacentTile of adjacentTiles) {

//Get tile is not in the open list

if (!this.openList.contains(adjacentTile)) {

//Get tile is not in the closed list

if (!this.closedList.contains(adjacentTile)) {

//move it to the open list and calculate cost

this.openList.push(adjacentTile);

//calculate the cost

adjacentTile.cost = currentTile.cost + 1;

//calculate the manhattan distance

adjacentTile.heuristic = this.manhattanDistance(adjacentTile);

// calculate the total amount

adjacentTile.total = adjacentTile.cost + adjacentTile.heuristic;

currentTile.setBackgroundColor('rgba(0, 181, 93, 0.8)');

}

}

}

}

}

}

getTileWithLowestTotal(openList: Tile[]): Tile {

let tileWithLowestTotal = new Tile();

let lowestTotal: number = 999999999;

/** Search open tiles and get the tile with the lowest total cost */

for (let openTile of openList) {

if (openTile.total <= lowestTotal) {

//clone lowestTotal

lowestTotal = openTile.total;

tileWithLowestTotal = openTile;

}

}

return tileWithLowestTotal;

}

getAdjacentTiles(current: Tile): Tile[] {

let adjacentTiles: Tile[] = [];

let adjacentTile: Tile;

//Tile to left

if (current.index.x - 1 >= 0) {

adjacentTile = this.grid[current.index.x - 1][current.index.y];

if (adjacentTile && adjacentTile.walkable) {

adjacentTiles.push(adjacentTile);

}

}

//Tile to right

if (current.index.x + 1 < this.gridWidth) {

adjacentTile = this.grid[current.index.x + 1][current.index.y];

if (adjacentTile && adjacentTile.walkable) {

adjacentTiles.push(adjacentTile);

}

}

//Tile to Under

if (current.index.y + 1 < this.gridHeight) {

adjacentTile = this.grid[current.index.x][current.index.y + 1];

if (adjacentTile && adjacentTile.walkable) {

adjacentTiles.push(adjacentTile);

}

}

//Tile to Above

if (current.index.y - 1 >= 0) {

adjacentTile = this.grid[current.index.x][current.index.y - 1];

if (adjacentTile && adjacentTile.walkable) {

adjacentTiles.push(adjacentTile);

}

}

/** TODO: Diagonal moves */

return adjacentTiles;

}

/** Calculate the manhattan distance */

manhattanDistance(adjacentTile: Tile): number {

return Math.abs((this.endTile.index.x - adjacentTile.index.x) +

(this.endTile.index.y - adjacentTile.index.y));

}

shortestPath() {

let startFound: boolean = false;

let currentTile = this.endTile;

let pathTiles = [];

//includes the end tile in the path

pathTiles.push(this.endTile);

this.endTile.ball = true;

while (!startFound) {

let adjacentTiles = this.getAdjacentTiles(currentTile);

//check to see what newest current tile.

for (let adjacentTile of adjacentTiles) {

//check if it is the start tile

if (JSON.stringify(adjacentTile.index) === JSON.stringify(this.startTile.index)){

return pathTiles;

}

//it has to be inside the closedList or openList

if (this.closedList.contains(adjacentTile) || this.openList.contains(adjacentTile)) {

if (adjacentTile.cost <= currentTile.cost && adjacentTile.cost > 0) {

//change the current tile.

currentTile = adjacentTile;

//Add this adjacentTile to the path list

pathTiles.push(adjacentTile);

//highlight way with yellow balls

adjacentTile.ball = true;

break;

}

}

}

}

}

}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
n个点之间的最短距离在C语言中可以通过使用Dijkstra算法来实现。Dijkstra算法是一种用于计算图中节点间最短路径的算法。具体步骤如下: 1. 创建一个二维数组来表示点之间的距离,如果两点之间没有直接连接,则距离设为无穷大。 2. 创建一个一维数组来保存起始点到其他点的最短距离,并初始化为无穷大。 3. 将起始点的最短距离设置为0,并将其添加到一个优先队列中。 4. 从优先队列中取出离起始点最近的点,更新与该点相邻的点的最短距离。 5. 将更新后的点加入优先队列,重复以上步骤直到所有点都被访问过。 通过以上步骤,可以得任意两点之间的最短距离。在C语言中,可以使用二维数组来表示点之间的距离,并通过优先队列来实现Dijkstra算法。具体的代码实现可以参考如下: ```c #include <stdio.h> #include <limits.h> #define V 9 int minDistance(int dist[], bool sptSet[]) { int min = INT_MAX, min_index; for (int v = 0; v < V; v++) if (sptSet[v] == false && dist[v] <= min) min = dist[v], min_index = v; return min_index; } void dijkstra(int graph[V][V], int src) { int dist[V]; bool sptSet[V]; for (int i = 0; i < V; i++) dist[i] = INT_MAX, sptSet[i] = false; dist[src] = 0; for (int count = 0; count < V-1; count++) { int u = minDistance(dist, sptSet); sptSet[u] = true; for (int v = 0; v < V; v++) if (!sptSet[v] && graph[u][v] && dist[u] != INT_MAX && dist[u]+graph[u][v] < dist[v]) dist[v] = dist[u] + graph[u][v]; } for (int i = 0; i < V; i++) printf("从源点到%d的最短距离是 %d\n", i, dist[i]); } int main() { int graph[V][V] = { {0, 4, 0, 0, 0, 0, 0, 8, 0}, {4, 0, 8, 0, 0, 0, 0, 11, 0}, {0, 8, 0, 7, 0, 4, 0, 0, 2}, {0, 0, 7, 0, 9, 14, 0, 0, 0}, {0, 0, 0, 9, 0, 10, 0, 0, 0}, {0, 0, 4, 14, 10, 0, 2, 0, 0}, {0, 0, 0, 0, 0, 2, 0, 1, 6}, {8, 11, 0, 0, 0, 0, 1, 0, 7}, {0, 0, 2, 0, 0, 0, 6, 7, 0} }; dijkstra(graph, 0); return 0; } ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值