数据结构 - Classical String Problem - 2020牛客暑期多校训练营(第三场)

数据结构 - Classical String Problem - 2020牛客暑期多校训练营(第三场)

题意:

给 定 一 个 字 符 串 S , 以 及 Q 组 询 问 , 给定一个字符串S,以及Q组询问, SQ

分 成 两 种 情 况 : 分成两种情况:

A   x : 输 出 S 的 第 x 个 字 符 。 A\ x:输出S的第x个字符。 A xSx

Q   x : 若 x > 0 , 表 示 将 S 的 长 度 为 x 前 缀 转 移 到 S 的 尾 部 。 Q\ x:若x>0,表示将S的长度为x前缀转移到S的尾部 。 Q xx>0SxS

    若 x < 0 , 表 示 将 S 的 长 度 为 ∣ x ∣ 的 后 缀 转 移 到 S 的 首 部 。 \qquad\ \ \ 若x<0,表示将S的长度为|x|的后缀转移到S的首部。    x<0SxS

输入:

首 行 包 括 字 符 串 S 。 首行包括字符串S。 S

第 二 行 包 括 整 数 Q 。 第二行包括整数Q。 Q

接 着 Q 行 表 示 Q 组 操 作 。 接着Q行表示Q组操作。 QQ

每 组 操 作 包 括 字 符 c , 和 整 数 x 。 每组操作包括字符c,和整数x。 cx

示例1
输入

nowcoder
6
A 1
M 4
A 6
M -3
M 1
A 1

输出

n
o
w

数据范围:

2 ≤ ∣ S ∣ ≤ 2 × 1 0 6 , 1 ≤ Q ≤ 8 × 1 0 5 , 2≤∣S∣≤2×10^6, 1≤Q≤8×10^5, 2S2×106,1Q8×105,

c = ′ M ′   o r   ′ A ′ c = 'M' \ or\ 'A' c=M or A

c = ′ M ′ , 1 ≤ ∣ x ∣ < ∣ S ∣ c = 'M', 1≤∣x∣<|S | c=M,1x<S

c = ′ A ′ , 1 ≤ x ≤ ∣ S ∣ c = 'A', 1≤x≤|S| c=A,1xS


分析:

指 针 维 护 字 符 串 的 首 字 母 位 置 即 可 。 查 询 时 增 加 偏 移 量 x , 就 能 够 在 O ( 1 ) 的 时 间 内 快 速 查 询 。 指针维护字符串的首字母位置即可。查询时增加偏移量x,就能够在O(1)的时间内快速查询。 xO(1)

c = ′ M ′ , x > 0 : 更 新 s t = s t ′ , e d = e d ′ 。 c='M',x>0:更新st=st',ed=ed'。 c=Mx>0st=sted=ed

在这里插入图片描述
c = ′ M ′ , x < 0 : 更 新 s t = s t ′ , e d = e d ′ 。 c='M',x<0:更新st=st',ed=ed'。 c=Mx<0st=sted=ed
在这里插入图片描述

代码:

#include <cstdio>
#include <cstring>
#include <string>
#include <cmath>
#include <iostream>
#include <algorithm>

using namespace std;

const int N=2e6+10;

int q;
char str[N];

int main()
{
    scanf("%s",str);
    int len=strlen(str);
    int st=0,ed=len-1;
    
    char op[2];
    int x;
    cin>>q;
    while(q--)
    {
        scanf("%s%d",op,&x);
        if(*op=='A') printf("%c\n",str[(st+x-1)%len]);
        else
        {
            if(x>0) 
            {
                st=(st+x)%len;
                ed=(st-1+len)%len;
            }
            else
            {
                st=(ed+x+1+len)%len;
                ed=(ed+x+len)%len;
            }
        }
    }
    
    return 0;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值