2013-10-05 92 views
4

目前我建立在C小的基於網格的遊戲++使用SDL。我製作了一個貼圖類,它代表地圖上的每個貼圖。此瓦片類用於2維矢量,一維表示X軸,另一維表示Y軸。尋路的網格系統

我有一個算法問題,我甚至不知道從哪裏開始的這一點,讓我們說我有這個地圖:

0 0 1 1 0 E 
0 0 0 1 0 1 
0 C 0 1 0 1 
0 1 0 1 0 1 
0 1 1 1 1 1 

C是我的性格,E是一個出口,和1一塊地板磚。

我想找出最優化的方式,以找出是否有一個爲到達出口處的字符的方式。我知道我可以使用一個函數來手動檢查C周圍的每個瓷磚,並且對於C周圍的每個地磚,我再次檢查周圍的每個瓷磚,直到找到達到E的一致路徑,但這看起來不是最佳的。

我能有一個線索或某種方向,其中以確定自己的方向?

+0

廣度優先搜索和Dijkstra算法 – thefourtheye

+1

我認爲,[A *](HTTP:// EN .wikipedia.org/wiki/A * _search_algorithm)是最好的算法(雖然不太容易編碼)。 – memo1288

+0

對於那些你只想知道是否有退出的小型網格,我可能會使用BFS。 –

回答

5

有這麼多的算法,它可以找到兩個點之間的路徑。有三種算法易於實現和理解。

  1. 深度優先搜索(DFS)
  2. 廣度優先搜索(BFS)
  3. Dijkstra算法

深度優先搜索

這種算法,以當前節點,發現所有的鄰居,把它們放在一個堆棧中,一個彈出並遍歷到最後或找到路徑。

廣度優先搜索

這種算法,以當前的節點,發現所有的鄰居,把它們放在一個隊列,一個隊列中取出一個穿越到年底或者找到的路徑。

DFS和BFS之間的不同之處在於,DFS無法保證最佳的解決方案。考慮這種情況。

S 1 1 
1 1 1 
1 1 E 

假設S是(0,0),E是(2,2)。這個迷宮有許多最佳解決方案。因爲DFS檢查其鄰居的路徑直到結束,它可能需要S -> (1,0) -> (2,0) -> (2,1) -> (1,1) -> (1,2) -> E,它將返回6作爲路徑的成本。而BFS找到所有的鄰居,鄰居的鄰居並繼續。如果其中一個鄰居是E,它將返回成本。這將被保證是最佳的。所以,BFS可能會這樣。 S -> (1,0) -> (2,0) -> (2,1) -> E(它發現鄰居的鄰居,它不會走到每個鄰居的盡頭)。

Dijkstra算法

它類似於BFS,但它可以具有權重。在這個例子中,我們假定從一個節點移動到另一個節點的成本爲1個單位。在Dijkstra算法中,它允許我們使用任何正整數作爲成本,並且它對於每個鏈接都可能不同。

結論

如果你想要最佳的結果,去BFS或Dijkstra算法。對於你的情況,BFS應該工作。

0

讓我們假設地面爲:

     1 1 1 1 1 E 
         1 1 1 1 1 1 
         1 1 1 1 1 1 
         1 1 1 1 1 1 
         1 1 1 1 1 1 
         C 1 1 1 1 1 

但總是試圖讓程序知道形狀的特性如廣場上的各方平等所以這就是爲什麼一個完美的對角線方法是最短的,所以如果有牆壁ü可以讓你的程序選擇對角線的最近部分爲

     1 1 1 1 1 E 
         1 1 1 1 0 1 
         1 1 1 0 1 1 
         1 1 0 1 1 1 
         1 0 1 1 1 1 
         C 1 1 1 1 1 

部分旁邊C( 1),然後再對角繼續將有所幫助。 爲任何語法或拼寫錯誤道歉。

1
#include<bits/stdc++.h> 
using namespace std; 

#define ROW 9 
#define COL 10 

// Creating a shortcut for int, int pair type 
typedef pair<int, int> Pair; 

// Creating a shortcut for pair<int, pair<int, int>> type 
typedef pair<double, pair<int, int> > pPair; 

// A structure to hold the neccesary parameters 
struct cell 
{ 
    // Row and Column index of its parent 
    // Note that 0 <= i <= ROW-1 & 0 <= j <= COL-1 
    int parent_i, parent_j; 
    // f = g + h 
    double f, g, h; 
}; 

// A Utility Function to check whether given cell (row, col) 
// is a valid cell or not. 
bool isValid(int row, int col) 
{ 
    // Returns true if row number and column number 
    // is in range 
    return (row >= 0) && (row < ROW) && 
      (col >= 0) && (col < COL); 
} 

// A Utility Function to check whether the given cell is 
// blocked or not 
bool isUnBlocked(int grid[][COL], int row, int col) 
{ 
    // Returns true if the cell is not blocked else false 
    if (grid[row][col] == 1) 
     return (true); 
    else 
     return (false); 
} 

// A Utility Function to check whether destination cell has 
// been reached or not 
bool isDestination(int row, int col, Pair dest) 
{ 
    if (row == dest.first && col == dest.second) 
     return (true); 
    else 
     return (false); 
} 

// A Utility Function to calculate the 'h' heuristics. 
double calculateHValue(int row, int col, Pair dest) 
{ 
    // Return using the distance formula 
    return ((double)sqrt ((row-dest.first)*(row-dest.first) 
          + (col-dest.second)*(col-dest.second))); 
} 

// A Utility Function to trace the path from the source 
// to destination 
void tracePath(cell cellDetails[][COL], Pair dest) 
{ 
    printf ("\nThe Path is "); 
    int row = dest.first; 
    int col = dest.second; 

    stack<Pair> Path; 

    while (!(cellDetails[row][col].parent_i == row 
      && cellDetails[row][col].parent_j == col)) 
    { 
     Path.push (make_pair (row, col)); 
     int temp_row = cellDetails[row][col].parent_i; 
     int temp_col = cellDetails[row][col].parent_j; 
     row = temp_row; 
     col = temp_col; 
    } 

    Path.push (make_pair (row, col)); 
    while (!Path.empty()) 
    { 
     pair<int,int> p = Path.top(); 
     Path.pop(); 
     printf("-> (%d,%d) ",p.first,p.second); 
    } 

    return; 
} 

// A Function to find the shortest path between 
// a given source cell to a destination cell according 
// to A* Search Algorithm 
void aStarSearch(int grid[][COL], Pair src, Pair dest) 
{ 
    // If the source is out of range 
    if (isValid (src.first, src.second) == false) 
    { 
     printf ("Source is invalid\n"); 
     return; 
    } 

    // If the destination is out of range 
    if (isValid (dest.first, dest.second) == false) 
    { 
     printf ("Destination is invalid\n"); 
     return; 
    } 

    // Either the source or the destination is blocked 
    if (isUnBlocked(grid, src.first, src.second) == false || 
      isUnBlocked(grid, dest.first, dest.second) == false) 
    { 
     printf ("Source or the destination is blocked\n"); 
     return; 
    } 

    // If the destination cell is the same as source cell 
    if (isDestination(src.first, src.second, dest) == true) 
    { 
     printf ("We are already at the destination\n"); 
     return; 
    } 

    // Create a closed list and initialise it to false which means 
    // that no cell has been included yet 
    // This closed list is implemented as a boolean 2D array 
    bool closedList[ROW][COL]; 
    memset(closedList, false, sizeof (closedList)); 

    // Declare a 2D array of structure to hold the details 
    //of that cell 
    cell cellDetails[ROW][COL]; 

    int i, j; 

    for (i=0; i<ROW; i++) 
    { 
     for (j=0; j<COL; j++) 
     { 
      cellDetails[i][j].f = FLT_MAX; 
      cellDetails[i][j].g = FLT_MAX; 
      cellDetails[i][j].h = FLT_MAX; 
      cellDetails[i][j].parent_i = -1; 
      cellDetails[i][j].parent_j = -1; 
     } 
    } 

    // Initialising the parameters of the starting node 
    i = src.first, j = src.second; 
    cellDetails[i][j].f = 0.0; 
    cellDetails[i][j].g = 0.0; 
    cellDetails[i][j].h = 0.0; 
    cellDetails[i][j].parent_i = i; 
    cellDetails[i][j].parent_j = j; 

    /* 
    Create an open list having information as- 
    <f, <i, j>> 
    where f = g + h, 
    and i, j are the row and column index of that cell 
    Note that 0 <= i <= ROW-1 & 0 <= j <= COL-1 
    This open list is implenented as a set of pair of pair.*/ 
    set<pPair> openList; 

    // Put the starting cell on the open list and set its 
    // 'f' as 0 
    openList.insert(make_pair (0.0, make_pair (i, j))); 

    // We set this boolean value as false as initially 
    // the destination is not reached. 
    bool foundDest = false; 

    while (!openList.empty()) 
    { 
     pPair p = *openList.begin(); 

     // Remove this vertex from the open list 
     openList.erase(openList.begin()); 

     // Add this vertex to the open list 
     i = p.second.first; 
     j = p.second.second; 
     closedList[i][j] = true; 

     /* 
     Generating all the 8 successor of this cell 

      N.W N N.E 
       \ | /
       \ |/
      W----Cell----E 
       /| \ 
      / | \ 
      S.W S S.E 

     Cell-->Popped Cell (i, j) 
     N --> North  (i-1, j) 
     S --> South  (i+1, j) 
     E --> East  (i, j+1) 
     W --> West   (i, j-1) 
     N.E--> North-East (i-1, j+1) 
     N.W--> North-West (i-1, j-1) 
     S.E--> South-East (i+1, j+1) 
     S.W--> South-West (i+1, j-1)*/ 

     // To store the 'g', 'h' and 'f' of the 8 successors 
     double gNew, hNew, fNew; 

     //----------- 1st Successor (North) ------------ 

     // Only process this cell if this is a valid one 
     if (isValid(i-1, j) == true) 
     { 
      // If the destination cell is the same as the 
      // current successor 
      if (isDestination(i-1, j, dest) == true) 
      { 
       // Set the Parent of the destination cell 
       cellDetails[i-1][j].parent_i = i; 
       cellDetails[i-1][j].parent_j = j; 
       printf ("The destination cell is found\n"); 
       tracePath (cellDetails, dest); 
       foundDest = true; 
       return; 
      } 
      // If the successor is already on the closed 
      // list or if it is blocked, then ignore it. 
      // Else do the following 
      else if (closedList[i-1][j] == false && 
        isUnBlocked(grid, i-1, j) == true) 
      { 
       gNew = cellDetails[i][j].g + 1.0; 
       hNew = calculateHValue (i-1, j, dest); 
       fNew = gNew + hNew; 

       // If it isn’t on the open list, add it to 
       // the open list. Make the current square 
       // the parent of this square. Record the 
       // f, g, and h costs of the square cell 
       //    OR 
       // If it is on the open list already, check 
       // to see if this path to that square is better, 
       // using 'f' cost as the measure. 
       if (cellDetails[i-1][j].f == FLT_MAX || 
         cellDetails[i-1][j].f > fNew) 
       { 
        openList.insert(make_pair(fNew, 
               make_pair(i-1, j))); 

        // Update the details of this cell 
        cellDetails[i-1][j].f = fNew; 
        cellDetails[i-1][j].g = gNew; 
        cellDetails[i-1][j].h = hNew; 
        cellDetails[i-1][j].parent_i = i; 
        cellDetails[i-1][j].parent_j = j; 
       } 
      } 
     } 

     //----------- 2nd Successor (South) ------------ 

     // Only process this cell if this is a valid one 
     if (isValid(i+1, j) == true) 
     { 
      // If the destination cell is the same as the 
      // current successor 
      if (isDestination(i+1, j, dest) == true) 
      { 
       // Set the Parent of the destination cell 
       cellDetails[i+1][j].parent_i = i; 
       cellDetails[i+1][j].parent_j = j; 
       printf("The destination cell is found\n"); 
       tracePath(cellDetails, dest); 
       foundDest = true; 
       return; 
      } 
      // If the successor is already on the closed 
      // list or if it is blocked, then ignore it. 
      // Else do the following 
      else if (closedList[i+1][j] == false && 
        isUnBlocked(grid, i+1, j) == true) 
      { 
       gNew = cellDetails[i][j].g + 1.0; 
       hNew = calculateHValue(i+1, j, dest); 
       fNew = gNew + hNew; 

       // If it isn’t on the open list, add it to 
       // the open list. Make the current square 
       // the parent of this square. Record the 
       // f, g, and h costs of the square cell 
       //    OR 
       // If it is on the open list already, check 
       // to see if this path to that square is better, 
       // using 'f' cost as the measure. 
       if (cellDetails[i+1][j].f == FLT_MAX || 
         cellDetails[i+1][j].f > fNew) 
       { 
        openList.insert(make_pair (fNew, make_pair (i+1, j))); 
        // Update the details of this cell 
        cellDetails[i+1][j].f = fNew; 
        cellDetails[i+1][j].g = gNew; 
        cellDetails[i+1][j].h = hNew; 
        cellDetails[i+1][j].parent_i = i; 
        cellDetails[i+1][j].parent_j = j; 
       } 
      } 
     } 

     //----------- 3rd Successor (East) ------------ 

     // Only process this cell if this is a valid one 
     if (isValid (i, j+1) == true) 
     { 
      // If the destination cell is the same as the 
      // current successor 
      if (isDestination(i, j+1, dest) == true) 
      { 
       // Set the Parent of the destination cell 
       cellDetails[i][j+1].parent_i = i; 
       cellDetails[i][j+1].parent_j = j; 
       printf("The destination cell is found\n"); 
       tracePath(cellDetails, dest); 
       foundDest = true; 
       return; 
      } 

      // If the successor is already on the closed 
      // list or if it is blocked, then ignore it. 
      // Else do the following 
      else if (closedList[i][j+1] == false && 
        isUnBlocked (grid, i, j+1) == true) 
      { 
       gNew = cellDetails[i][j].g + 1.0; 
       hNew = calculateHValue (i, j+1, dest); 
       fNew = gNew + hNew; 

       // If it isn’t on the open list, add it to 
       // the open list. Make the current square 
       // the parent of this square. Record the 
       // f, g, and h costs of the square cell 
       //    OR 
       // If it is on the open list already, check 
       // to see if this path to that square is better, 
       // using 'f' cost as the measure. 
       if (cellDetails[i][j+1].f == FLT_MAX || 
         cellDetails[i][j+1].f > fNew) 
       { 
        openList.insert(make_pair(fNew, 
             make_pair (i, j+1))); 

        // Update the details of this cell 
        cellDetails[i][j+1].f = fNew; 
        cellDetails[i][j+1].g = gNew; 
        cellDetails[i][j+1].h = hNew; 
        cellDetails[i][j+1].parent_i = i; 
        cellDetails[i][j+1].parent_j = j; 
       } 
      } 
     } 

     //----------- 4th Successor (West) ------------ 

     // Only process this cell if this is a valid one 
     if (isValid(i, j-1) == true) 
     { 
      // If the destination cell is the same as the 
      // current successor 
      if (isDestination(i, j-1, dest) == true) 
      { 
       // Set the Parent of the destination cell 
       cellDetails[i][j-1].parent_i = i; 
       cellDetails[i][j-1].parent_j = j; 
       printf("The destination cell is found\n"); 
       tracePath(cellDetails, dest); 
       foundDest = true; 
       return; 
      } 

      // If the successor is already on the closed 
      // list or if it is blocked, then ignore it. 
      // Else do the following 
      else if (closedList[i][j-1] == false && 
        isUnBlocked(grid, i, j-1) == true) 
      { 
       gNew = cellDetails[i][j].g + 1.0; 
       hNew = calculateHValue(i, j-1, dest); 
       fNew = gNew + hNew; 

       // If it isn’t on the open list, add it to 
       // the open list. Make the current square 
       // the parent of this square. Record the 
       // f, g, and h costs of the square cell 
       //    OR 
       // If it is on the open list already, check 
       // to see if this path to that square is better, 
       // using 'f' cost as the measure. 
       if (cellDetails[i][j-1].f == FLT_MAX || 
         cellDetails[i][j-1].f > fNew) 
       { 
        openList.insert(make_pair (fNew, 
              make_pair (i, j-1))); 

        // Update the details of this cell 
        cellDetails[i][j-1].f = fNew; 
        cellDetails[i][j-1].g = gNew; 
        cellDetails[i][j-1].h = hNew; 
        cellDetails[i][j-1].parent_i = i; 
        cellDetails[i][j-1].parent_j = j; 
       } 
      } 
     } 

     //----------- 5th Successor (North-East) ------------ 

     // Only process this cell if this is a valid one 
     if (isValid(i-1, j+1) == true) 
     { 
      // If the destination cell is the same as the 
      // current successor 
      if (isDestination(i-1, j+1, dest) == true) 
      { 
       // Set the Parent of the destination cell 
       cellDetails[i-1][j+1].parent_i = i; 
       cellDetails[i-1][j+1].parent_j = j; 
       printf ("The destination cell is found\n"); 
       tracePath (cellDetails, dest); 
       foundDest = true; 
       return; 
      } 

      // If the successor is already on the closed 
      // list or if it is blocked, then ignore it. 
      // Else do the following 
      else if (closedList[i-1][j+1] == false && 
        isUnBlocked(grid, i-1, j+1) == true) 
      { 
       gNew = cellDetails[i][j].g + 1.414; 
       hNew = calculateHValue(i-1, j+1, dest); 
       fNew = gNew + hNew; 

       // If it isn’t on the open list, add it to 
       // the open list. Make the current square 
       // the parent of this square. Record the 
       // f, g, and h costs of the square cell 
       //    OR 
       // If it is on the open list already, check 
       // to see if this path to that square is better, 
       // using 'f' cost as the measure. 
       if (cellDetails[i-1][j+1].f == FLT_MAX || 
         cellDetails[i-1][j+1].f > fNew) 
       { 
        openList.insert(make_pair (fNew, 
            make_pair(i-1, j+1))); 

        // Update the details of this cell 
        cellDetails[i-1][j+1].f = fNew; 
        cellDetails[i-1][j+1].g = gNew; 
        cellDetails[i-1][j+1].h = hNew; 
        cellDetails[i-1][j+1].parent_i = i; 
        cellDetails[i-1][j+1].parent_j = j; 
       } 
      } 
     } 

     //----------- 6th Successor (North-West) ------------ 

     // Only process this cell if this is a valid one 
     if (isValid (i-1, j-1) == true) 
     { 
      // If the destination cell is the same as the 
      // current successor 
      if (isDestination (i-1, j-1, dest) == true) 
      { 
       // Set the Parent of the destination cell 
       cellDetails[i-1][j-1].parent_i = i; 
       cellDetails[i-1][j-1].parent_j = j; 
       printf ("The destination cell is found\n"); 
       tracePath (cellDetails, dest); 
       foundDest = true; 
       return; 
      } 

      // If the successor is already on the closed 
      // list or if it is blocked, then ignore it. 
      // Else do the following 
      else if (closedList[i-1][j-1] == false && 
        isUnBlocked(grid, i-1, j-1) == true) 
      { 
       gNew = cellDetails[i][j].g + 1.414; 
       hNew = calculateHValue(i-1, j-1, dest); 
       fNew = gNew + hNew; 

       // If it isn’t on the open list, add it to 
       // the open list. Make the current square 
       // the parent of this square. Record the 
       // f, g, and h costs of the square cell 
       //    OR 
       // If it is on the open list already, check 
       // to see if this path to that square is better, 
       // using 'f' cost as the measure. 
       if (cellDetails[i-1][j-1].f == FLT_MAX || 
         cellDetails[i-1][j-1].f > fNew) 
       { 
        openList.insert(make_pair (fNew, make_pair (i-1, j-1))); 
        // Update the details of this cell 
        cellDetails[i-1][j-1].f = fNew; 
        cellDetails[i-1][j-1].g = gNew; 
        cellDetails[i-1][j-1].h = hNew; 
        cellDetails[i-1][j-1].parent_i = i; 
        cellDetails[i-1][j-1].parent_j = j; 
       } 
      } 
     } 

     //----------- 7th Successor (South-East) ------------ 

     // Only process this cell if this is a valid one 
     if (isValid(i+1, j+1) == true) 
     { 
      // If the destination cell is the same as the 
      // current successor 
      if (isDestination(i+1, j+1, dest) == true) 
      { 
       // Set the Parent of the destination cell 
       cellDetails[i+1][j+1].parent_i = i; 
       cellDetails[i+1][j+1].parent_j = j; 
       printf ("The destination cell is found\n"); 
       tracePath (cellDetails, dest); 
       foundDest = true; 
       return; 
      } 

      // If the successor is already on the closed 
      // list or if it is blocked, then ignore it. 
      // Else do the following 
      else if (closedList[i+1][j+1] == false && 
        isUnBlocked(grid, i+1, j+1) == true) 
      { 
       gNew = cellDetails[i][j].g + 1.414; 
       hNew = calculateHValue(i+1, j+1, dest); 
       fNew = gNew + hNew; 

       // If it isn’t on the open list, add it to 
       // the open list. Make the current square 
       // the parent of this square. Record the 
       // f, g, and h costs of the square cell 
       //    OR 
       // If it is on the open list already, check 
       // to see if this path to that square is better, 
       // using 'f' cost as the measure. 
       if (cellDetails[i+1][j+1].f == FLT_MAX || 
         cellDetails[i+1][j+1].f > fNew) 
       { 
        openList.insert(make_pair(fNew, 
             make_pair (i+1, j+1))); 

        // Update the details of this cell 
        cellDetails[i+1][j+1].f = fNew; 
        cellDetails[i+1][j+1].g = gNew; 
        cellDetails[i+1][j+1].h = hNew; 
        cellDetails[i+1][j+1].parent_i = i; 
        cellDetails[i+1][j+1].parent_j = j; 
       } 
      } 
     } 

     //----------- 8th Successor (South-West) ------------ 

     // Only process this cell if this is a valid one 
     if (isValid (i+1, j-1) == true) 
     { 
      // If the destination cell is the same as the 
      // current successor 
      if (isDestination(i+1, j-1, dest) == true) 
      { 
       // Set the Parent of the destination cell 
       cellDetails[i+1][j-1].parent_i = i; 
       cellDetails[i+1][j-1].parent_j = j; 
       printf("The destination cell is found\n"); 
       tracePath(cellDetails, dest); 
       foundDest = true; 
       return; 
      } 

      // If the successor is already on the closed 
      // list or if it is blocked, then ignore it. 
      // Else do the following 
      else if (closedList[i+1][j-1] == false && 
        isUnBlocked(grid, i+1, j-1) == true) 
      { 
       gNew = cellDetails[i][j].g + 1.414; 
       hNew = calculateHValue(i+1, j-1, dest); 
       fNew = gNew + hNew; 

       // If it isn’t on the open list, add it to 
       // the open list. Make the current square 
       // the parent of this square. Record the 
       // f, g, and h costs of the square cell 
       //    OR 
       // If it is on the open list already, check 
       // to see if this path to that square is better, 
       // using 'f' cost as the measure. 
       if (cellDetails[i+1][j-1].f == FLT_MAX || 
         cellDetails[i+1][j-1].f > fNew) 
       { 
        openList.insert(make_pair(fNew, 
             make_pair(i+1, j-1))); 

        // Update the details of this cell 
        cellDetails[i+1][j-1].f = fNew; 
        cellDetails[i+1][j-1].g = gNew; 
        cellDetails[i+1][j-1].h = hNew; 
        cellDetails[i+1][j-1].parent_i = i; 
        cellDetails[i+1][j-1].parent_j = j; 
       } 
      } 
     } 
    } 

    // When the destination cell is not found and the open 
    // list is empty, then we conclude that we failed to 
    // reach the destiantion cell. This may happen when the 
    // there is no way to destination cell (due to blockages) 
    if (foundDest == false) 
     printf("Failed to find the Destination Cell\n"); 

    return; 
} 


// Driver program to test above function 
int main() 
{ 
    /* Description of the Grid- 
    1--> The cell is not blocked 
    0--> The cell is blocked */ 
    int grid[ROW][COL] = 
    { 
     { 1, 0, 1, 1, 1, 1, 0, 1, 1, 1 }, 
     { 1, 1, 1, 0, 1, 1, 1, 0, 1, 1 }, 
     { 1, 1, 1, 0, 1, 1, 0, 1, 0, 1 }, 
     { 0, 0, 1, 0, 1, 0, 0, 0, 0, 1 }, 
     { 1, 1, 1, 0, 1, 1, 1, 0, 1, 0 }, 
     { 1, 0, 1, 1, 1, 1, 0, 1, 0, 0 }, 
     { 1, 0, 0, 0, 0, 1, 0, 0, 0, 1 }, 
     { 1, 0, 1, 1, 1, 1, 0, 1, 1, 1 }, 
     { 1, 1, 1, 0, 0, 0, 1, 0, 0, 1 } 
    }; 

    // Source is the left-most bottom-most corner 
    Pair src = make_pair(8, 0); 

    // Destination is the left-most top-most corner 
    Pair dest = make_pair(0, 0); 

    aStarSearch(grid, src, dest); 

    return(0); 
} 

你可以嘗試爲9行取得A *算法中 和10周的cols 更新按照您的要求