30 60
first last
首先我们认为结果在这个范围之内,利用mid去测试
如果mid可以,在30,mid之间
否则 在mid+1,60之间
当first=last的时候,到最底层。
#include<stdio.h>
#include<iostream>
#include<string.h>
using namespace std;
int N;
#define MAX 120
int map[MAX][MAX];
int dir[4][2]={{1,0},{0,1},{-1,0},{0,-1}};
int flag[MAX][MAX];
int bfs(int row,int col,int low,int high)
{
//如果越界
if(row<0||col<0||row>=N||col>=N)
{
return 0;
}
//如果不和条件
if(map[row][col]<low||map[row][col]>high)
{
return 0;
}
//如果这个地方访问过,貌似是为了不走回头路
if(flag[row][col])
{
return 0;
}
if(row==N-1&&col==N-1)
{
return 1;
}
flag[row][col]=1;
int temprow;int tempcol;int i=0;
for(i=0;i<4;i++)
{
temprow=row+dir[i][0];tempcol=col+dir[i][1];
//如果有一条路可以到最后
if(bfs(temprow,tempcol,low,high))
{
return 1;
}
}
return 0;
}
int slove(int mid)
{
int i=0;
for(i=0;i+mid<=120;i++)
{
memset(flag,0,sizeof(flag));
if(bfs(0,0,i,i+mid))
{
return 1;
}
}
return 0;
}
int main()
{
//freopen("in.txt","r",stdin);
while(scanf("%d",&N)!=EOF)
{
int i=0;int j=0;
//输入
for(i=0;i<N;i++)
{
for(j=0;j<N;j++)
{
scanf("%d",&map[i][j]);
}
}
int first,last,mid;
first=map[0][0]-map[N-1][N-1];
if(first<0)
first=-first;
last=120;
while(first<last)
{
mid=(first+last)/2;
if(slove(mid))
last=mid;
else
first=mid+1;
}
cout<<first<<endl;
}
return 0;
}