给定长度为 n 的字符串 s,进行 c 次操作,每次操作将 sl 到 sr 复制到字符串尾。 全部操作结束后有 q 次询问,每次询问字符串 s 的第 k 位。
1≤n≤2⋅10^5,1≤c≤40,1≤q≤104,1≤l≤r≤10^18,1≤k≤10^18
数据保证 r 不超过当前字符串长,度,k 不超过最终字符串长度。
#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>
#include <algorithm>
const int N=2e5+15;
using namespace std;
typedef long long ll;
int t,c,q;
ll len[45],cp[45][2];
char a[N];
void solve(ll x){
int pt=0;
if(x<=len[0]){printf("%c\n",a[x-1]);return;}
while(len[pt]<x) ++pt;
x-=len[--pt];
solve(cp[pt+1][0]-1+x); //字符串 s 粘贴位置的字符=对应复制位置的字符
return;
}
int main(){
scanf("%d",&t);
while(t--){
scanf("%lld%d%d%s",&len[0],&c,&q,a);
for(ll i=1;i<=c;++i)//i使用long long
scanf("%lld%lld",&cp[i][0],&cp[i][1]),len[i]=len[i-1]+cp[i][1]-cp[i][0]+1;
//输入时存储左(第几位),右端点,顺便处理长度
while(q--){
ll k;scanf("%lld",&k);
solve(k);
}
}
return 0;
}