題意:給定一個序列,問序列第i位數字;
思路:顯而易見,在1~9中,序列長度依次增加1,在10~99中,序列長度依次增加2。那麼我們可以求出所有num[n](num[n]以數n結尾的序列長度),因爲給的條件(1 ≤ i ≤ 2147483647),所以n最大爲31269(對所有的num[n]求個和就知道了);具體思路看代碼吧;
#include<iostream>
#include<algorithm>
#include<string>
#include<cstring>
#include<map>
#include<queue>
#include<cmath>
#include<stack>
#include<vector>
#include<cstdio>
#define MAXN 33000
#define INF 0x3f3f3f3f
#define lmid l,m,rt<<1
#define rmid m+1,r,rt<<1|1
#define ls rt<<1
#define rs rt<<1|1
#define Mod 1000000007
#define i64 __int64
#define LIMIT_ULL 100000000000000000
#define Max(a,b) (a>b)?a:b
#define lowbit(x) x&(-x)
using namespace std;
typedef long long ll;
int s[31269];
char ch[10];
void init()
{
s[0]=0;
for(int i=1;i<=31268;i++)
{
int j=i;
int t=0;
while(j)
{
j/=10;
t++;
}
s[i]=s[i-1]+t;
}
}
int main()
{
init();
int t;
scanf("%d",&t);
while(t--)
{
int n;
scanf("%d",&n);
int m;
for(int i=1;i<=31268;i++)//知道n所在的序列,該序列以m結尾
{
if(n<s[i])
{
m=i;
break;
}
n-=s[i];
}
if(n==0)//n==0說明n爲前一個序列的末尾,即(m-1)%10
{
cout<<(m-1)%10<<endl;
continue;
}
for(int i=m-1;i>=1;i--)//找到第一個長度小於n的序列,該序列以m結尾
{
if(s[i]<=n)
{
m=i;
n-=s[i];
break;
}
}
if(n==0)//n==0說明n爲該序列的末尾,即m%10
{
cout<<m%10<<endl;
continue;
}
for(int i=m+1;;i++)//枚舉,確定n所在位置
{
int j=i;
int t=0;
while(j)
{
j/=10;
t++;
}
if(n>=t)
{
n-=t;
if(n==0)
{
cout<<i%10<<endl;
break;
}
continue;
}
if(n<t)
{
sprintf(ch,"%d",i);
cout<<ch[n-1]<<endl;
break;
}
}
}
return 0;
}