题目链接 :
P3612 [USACO17JAN]Secret Cow Code S
这道题的思路是给你一个字符串,这个字符串变长的规律是先加尾结点,然后再把前面的部分平移到后面
a + b 反 转 后 a + b + b + a a + b 反转后 a + b +b + a a+b反转后a+b+b+a
b是原字符串的最后一个字符,变换规律如上所示,这道题给你第n个字符,让你输出相应的字符
思路 : 我们先把字符串扩展到第一次出现大于等于n的长度 , 然后根据最后一次扩展的位置,返回上一个扩展字符所在的位置
首先我们观察一下
现在的扩展的字符串 , 字符串由原字符串 + 新扩展的字符串 组成。
故我们可以推出,如果这个当前我们所需要的pos在右半边,我们就返回左半边对应的位置,如果在左半边直接返回当前位置(左半边是原字符串)。
故题意清晰,代码实现:
//#pragma GCC optimize(2)
#include <iostream>
#include <algorithm>
#include <cstdio>
#include <cmath>
#include <cstring>
#include <queue>
#include <stack>
#include <set>
#include <vector>
#include <unordered_map>
#include <map>
#include <unordered_set>
#include <ctime>
using namespace std ;
typedef long long LL ;
typedef pair<int , int> PII ;
const int N = 1e5 + 10 , INF = 0x3f3f3f3f ;
const double eps = 1e-8 ;
int read()
{
int res = 0 , flag = 1 ;
char c = getchar();
while(!isdigit(c))
{
if(c == '-') flag = -1 ;
c = getchar() ;
}
while(isdigit(c))
res = (res << 1) + (res << 3) + (c ^ 48) , c = getchar() ;
return res * flag ;
}
LL n ;
LL get(LL k , LL len)
{
LL pos = 0 ;
if(len < n) pos = get(k + 1 , len * 2) ;
if(k == 1) // 小细节
{
if(pos == 0) return n ;
else return pos ;
}
if(pos == 0) // 小细节
{
LL ans = n - len / 2 ;
if(ans == 1) return len / 2 ;
else return ans - 1 ;
}
else // 代码实现操作
{
if(pos <= len / 2) return pos ;
else
{
LL ans = pos - len / 2 ;
if(ans == 1) return len / 2 ;
else return ans - 1 ;
}
}
}
int main()
{
string s ;
cin >> s >> n ;
cout << s[get(1 , s.size()) - 1] ;
}