hdu 5745 La Vie en rose(2016 Multi-University Training Contest 2——暴力)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5745

La Vie en rose

Time Limit: 14000/7000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)
Total Submission(s): 949    Accepted Submission(s): 516


Problem Description
Professor Zhang would like to solve the multiple pattern matching problem, but he only has only one pattern string  p=p1p2...pm . So, he wants to generate as many as possible pattern strings from  p  using the following method:

1. select some indices  i1,i2,...,ik  such that  1i1<i2<...<ik<|p|  and  |ijij+1|>1  for all  1j<k .
2. swap  pij  and  pij+1  for all  1jk .

Now, for a given a string  s=s1s2...sn , Professor Zhang wants to find all occurrences of all the generated patterns in  s .
 

Input
There are multiple test cases. The first line of input contains an integer  T , indicating the number of test cases. For each test case:

The first line contains two integers  n  and  m   (1n105,1mmin{5000,n})  -- the length of  s  and  p .

The second line contains the string  s  and the third line contains the string  p . Both the strings consist of only lowercase English letters.
 

Output
For each test case, output a binary string of length  n . The  i -th character is "1" if and only if the substring  sisi+1...si+m1  is one of the generated patterns.
 

Sample Input
  
  
3 4 1 abac a 4 2 aaaa aa 9 3 abcbacacb abc
 

Sample Output
  
  
1010 1110 100100100
 

Author
zimpha
 

Source

 
题目大意:给你一个长为 n 的串 A 和一个长为 m 的串 B ,然后从头开始匹配,如果可以匹配,则当前输出1,如果不能输出0,可以在 B 串中选取一些下标 ij ,其中|ijij+1|>1,每次可以选择 Pij Pij+1 交换。

解题思路:

我们采用pre的方法进行标记前一状态。分为以下三种:

1、pre=0;表示和当前位置正好匹配成功

2、pre=1;表示和后一位匹配成功

3、pre=-1;表示和前一位匹配成功

根据pre的状态就可以知道是否两个字符串可以匹配成功。

因为第一位只可能是和当前位匹配或者和后一位匹配,最后一位就只能是当前位和前一位是否匹配。

而加在两位中间的就是以上三种情况。

通过这样一位一位的查找,如果能够成功,循环就会结束、j>=m,就输出1,否则,输出0;


详见代码。

#include <iostream>
#include <cstdio>

using namespace std;

char ch1[100010],ch2[5010];

int main()
{
    int t,pre;
    scanf("%d",&t);
    while (t--)
    {
        int n,m;
        scanf("%d%d",&n,&m);
        scanf("%s%s",ch1,ch2);
        for (int i=0; i<n; i++)//ch1的起点
        {
            if (ch1[i]==ch2[0])
                pre=0;
            else if (ch1[i]==ch2[1])
                pre=1;
            else
            {
                //cout<<1<<endl;
                printf ("0");
                continue;
            }
            int k=i+1,j;
            for (j=1; j<m; j++,k++)//ch2
            {
                if (pre==0||pre==-1)
                {
                    if (ch1[k]==ch2[j])
                    {
                        pre=0;
                    }
                    else if (j<m-1&&ch1[k]==ch2[j+1])
                    {
                        pre=1;
                    }
                    else
                        break;
                }
                else if (pre==1)
                {
                    if (ch1[k]==ch2[j-1])
                        pre=-1;
                    else
                        break;
                }
            }
            if (j>=m)
                printf ("1");
            else
                printf ("0");
        }
        printf("\n");
    }
    return 0;
}



| ij ij+1 | > 1
| ij ij+1 | > 1
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值