加载中…
个人资料
  • 博客等级:
  • 博客积分:
  • 博客访问:
  • 关注人气:
  • 获赠金笔:0支
  • 赠出金笔:0支
  • 荣誉徽章:
正文 字体大小:

POJ PKU 3720 除法模拟

(2010-04-30 07:43:10)
标签:

poj

pku

3720

it

分类: 杂题

题目描述:

给你一个n和k,在2~100之间,k在0 ~ 9之间,求1/2 ..... 1/n的小数(或者无限循环)中,k数字出现的次数。

解题报告:

纯粹模拟即可:

模拟99次除法,把每次的无限循环小数出现的次数存入ans[i][j]里

表示1 / i的小数中,数字j出现的次数。

那么答案就是

sigma(ans[i][k])  2<=i<=n。

下面说一下怎样求每个的答案。

以7为例:

now表示当前的被除数。初始时一定是10.

10 / 7 = 1  => 第1位小数是1。now变为 10 - 7 * 1 = 3,然后再添个0,成了30.

30 / 7 =  => 第2位小数是4。now变为 30 - 7 * 4 = 2,然后再添个0,成了20.

20 / 7 =  => 第3位小数是2。now变为 20 - 7 * 2 = 6,然后再添个0,成了60.

60 / 7 =  => 第4位小数是8。now变为 60 - 7 * 8 = 4,然后再添个0,成了40.

40 / 7 =  => 第5位小数是5。now变为 40 - 7 * 5 = 5,然后再添个0,成了50.

50 / 7 =  => 第6位小数是7。now变为 50 - 7 * 7 = 1,然后再添个0,成了10.

注意,10已经在第一行出现过了,所以在此开始循环,所以

1/7 = 0.142857

代码很短,如下:

#include<iostream>
using namespace std;
int n, k, ans[101][10];
bool vst[10000];
void jeogia(int n)
{
    int now = 10;
    memset(vst, 0, sizeof(vst));
    while(!vst[now] && now != 0)
    {
        vst[now] = 1;
        int temp = now / n;
        ans[n][temp] ;
        now -= temp * n;
        now *= 10;
    }
}
int main()
{
    memset(ans, 0 ,sizeof(ans));
    for(int i = 2; i <= 100; i ) jeogia(i);
    while(scanf("%d%d", &n, &k) != EOF)
    {
        int re = 0;
        for(int i = 2; i <= n; i )
            re = ans[i][k];
        printf("%d\n", re);
    }
    return 0;
}

 

0

阅读 收藏 喜欢 打印举报/Report
  

新浪BLOG意见反馈留言板 欢迎批评指正

新浪简介 | About Sina | 广告服务 | 联系我们 | 招聘信息 | 网站律师 | SINA English | 产品答疑

新浪公司 版权所有