【SSL】20210817A

博客介绍了如何解决一个关于字符串子序列的问题。给定一个字符串S和多个询问T,任务是判断每个T是否为S的子序列。文章提供了输入输出格式、解题思路和代码实现。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

【SSL】20210817A


题目描述

给出长度为n的字符串S,以及Q个询问
每个询问给出一个字符串T,判断T是否为S的一个子序列
所有串仅包含小写字母
30%:n<=1e4,q<=1e5
100%:
在这里插入图片描述

输入格式

第一行给出正整数n,Q
第二行给出S
接下来Q行,每行给出一个询问T

输出格式

对于每个询问输出一行表示答案,符合输出YES,不符输出NO

输入样例

3 1
abc
ac

输出样例

YES

解题思路

输入时用f[i,j]表示位置i以后字符j第一次出现的位置
然后预处理所有的f[i,j],然后暴力每次询问。

Code

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
const int mx=100100;
int n,q,tong[30][mx],lt[30],f[mx][30],lent;
string s,at;
int main()
{
	scanf("%d%d",&n,&q);
	cin>>s;
	for(int i=0;i<n;++i)
	{
		tong[s[i]-96][++lt[s[i]-96]]=i;
	}
	for(int i=1;i<=26;++i)
	{
		int k=1;
		for(int j=0;j<n;++j)
		{
			if(tong[i][k]<j) k++;
			if(k>lt[i]) f[j][i]=-1;
			else f[j][i]=tong[i][k];
		}
	}
	for(int i=1;i<=q;++i)
	{
		cin>>at;
		lent=at.size();
		int k=0;
		bool flag=true;
		for(int j=0;j<lent;++j)
		{
			if(k<n&&f[k][at[j]-96]>=0)k=f[k][at[j]-96]+1;
			else
			{
				flag=false;
				break;
			}
		}
		if(flag) printf("YES\n");
		else printf("NO\n");
	}
}

谢谢阅读

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值