中心对称字符串

文章介绍C++实现字符串中心对称性判断的方法,通过预计算和哈希函数检测子串特征。

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

题目

#include<bits/stdc++.h>
using namespace std;
#define int long long
using ll = long long;
const int maxn = 5e6 + 5;
const string a("bdpqnuosxz");
const string b("qpdbunosxz");
const ll mod = 1e9 + 7, base = 397;
int pre[maxn], p[maxn];
int pre_hash(int l, int r){
    return ((pre[r] - pre[l - 1] * p[r - l + 1]) % mod + mod) % mod;
}
void solve()
{
    string s;
    cin >> s;
    int n = s.size();
    s = '*' + s;
    for (int i = 1; i <= n; ++i)
    {
        if (a.find(s[i]) == -1)
        {
            cout << "No\n";
            return;
        }
    }
    
    string t = s;
    for (int i = n; i >= 1; --i)
    {
        int fd = a.find(s[i]);
        t += b[fd];//t是s拼接上 经过字符反转和整个字符串翻转的s
    }
    
    //cout << t << '\n';
    // get p
    //vector<ll> p(n + 3);
    
    
    // get hash
    //vector<ll> pre(n * 2 + 3);
    //pre[0] = s[0];
    for (int i = 1; i <= n * 2; ++i)
    {
        pre[i] = (pre[i - 1] * base % mod + t[i]) % mod;
            
    }
    int l = 1, r1 = n * 2;
    for (int r = 1, l1 = n * 2; r <= n; ++r, --l1){
         //在s进行分割出[l, r],如果[l, r]是中心对称的,那么t的[l, r]的子串与t的[l1, r1]子串相同
        //然后l跳到r + 1(即在s中分割出尽可能短的中心对称串)
        if (pre_hash(l, r) == pre_hash(l1, r1))
            r1 = l1 - 1, l = r + 1;   
    }
        

    if (l == n + 1)
        cout << "Yes\n";
    else
        cout << "No\n";
}
signed main(){
    ios::sync_with_stdio(0);
    cin.tie(0);
    p[0] = 1;
    for (int i = 1; i <= maxn - 5; ++i)
        p[i] = p[i - 1] * base % mod;
    int T;
    cin >> T;
    while(T--){
        solve();
    }
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

__night_

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值