//用队列进行广度优先搜索
#include<iostream>
#include<queue>
#include<fstream>
using namespace std;
//import the grid data;
ifstream fin("map.txt");//这个map是7行7列,请以这个为例子来理解这个程序
typedef struct Position
{
int row;
int col;
} Posi;
//find the shortest path for the grid
bool FindPath(Posi start,Posi finish,int & PathLen,int **&grid,Posi *& path,int n,int m)
{
//if the start position is the finish position
if((start.row == finish.row) && (start.col == finish.col))
{
PathLen = 0;
return true;
}
Position offset[4];
offset[0].row = -1;//up
offset[0].col = 0;
offset[1].row = 1;//down
offset[1].col = 0;
offset[2].row = 0;//left
offset[2].col = -1;
offset[3].row = 0;//right
offset[3].col = 1;
Posi here,nbr;
here.row = start.row;
here.col = start.col;
int NumOfNbrs = 4;//ajacent position;
grid[start.row][start.col] = 2;//init the start position's length with value 2,
queue<Posi> Q;
do
{
for(int firdex = 0;firdex < NumOfNbrs;firdex++)
{
nbr.row = here.row + offset[firdex].row;
nbr.col = here.col + offset[firdex].col;
if(grid[nbr.row][nbr.col] == 0)//this position haven't been visted
{
grid[nbr.row][nbr.col] = grid[here.row][here.col] + 1;
if((nbr.row == finish.row) && (nbr.col == finish.col))//find the shortest path
{
break;
}
Q.push(nbr);
}
}
if((nbr.row == finish.row) && (nbr.col ==finish.col))
{
break;//wiring was completed
}
if(Q.empty())//if queue is empty
{
return false;//no result
}
here = Q.front();
Q.pop();
}while(true);
//traceback the shortest path
PathLen = grid[finish.row][finish.col]-2;
path = new Posi[PathLen];
here = finish;
for(int firdex = PathLen-1;firdex >=0;firdex--)
{
path[firdex] = here;
for(int secdex = 0;secdex < NumOfNbrs;secdex++)
{
nbr.row = here.row + offset[secdex].row;
nbr.col = here.col + offset[secdex].col;
if(grid[nbr.row][nbr.col] == firdex+2)//It is the nbr's grid that why the grid[nbr.row][nbr.col] can give index of "firdex+2"
{
break;
}
}
here =nbr;//move to the previous node
}
return true;
}
//allocate memory for the grid
void InitGrid(int **&grid,int n,int m)
{
grid = new int*[n+2];
for(int firdex = 0;firdex < n+2;firdex++)
grid[firdex] = new int[m+2];
//set the bound
for(int index = 0;index < m+2;index++)//top an bottom
{
grid[0][index] = grid[n+1][index] =1;
}
for(int index = 0;index < n+2;index++)
{
grid[index][0] = grid[index][m+1] = 1;
}
for(int firdex = 1;firdex < n+1;firdex++)
{
for(int secdex = 1;secdex < m+1;secdex++)
fin>>grid[firdex][secdex];
}
}
//destroy the resource for the grid
void Destroy(int ** &grid,int n,int m)
{
if(grid != NULL)
{
for(int firdex = 0;firdex < n+2;firdex++)
{
delete [] grid[firdex];
grid[firdex] = NULL;
}
delete grid;
grid = NULL;
}
}
int main(void)
{
int m = 0,n = 0;
Posi start,finish;
int PathLength = 0;
Posi * path = NULL;
int ** grid = NULL;
cout<<"Please input the m and n of the grid:"<<endl;
cin>>n>>m;
cout<<"Please input the start position:"<<endl;
cout<<"start:row =";
cin>>start.row;
cout<<"start:col =";
cin>>start.col;
cout<<"Please input the finish position:"<<endl;
cout<<"finish:row =";
cin>>finish.row;
cout<<"finish:col =";
cin>>finish.col;
InitGrid(grid,n,m);
cout<<"the map resource:"<<endl;
for(int firdex = 1;firdex < n+1;firdex++)
{
for(int secdex = 1;secdex < m+1;secdex++)
cout<<grid[firdex][secdex]<<" ";
cout<<endl;
}
cout<<endl;
FindPath(start,finish,PathLength,grid,path,n,m);
cout<<"The shortest path of wiring is :"<<PathLength<<endl;
cout<<"The path if follow:"<<endl;
for(int index = 0;index < PathLength;index++)
{
cout<<"("<<path[index].row<<","<<path[index].col<<")";
if(index < PathLength-1)
cout<<"-->";
}
cout<<endl;
//Destory the resource of grid
Destroy(grid,n,m);
//release the path's resource
if(path != NULL)
{
delete [] path;
path = NULL;
}
return 0;
}