LCP Array

LCP Array

 
 Accepts: 131
 
 Submissions: 1352
 Time Limit: 4000/2000 MS (Java/Others)
 
 Memory Limit: 131072/131072 K (Java/Others)
问题描述
Peter有一个字符串s=s_{1}s_{2}...s_{n}s=s1s2...sn, 令\text{suff}_i =s_{i}s_{i+1}...s_{n}suffi=sisi+1...snssii字符开头的后缀. Peter知道任意两个相邻的后缀的最长公共前缀a_i = \text{lcp}(\text{suff}_i, \text{suff}_{i+1}) \quad (1 \le i < nai=lcp(suffi,suffi+1)(1i<n).

现在给你数组aa, Peter有多少个仅包含小写字母的字符串满足这个数组. 答案也许会很大, 你只要输出对10^9 + 7109+7取模的结果即可.
输入描述
输入包含多组数据. 第一行有一个整数TT, 表示测试数据的组数. 对于每组数据:

第一行包含一个整数nn (2 \le n \le 10^5)2n105)表示字符串的长度. 第二行包含n - 1n1个整数: a_1,a_2,...,a_{n-1}a1,a2,...,an1 (0 \le a_i \le n)(0ain).

所有数据中nn的和不超过10^6106.
输出描述
对于每组数据, 输出答案对10^9+7109+7取模的结果.
输入样例
3
3
0 0
4
3 2 1
3
1 2
输出样例
16250
26
0

这道题的题意不是特别好理解,其实就是说有一个长字符串,然后告诉你每两个相邻字母开始的字符串,从第一个开始连续的有多少个字符是相同的,输入的数肯定不能大于从其开始的字符串的总长度,然后很必要的输入的数必定是严格递减的,一个一个的递减,最后算出这个字符串有多少种可能性。

#include 
#include
#include
#include

using namespace std;
#define mm 1000000007
int main()
{
    int t,n;
    scanf("%d",&t);
    while(t--)
    {
        long long int ans=26;
        int x[100010];
        memset(x,0,sizeof(x));
        scanf("%d",&n);
        for(int i=1;i0;i--)
        {
            if(x[i]+1!=x[i-1]&&x[i-1])
            {
                ans=0;
                break;
            }
            if(x[i]+i>n)
            {
                ans=0;
                break;
            }
            if(!x[i])
                ans*=25,ans%=mm;
        }
        printf("%I64d\n",ans%mm);

    }
    return 0;
}


你可能感兴趣的:(其他)