Codeforces 1130C

求从(r1,c2)到(r2,c2) 的最小花费,连通的0可以任意走,否则要搭桥,搭桥的费用是两点的欧几里得距离,bfs两次,分别把和(r1,c1)、(r2,c2)相连的0打上标记,n<=50,因此可以n^4枚举。

#include<bits/stdc++.h>
using namespace std;
#define forn(i,n) for(int i = 0;i<int(n);i++)
typedef long long LL;
int n,r1,c1,r2,c2;
char a[55][55];
int dx[] ={0,0,1,-1},dy[] = {1,-1,0,0},vis1[55][55],vis2[55][55],ans = 1e9;
typedef pair<int,int> P;
queue<P> q;
int dou(int x){
	return x*x;
}
int bfs(int x,int y,int o){
	while(!q.empty()) q.pop();
	q.push({x,y});
	if(o == 1) vis1[x][y] = 1;
	else vis2[x][y] = 1; 
	while(!q.empty()){
		P u = q.front();q.pop();
		int nowx= u.first,nowy = u.second;
		for(int i = 0;i<4;i++){
			int nx = nowx + dx[i],ny = nowy+dy[i];
			if(nx>=1&&nx<=n&&ny>=1&&ny<=n&&a[nx][ny] == '0'&&
			((o==1&&!vis1[nx][ny])||(o==2&&!vis2[nx][ny]))){ 
				if(o == 1)vis1[nx][ny] = 1;
				else vis2[nx][ny] = 1;
				q.push({nx,ny}); 
			}
		}
	}
	return 0;
}
int main(){
	ios::sync_with_stdio(false);
	cin.tie(0);cout.tie(0);
	//freopen("data.in","r",stdin);
	//freopen("data.out","w",stdout);
	cin>>n;
	cin>>r1>>c1>>r2>>c2;
	for(int i = 1;i<=n;i++) cin>>a[i]+1;
	bfs(r1,c1,1);
	bfs(r2,c2,2);
	for(int i = 1;i<=n;i++)
		for(int j = 1;j<=n;j++)
			if(vis1[i][j])
				for(int k = 1;k<=n;k++)
					for(int l = 1;l<=n;l++)
						if(vis2[k][l])
							ans = min(ans,dou(i-k)+dou(j-l));
	cout<<ans;
	return 0; 
} 

猜你喜欢

转载自blog.csdn.net/winhcc/article/details/88749622
今日推荐