zoukankan      html  css  js  c++  java
  • 子串

    题目描述

    有两个仅包含小写英文字母的字符串 AA 和 BB。

    现在要从字符串 AA 中取出 kk 个互不重叠的非空子串,然后把这 kk 个子串按照其在字符串 AA 中出现的顺序依次连接起来得到一个新的字符串。请问有多少种方案可以使得这个新串与字符串 BB 相等?

    注意:子串取出的位置不同也认为是不同的方案。

    输入输出格式

    输入格式:

    第一行是三个正整数 n,m,kn,m,k,分别表示字符串 AA 的长度,字符串 BB 的长度,以及问题描述中所提到的 kk,每两个整数之间用一个空格隔开。

    第二行包含一个长度为 nn 的字符串,表示字符串 AA。

    第三行包含一个长度为 mm 的字符串,表示字符串 BB。

    输出格式:

    一个整数,表示所求方案数。

    由于答案可能很大,所以这里要求输出答案对 10000000071000000007 取模的结果。

    【题解】

    有空补上,先上代码

    #include<iostream>
    #include<cstring>
    #include<cstdio>
    #include<cmath>
    #include<algorithm>
    #define ll long long
    #define mod 1000000007
    #define num ch-'0'
    using namespace std;
    int n,m,k;
    ll f[201][201],sum[201][201];
    char s1[10050],s2[10050];
    void print(int x)
    {
        if(x<0){putchar('-');x=-x;}
        if(x>9) print(x/10);
        putchar(x%10+'0');
    }
    void get(int &res)
    {
        char ch;bool flag=0;
        while(!isdigit(ch=getchar()))
            (ch=='-')&&(flag=true);
        for(res=num;isdigit(ch=getchar());res=res*10+num);
        (flag)&&(res=-res);
    }
    int main()
    {
        get(n),get(m),get(k);
        scanf("%s%s",s1,s2);
        f[0][0]=1;
        for(int i=1;i<=n;i++)
          for(int j=m;j>=1;j--)
            for(int w=k;w>=1;w--)
            {
                if(s1[i-1]==s2[j-1])
                {
                    sum[j][w]=(sum[j-1][w]+f[j-1][w-1])%mod;
                    f[j][w]=(f[j][w]+sum[j][w])%mod;
                }
                else sum[j][w]=0;
            }
        print(f[m][k]);
        return 0;
    }
  • 相关阅读:
    P1829 [国家集训队]Crash的数字表格 / JZPTAB 莫比乌斯反演
    Luogu P1447 [NOI2010]能量采集 数论??欧拉
    Luogu P2522 [HAOI2011]Problem b 莫比乌斯反演
    Luogu P2257 YY的GCD 莫比乌斯反演
    [笔记] 数论函数小记
    [笔记] 线性筛小记
    Luogu P1092 虫食算 爆搜
    Luogu P1066 2^k进制数 组合数学
    Luogu P1641 [SCOI2010]生成字符串 组合数学
    Luogu P2532 [AHOI2012]树屋阶梯 卡特兰数
  • 原文地址:https://www.cnblogs.com/mxrmxr/p/9715190.html
Copyright © 2011-2022 走看看