酷暑一夏1

不忘初心,方得始终


Vijos1181 CoVH之密码破解 题解

题目

话说一天,Dragon.Dai大菜和整个OIBH QQ群的超级大牛同心协力,终于进入了Vijos的系统,并设置了重重机关……
等到V某带着柯南来到服务器准备检查Log(即是日志文件)时,才发现Log文件被加了密,密码是一个数列中的指定一位……(数列见下)经过V某及柯南的思考,总算破解了密码,看到了Log。
数列:12345678910111213………..
输入是一个数$n$,表示求数列的第$n$位
1<=$n$<=10^8

题解

[例子中所有提到的位数已加粗斜体加粗,请对应后面提到的位数的字形]

先确定这个位置的每个数字有多少位,例如【1234567891011213】中第5位数字为1位数,第12位数字为2位数。可以直接用范围来确定,详见下图。图中第一行是数字的位数,第二行为这个位数的数字的最后一位在整个数列中是第几位,至于怎么用它确定位数就不用说了吧,实在不会看代码吧。
位数-对应值

1
2
可拷贝版本:
9,189,2889,38889,488889,5888889,68888889,788888889

然后要确定它的值,也就是获取这一位在这个位数的数字中是第几位(例如【1234567891011213】,第12位就是这个位数(2位数)中的第3位),然后除以数字的位数(取整),此时你获得了这个数是这个位数的数字中的第几个(0起计数)。(例如第12位,是两位数中的第三位,除数字位数2,去整,值为1),然后加上前面(位数-1)的数字个数,即为结果,但是这个结果只是这整个数,你需要输出的是:(所求位数-上一位最后一位在整个数列中是第几位)取余当前位数,若取余结果为0请输出这整个数的最后一位,例如若这个数是123,你要求的那一位取余后为0,请输出3。
说得可能有点乱,请看代码。

代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
#include<cstdio>
const int MAXN=1000+5;
int n,k,f,foot[MAXN][2],total[MAXN];
int main()
{
int a,ln;
scanf("%d %d",&n,&k);
scanf("%d",&f);
for(int i=1;i<=f;i++)
{
scanf("%d %d",&ln,&a);
total[ln]+=a;
}
int now=1,left=k,ans=1,nowfoot=1,line=foot[1][0],use;
while(now<=n)
{
// printf("Excuted.\n");
if(left<1)
{
ans++;
left=k;
}
left--;
use=total[now];
if(use)
{
if(left<use)
{
ans++;
left=k-1;
}
left-=use;
// printf("Foot %d of line %d on page %d, left %d line(s)\n",nowfoot,line,ans,left);
// line=foot[++nowfoot][0];
}
// printf("Line %d on page %d, left %d line(s)\n",now,ans,left);
now++;
// printf("Next: %d\n",now);
}
printf("%d",ans);
return 0;
}
最近的文章

Vijos1203 CoVH之资料页数 题解

题目柯南已经从灰原哀那里得到了一些关于OIBH组织的情报, 他想在阿笠把整理的资料打印出来, 仔细研究.这份资料的正文包含许多行,某些行可能包含一些脚注标记,一个脚注可能包含一行或多行,并且必须和对应的脚注标记印刷在同一页一页所允许印刷的最多行数是已知的,任何一页都不允许超过该行数(包括脚注)但是阿 …

于  CoVH系列, Vijos 继续阅读
更早的文章

hihoCoder1493 [Offer收割]编程练习赛12 A题题解

题目哥德巴赫猜想认为“每一个大于2的偶数,都能表示成两个质数之和”。给定一个大于2的偶数N,你能找到两个质数P和Q满足P&lt;=Q并且P+Q=N吗? 题解筛质数,然后在$[2,n)$中找结果即可。 代码1234567891011121314151617181920212223242526#incl …

于  Offer收割, hihoCoder, 比赛 继续阅读