Face questions
Title Description
There is only a digital \ (0 \) and \ (1 \) consisting of \ (n \ times n \) grid maze. If you are located on a lattice 0, then you can move to an adjacent \ (4 \) cells in a cell \ (1 \) , the same if you are in a grid 1, then you can move to an adjacent \ (4 \) a lattice grid the \ (0 \) on.
Your task is: for a given maze inquiry can begin to move from one cell to the number of grid (including its own).
Input and output formats
Input Format
The first \ (1 \) behavior of two positive integers \ (n-, m \) .
Here \ (n-\) rows, each row \ (n-\) characters, characters can only be \ (0 \) or \ (1 \) with no spaces between characters.
Next, \ (\ m) rows, each row \ (2 \) , separated by a space positive integer \ (I, J \) , corresponding to the first maze \ (I \) row \ (J \) column a grid, able to move from start to ask how much this grid cell.
Output Format
\ (m \) line, the output for each query corresponding answers.
Sample input and output
Input # 1:
2 2
01
10
1 1
2 2
Output # 1:
4
4
Description / Tips
For the sample, all the grid up to each other.
For \ (20 \% \) data, \ (n-\ Le 10 \) ;
For \ (40 \% \) data, \ (n-\ Le 50 \) ;
For \ (50 \% \) data, \ (m \ Le. 5 \) ;
For \ (60 \% \) data, \ (n-\ Le 100, m \ Le 100 \) ;
For \ (100 \% \) data, \ (n-\ 1000 Le, m \ 100000 Le \) .
analysis
This question appears to be a very simple search, but look at this question of the scope of data, we can see that this question is actually bloodshed. And recent search of water Niwai, looking at this question, I suddenly idea came: Can a disjoint-set to do it?
It may, it is clear that we might block communication, then we can construct maps. One-dimensional two-dimensional map to believe we are already well placed to exploit directly (i,j)
mapped to i*n+j
, simple and crude.
And check on the details of the set I'm not saying too much, I just want to say, disjoint-set really is the most beautiful of the data structure in the world.
At that time I used an ordinary two-dimensional array dfs
run disjoint-set, but the result MLE
of the 3
points made 70
pointsGood results.
As MLE
we can scroll across the map into an array, with disjoint-set, it is the simple things.
See in particular the code.
Code
Give dfs
versions, note that this version I got 70
points,Do not take a direct copyThen I have to pay attention to the spatial complexity, this is a lesson ah.
/*
* @Author: crab-in-the-northeast
* @Date: 2020-02-19 23:01:54
* @Last Modified by: crab-in-the-northeast
* @Last Modified time: 2020-02-19 23:41:37
*/
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
const int maxn = 1005;
const int maxn2 = 1000005;
int n;
int fa[maxn2],u[maxn2];
bool a[maxn][maxn];
int dx[4] = {1,-1,0,0};
int dy[4] = {0,0,1,-1};
int find(int x){//查
return fa[x] == x?x:fa[x] = find(fa[x]);
}
void merge(int a,int b){//并
int fa1 = find(a), fa2 = find(b);
if(fa1 != fa2){
u[fa1] += u[fa2];
fa[fa2] = fa[fa1];
}
}
// 以上都是并查集的板子,这里不再多说。
bool valid(int x,int y){
return x>0&&x<=n&&y>0&&y<=n;
}//边界判断。
int dfs(int x,int y){
int ind = x*n+y;//映射处理
if(fa[ind] != -1) return find(ind);//记忆化
fa[ind] = ind;
u[ind] = 1;
//初始化
for(int i=0;i<4;i++){
int nxtx = x+dx[i], nxty = y+dy[i];//枚举下一种情况的x坐标和y坐标。
if(valid(nxtx,nxty) && a[x][y]!=a[nxtx][nxty])//合法。
merge(ind,dfs(nxtx,nxty));//并。
}
return find(ind);//回溯
}
int main(){
int T;
scanf("%d%d",&n,&T);
memset(fa,-1,sizeof(fa));
for(int i = 1; i <= n ;i++)
for(int j = 1; j <= n; j++)
scanf("%1d",&a[i][j]);
while(T--){
int x,y;
scanf("%d%d",&x,&y);
printf("%d\n",u[dfs(x,y)]);
}
return 0;
}
Out of AC
the code (a rolling arrays)
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
const int maxn = 1005;
const int maxn2 = 1000005;
int n;
int fa[maxn2],u[maxn2];
char a[2][maxn];
int find(int x){
return fa[x] == x?x:fa[x] = find(fa[x]);
}
void merge(int a,int b){
int fa1 = find(a), fa2 = find(b);
if(fa1 != fa2){
u[fa1] += u[fa2];
fa[fa2] = fa[fa1];
}
}
int main(){
int T;
scanf("%d%d",&n,&T);
memset(fa,-1,sizeof(fa));
for(int i = 0; i < n; i++){
scanf("%s",a[i&1]);//读入
for(int j = 0; j < n; j++){
int ind = i*n+j;//映射
fa[ind] = ind;
u[ind] = 1;
if(i && a[(i-1)&1][j] !=a[i&1][j]) merge(ind-n,ind);//横向并
if(j && a[i&1][j-1] != a[i&1][j]) merge(ind,ind-1);//纵向并
}
}
while(T--){
int x,y;
scanf("%d%d",&x,&y);
printf("%d\n",u[find(x*n-n+y-1)]);
//这里蟹蟹懒。这里的原型应该是(x-1)*n+y-1,就是用了个乘法分配。
}
return 0;
}
Evaluation results
MLE 70
: R30836609
AC 100
: R30837084
over.