题目链接:
题意:
给出一张只有黑色和白色的图,每次可以改变一个联通块的所有颜色,求整张图颜色一样时的最少步骤。
题解:
将每个联通块缩点,然后对于每个点进行搜索,寻找到达最远点的距离,然后所有距离的最小值就是答案,可以用前向星算法存边。
AC代码
#include <iostream>
#include <algorithm>
#include <cstdio>
#include <cstring>
#include <queue>
#define INF 1e6
using namespace std;
const int maxn = 50;
int n,m;
char mapp[maxn][maxn];
int col[maxn][maxn];
int figuer[2000][2000];
int mov[4][2] = {0,1,0,-1,1,0,-1,0};
struct node{int x,y;};
struct edge{int to,next;}e[100000];
int head[2000];
int d[2000];
int tot;
void add(int u,int v)
{
e[++tot].to = v;
e[tot].next = head[u];
head[u] = tot;
}
void dfs(int x, int y, char color, int paint)
{
col[x][y] = paint;
for(int i = 0 ; i < 4; i++)
{
node a;
a.x = x + mov[i][0],a.y = y + mov[i][1];
if(a.x > 0 && a.x <= n && a.y > 0 && a.y <= m )
{
int v = col[a.x][a.y];
if(mapp[a.x-1][a.y-1] != color && v && !figuer[paint][v])
{
figuer[paint][v] = 1;
figuer[v][paint] = 1;
//cout << paint << " " << v <<endl;
add(paint,v);
add(v,paint);
}
else if(mapp[a.x-1][a.y-1] == color && !v)
{
col[a.x][a.y] = paint;
dfs(a.x,a.y,color,paint);
}
}
}
}
int bfs(int k){
int re = 0;
queue<int>q;
int x, y;
memset(d, 0, sizeof d);
q.push(k);
d[k] = 1;
while(!q.empty()){
x = q.front(); q.pop();
for(int i = head[x]; i; i = e[i].next){
y = e[i].to;
if (d[y]) continue;
q.push(y);
d[y] = d[x]+1;
//cout << d[y] <<endl;
re = max(re, d[y] - 1);
}
}
//cout << "re " <<re <<endl;
return re;
}
int main()
{
int t;
scanf("%d",&t);
while(t--)
{
scanf("%d%d",&n,&m);
memset(col,0,sizeof(col));
memset(head,0,sizeof(head));
memset(figuer,0,sizeof(figuer));
tot = 0;
for(int i = 0;i<n; i++)
{
scanf("%s",mapp[i]);
}
int colNumber = 1;
for(int i = 1; i <= n; i++)
{
for(int j = 1; j <= m; j++)
{
if(col[i][j]==0)
{
dfs(i,j,mapp[i-1][j-1],colNumber);
colNumber ++;
//cout << colNumber << endl;
}
}
}
/*for(int i = 1; i <= colNumber; i++)
{
for(int j = 1; j <= colNumber; j++)
cout << col[i][j] << " ";
cout << endl;
}*/
int ans = INF;
for(int i = 1; i <= colNumber-1; i++)
{
ans = min(ans,bfs(i));
}
printf("%d\n",ans);
}
return 0;
}
/*
2
2 2
OX
OX
3 3
XOX
OXO
XOX
*/