HDU 1495非常可乐(BFS)

题目地址:http://acm.hdu.edu.cn/showproblem.php?pid=1495

话说从这个题中我发现了一个惊天的秘密!我以前写的BFS好多都写多余了!!sad。。

因为这题需要标记数组,我以前一直都是传递数组,但这道题的标记数组需要10^6的数组大小,光传递的时候就需要10^6的复杂度。。于是想了好长时间怎样把标记数组写的小一点,因为和是一定的,所以可以把因数变小。开始想到s*4+n*2+m的结果标记,结果提交WA,然后发现(1,0,2)与(0,3,0)是一样的。。。然后又改成s*3+n*2+m,虽然没想出反例,但还是WA。。然后无奈找了找题解(再次表示罪过罪过。。),发现不用传递。。我仔细想了想。。的确不用传递。。。。。。而且不传递还能节省好大一部分无用的时间。。sad。。以前的有好多BFS的题都写挫了。。

这题很有收获。。发现的这个问题很严重啊。。

#include <iostream>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <math.h>
#include <ctype.h>
#include <queue>
#include <map>
#include<algorithm>

using namespace std;
int s, n, m, vis[101][101][101];
struct node
{
    int a, b, c, ans;
};
void bfs()
{
    int i, j, x;
    queue<node>q;
    node f1, f2;
    memset(vis,0,sizeof(vis));
    f1.a=s;
    f1.b=0;
    f1.c=0;
    f1.ans=0;
    q.push(f1);
    vis[s][0][0]=1;
    while(!q.empty())
    {
        f1=q.front();
        //printf("%d %d %d %d\n",f1.a,f1.b,f1.c,f1.ans);
        q.pop();
        if((f1.a==s/2)+(f1.b==s/2)+(f1.c==s/2)==2)
        {
            printf("%d\n",f1.ans);
            return ;
        }
        if(f1.b<n)
        {
            x=f1.a+f1.b;
            if(x>=n)
            {
                f2.b=n;
                f2.a=x-n;
            }
            else
            {
                f2.b=x;
                f2.a=0;
            }
            f2.c=f1.c;
            f2.ans=f1.ans+1;
            if(!vis[f2.a][f2.b][f2.c])
            {
                vis[f2.a][f2.b][f2.c]=1;
                q.push(f2);
            }
            f2.a=f1.a;
            x=f1.c+f1.b;
            if(x>=n)
            {
                f2.b=n;
                f2.c=x-n;
            }
            else
            {
                f2.b=x;
                f2.c=0;
            }
            if(!vis[f2.a][f2.b][f2.c])
            {
                vis[f2.a][f2.b][f2.c]=1;
                q.push(f2);
            }
        }
        if(f1.a<s)
        {
            x=f1.a+f1.b;
            if(x>=s)
            {
                f2.a=s;
                f2.b=x-s;
            }
            else
            {
                f2.a=x;
                f2.b=0;
            }
            f2.c=f1.c;
            f2.ans=f1.ans+1;
            if(!vis[f2.a][f2.b][f2.c])
            {
                vis[f2.a][f2.b][f2.c]=1;
                q.push(f2);
            }
            x=f1.a+f1.c;
            if(x>=s)
            {
                f2.a=s;
                f2.c=x-s;
            }
            else
            {
                f2.a=x;
                f2.c=0;
            }
            f2.b=f1.b;
            if(!vis[f2.a][f2.b][f2.c])
            {
                vis[f2.a][f2.b][f2.c]=1;
                q.push(f2);
            }
        }
        if(f1.c<m)
        {
            x=f1.c+f1.b;
            if(x>=m)
            {
                f2.c=m;
                f2.b=x-m;
            }
            else
            {
                f2.c=x;
                f2.b=0;
            }
            f2.a=f1.a;
            f2.ans=f1.ans+1;
            if(!vis[f2.a][f2.b][f2.c])
            {
                vis[f2.a][f2.b][f2.c]=1;
                q.push(f2);
            }
            x=f1.a+f1.c;
            if(x>=m)
            {
                f2.c=m;
                f2.a=x-m;
            }
            else
            {
                f2.c=x;
                f2.a=0;
            }
            f2.b=f1.b;
            if(!vis[f2.a][f2.b][f2.c])
            {
                vis[f2.a][f2.b][f2.c]=1;
                q.push(f2);
            }
        }
    }
    printf("NO\n");
}
int main()
{
    while(scanf("%d%d%d",&s,&n,&m)!=EOF&&s&&n&&m)
    {
        if(s%2)
            printf("NO\n");
        else
            bfs();
    }
    return 0;
}


你可能感兴趣的:(编程,算法,C语言,bfs)