2023ACM暑假训练day 6 字符串

DAY 6 字符串

训练地址:传送门

训练情况简介

2023-07-01 星期六
早上:A
下午:BCD
晚上:J

A 题

题意:
KMP算法板子
思路:
KMP算法板子,套板子即可
这里附上代码,再记一次KMP算法!

void get_nxt(string a){
	nxt[0]=-1;
	int j=0,k=-1;
	while(j<a.size()){
		if(k==-1||a[j]==a[k]){
			++j;++k;
			if(a[j]!=a[k]) nxt[j]=k;//优化的nxt数组
			else nxt[j]=nxt[k];
		}else k=nxt[k];
	}
	return ;
}

void solve(){
	while(cin>>ss){
		if(ss=="#") break;
		cin>>tt;
		get_nxt(tt);
		ll cnt=0;
		for(int i=0,j=0;i<ss.size();){//匹配
			if(j==-1||ss[i]==tt[j]){
				++i;++j;
			}else j=nxt[j];
			if(j==tt.size()){
				++cnt;
				j=0;//j=0重新开始判断
			}
		}
		cout<<cnt<<'\n';
	}
	return ;
}

B 题

题意:
给你一个字符串,你仅可以在字符串的头部和尾部添加字符,将这个字符串首尾相连,问你添加字符的最少数,使得添加后的字符串是一个循环字符串
思路:
传送门

//>>>Qiansui
#include<map>
#include<set>
#include<list>
#include<stack>
#include<cmath>
#include<queue>
#include<deque>
#include<cstdio>
#include<string>
#include<vector>
#include<utility>
#include<iomanip>
#include<cstring>
#include<cstdlib>
#include<iostream>
#include<algorithm>
#include<functional>
#define ll long long
#define ull unsigned long long
#define mem(x,y) memset(x,y,sizeof(x))
#define debug(x) cout << #x << " = " << x << endl
#define debug2(x,y) cout << #x << " = " << x << " " << #y << " = "<< y << endl
//#define int long long

inline ll read()
{
	ll x=0,f=1;char ch=getchar();
	while (ch<'0'||ch>'9'){if (ch=='-') f=-1;ch=getchar();}
	while (ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+ch-48;ch=getchar();}
	return x*f;
}

using namespace std;
typedef pair<int,int> pii;
typedef pair<ll,ll> pll;
typedef pair<ull,ull> pull;
typedef pair<double,double> pdd;
/*
找循环节
*/
const int maxm=1e5+5,inf=0x3f3f3f3f,mod=998244353;
string ss;
int nxt[maxm];

void get_nxt(string a){
	nxt[0]=-1;
	int j=0,k=-1;
	while(j<a.size()){
		if(k==-1||a[j]==a[k]){
			++j;++k;
			nxt[j]=k;
		}else k=nxt[k];
	}
	return ;
}

void solve(){
	cin>>ss;
	get_nxt(ss);
	int n=ss.size();
	int l=n-nxt[n];
	if(nxt[n]==0) cout<<n<<'\n';//特判
	else cout<<(l-n%l)%l<<'\n';
	return ;
}

signed main(){
	ios::sync_with_stdio(false),cin.tie(0),cout.tie(0);
	int _=1;
	cin>>_;
	while(_--){
		solve();
	}
	return 0;
}

C 题

题意:
马拉车算法模板题
思路:
马拉车算法模板题

string manacher(string s)
{
    string t="$#";
	for(auto a:s){
		t+=a;
		t+='#';
	}
	vector<int> p(t.size()+5,0);
	int mx=0,id=0,maxl=0,maxp=0;
	for(int i=1;i<t.size();++i){
		p[i]=mx>i ? min(mx-i,p[(id<<1)-i]) : 1 ;
		while(t[i+p[i]]==t[i-p[i]]) ++p[i];
		if(i+p[i]>mx){
			mx=i+p[i];
			id=i;
		}
		if(p[i]>maxl){
			maxl=p[i];
			maxp=(i-p[i])/2;
		}
	}
	return s.substr(maxp,maxl-1);
}

D 题

题意:
给定n个字符串,让你判定这n个字符串的种类数
思路:
字符串哈希

const int maxm=1e4+5,inf=0x3f3f3f3f,mod=998244353;
int n;
ull a[maxm];
set<ull> q;
string ss;

ull stringhash(string s){//进制哈希
	ull p=131,ans=0;
	for(auto a:s){
		ans=ans*p+a;
	}
	return ans;
}

void solve(){
	cin>>n;
	for(int i=0;i<n;++i){
		cin>>ss;
		q.insert(stringhash(ss));
	}
	cout<<q.size()<<'\n';
	return ;
}

J 题

题意:
ac自动机模板题
思路:
ac自动机模板题

posted on 2023-07-01 09:21  Qiansui  阅读(9)  评论(0编辑  收藏  举报