Timus 1501

搞了一天终于AC了,感觉题目有点问题,没有说有多个可行顺序的情况如何输出,然而测试数据是按照某一个顺序输出的。

比如说:101  010   是按照111222输出,其实(如果题意我没有读错的话)121212   221112应该也是正确的。听说这道题有一定的改动,是不是出题人忽视了呢????

令res[i][j]表示串1的前i个字符与串2的前j个字符是否能够按照规则分成两堆。

res[i][j]= (res[i-1][j-1] && str1[i]!=str2[j]) || (res[i-2][j] && str1[i]!=str1[i-1]) || (res[i][j-2] && str2[j]!=str2[j-1]);

#include<iostream>

#include<cstdio>

#include<cstring>

#include<stack>

using namespace std;

char str1[1010],str2[1010];

short res[1010][1010];

int work(int n)

{

    int i,j;

    res[0][0]=1;

    for(i=2;i<=n;i+=2)

        if(res[0][i-2] && str2[i-1]!=str2[i]) res[0][i]=1;

    for(i=2;i<=n;i+=2)

        if(res[i-2][0] && str1[i-1]!=str1[i]) res[i][0]=1;

    for(i=1;i<=n;i++)

        for(j=1;j<=n;j++)

        {

            if((i+j)%2==1) continue;

            if(str1[i]!=str2[j] && res[i-1][j-1]) res[i][j]=1;

            if(str1[i]!=str1[i-1] && res[i-2][j]) res[i][j]=1;

            if(str2[j]!=str2[j-1] && res[i][j-2]) res[i][j]=1;

        }

    return res[n][n];

}

int print(int n)

{

    int i,j;

    stack <int> S;

    i=j=n;

    while(i>0 || j>0)

    {

        if(res[i][j-2])

        {

            S.push(2); S.push(2);j-=2;

        }

        else if(res[i-1][j-1])

        {

            S.push(2); S.push(1); i--;j--;

        }

        else if(res[i-2][j])

        {

            S.push(1); S.push(1);i-=2;

        }

    }

    while(!S.empty())

    {

        printf("%d",S.top()); S.pop();

    }

    printf("\n");

    return 0;

}

int main()

{

    int n;

    while(scanf("%d",&n)!=EOF)

    {

        memset(res,0,sizeof(res));

        scanf("%s %s",str1+1,str2+1);

        str1[0]=str1[1]; 

        str2[0]=str2[1];

        if(work(n))

        {

            print(n);

        }

        else

        {

            printf("Impossible\n");

        }

    }

    return 0;

}

你可能感兴趣的:(IM)