前言:
只会两题了,再见
A:
题目描述:
给出一个字符串,求本质不同的子序列个数。
题目分析:
对于一个字母可选可不选 所以答案就是
每个字母出现次数+1的乘积
代码:
#include <cstdio>
#include <iostream>
#include <cstring>
#include <cstring>
#define ll long long
const int MOD=1e9+7;
int n,num[30];
char s[110000];
ll ans=1;
int main()
{
scanf("%d\n",&n);
scanf("%s",s);
for(int i=1;i<=n;i++) num[s[i-1]-'a'+1]++;
for(int i=1;i<=26;i++) ans=(1ll*ans*(num[i]+1))%MOD;
ans--;
printf("%lld\n",ans);
return 0;
}
B:
题目描述:
给出一个元素个数为N的序列,每个元素有颜色,选取两个颜色相同的元素,把之间的元素都染成这个色,可以进行若干次染色操作,问可能存在的颜色序列个数
题目分析:
考虑dp[i]为考虑1-i这些存在的颜色序列,由于我们可以对一个地方进行染色和不染色两种选择,那么dp[i]=dp[i-1]+dp[last],其中dp[i-1]表示不染色,dp[last]表示上一个与i颜色相同的地方的方案数。
代码:
#include <cstdio>
#include <iostream>
const int maxm=2e5+100;
const int mod=1e9+7;
int c[maxm],n,ans;
int dp[maxm],lst[maxm];
int main()
{
scanf("%d",&n);
int now=0,tot=0;
for(int i=1,x;i<=n;i++)
{
scanf("%d",&x);
if(x!=now) now=x,c[++tot]=x;
}
dp[0]=1;
for(int i=1;i<=tot;i++) dp[i]=(dp[i-1]+lst[c[i]])%mod,lst[c[i]]=dp[i];
printf("%d\n",dp[tot]);
return 0;
}