[codeforces] 897C Nephren gives a riddle

题目链接:

C. Nephren gives a riddle

题目大意:

q组测试,每组给一个初始字符串 s0 , 定义字符串 si= “What are you doing while sending “ fi1 ”? Are you busy? Will you send “ fi1 ”?” 问 Sn 的第k个字母是什么 。

数据范围:

1q10
1n105
1k1018

解题思路:

思路就是看k在哪一段, 一段一段的去判断, 当位于 si1 段的时候, 就递归一下查找。

AC代码:
/********************************************
 *Author*        :ZZZZone
 *Created Time*  : 六 12/ 2 21:53:02 2017
 * Ended  Time*  : 二 12/ 5 16:12:47 2017
*********************************************/

#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#include <vector>
#include <queue>
#include <set>
#include <map>
#include <string>
#include <cmath>
#include <cstdlib>
#include <ctime>
#include <stack>
using namespace std;
typedef pair<int, int> PII;
typedef long long LL;
typedef unsigned long long ULL;
const LL INF = 1e18;
const int MaxN = 1e5;

const string s0 = "What are you doing at the end of the world? Are you busy? Will you save us?";
const string s1 = "What are you doing while sending \"";
const string s2 = "\"? Are you busy? Will you send \"";
const string s3 = "\"?";
const LL len0 = s0.size(), len1 = s1.size(), len2 = s2.size(), len3 = s3.size();

LL sum[MaxN + 5];

char solve(LL k, int n){
    if(n == 0){
        if(k >= 1 && k <= len0) return s0[k - 1];
        else return '.';
    }
    if(k <= len1) return s1[k - 1];
    k -= len1;
    if(k <= sum[n - 1] || sum[n - 1] == 0) return solve(k, n - 1);
    k -= sum[n - 1];
    if(k <= len2) return s2[k - 1];
    k -= len2;
    if(k <= sum[n - 1] || sum[n - 1] == 0) return solve(k, n - 1);
    k -= sum[n - 1];
    if(k <= len3) return s3[k - 1];
    return '.';
}

int main()
{
    int q, n;
    LL k;
    sum[0] = len0;
    LL tot = len1 + len2 + len3;
    for(int i = 1; sum[i - 1] <= INF; i++)
        sum[i] = tot + sum[i - 1] * 2LL;
    scanf("%d", &q);
    while(q--){
        scanf("%d %lld", &n, &k);
        printf("%c", solve(k, n));
    }
    return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值