luogu1451 求细胞数量

这道题有挺多注意的点的,主要是新手还是要学习一个‘

 

这是每次新开始的循环,第几次找,答案ans就是几,if语句满足判断才进行下一步

    for(int i=0;i<m;i++)//m=4
        for(int j=0;j<n;j++)//n=10
        {
            if(a[i][j])
            {
                ans++;
                dfs(i,j);
            }
        }

dfs,有三个关键之处

void dfs(int x,int y)
{
    if(x<0||y<0||x>m||y>n) return;
    a[x][y]=0;
    for(int i=0;i<4;i++)
    {
        if (a[x+dx[i]][y+dy[i]])
            dfs(x+dx[i],y+dy[i]);//如果有才搜
    }
 } 

1.

递归转移

        if (a[x+dx[i]][y+dy[i]])
            dfs(x+dx[i],y+dy[i]);//如果有才搜

要注意,在这一步,由于有4种(多种)可能,所以不能够改变x,y原有的数值

不能写成

        x=+dx[i];
        y=+dy[i];
        if (a[x][y])
            dfs(x,y);

这样比如,i=0的时候是一样的,

可是如果再下一次,即i=1的时候,则是在i=0改变后的x,y再改变,

而不是从原有的x,y转移而来

2,

在界内再搜索,只要满足界内就可以

if(x<0||y<0||x>m||y>n) return;

3.

改变点的状态

要把这个点清零

        a[x][y]=0;    

其实在实际操作是213的顺序,可以说是途径型的典型

 

在输入时有使用的技巧,确保每次输入一个

    scanf("%1d",&a[i][j]);    

 

#include<bits/stdc++.h>
using namespace std;

int dx[4]={0,1,-1,0};
int dy[4]={1,0,0,-1};
int n,m;
int ans;
int a[110][110];

void dfs(int x,int y)
{
    if(x<0||y<0||x>m||y>n) return;
    a[x][y]=0;
    for(int i=0;i<4;i++)
    {
        if (a[x+dx[i]][y+dy[i]])
            dfs(x+dx[i],y+dy[i]);//如果有才搜
    }
 } 

int main()
{
    cin>>m>>n;
    for(int i=0;i<m;i++)//m=4
        for(int j=0;j<n;j++)//n=10
            {
                scanf("%1d",&a[i][j]);
            }
    for(int i=0;i<m;i++)//m=4
        for(int j=0;j<n;j++)//n=10
        {
            if(a[i][j])
            {
                ans++;
                dfs(i,j);
            }
        }
    cout<<ans;
    return 0;
}

 

posted on 2020-03-08 20:42  lyyyt  阅读(125)  评论(0编辑  收藏  举报