您的位置:首页 > 其它

循环小数的循环节问题

2016-11-10 15:25 218 查看
题目链接:https://www.bnuoj.com/v3/external/2/202.pdf

/*
通过模拟手算竖式的过程,可以发现
如果同一个余数在竖式中出现两次,
那么小数就开始循环了,循环节的始末位置
与这个余数出现在竖式中的位置有关
这里就不详细给出分析过程了,网上可以找到
详细的解题过程
*/
#include <cstdio>
#include <cstring>
const int maxn = 3010;
//数组d用来存放商,数组m用来存放余数,book[k]统计余数k出现的次数
int d[maxn], m[maxn], book[maxn];
int main()
{
int a, b;
while (scanf("%d %d", &a, &b) == 2) {
//head,tail用来锁定循环节的始末位置
int len, head, tail;
memset(book, 0, sizeof(book));
d[0] = a / b;
m[0] = a % b;
book[m[0]]++;

int i;
//余数重复出现,说明出现循环节,跳出循环
for (i = 0; book[m[i]] < 2; i++) {
int tem = m[i] * 10;
d[i+1] = tem / b;
m[i+1] = tem % b;
book[m[i+1]]++;   //统计余数出现的次数
}
tail = i;
//找到循环节长度
for (head = 0; m[head] != m[tail]; head++)
;
len = tail - head;

//输出部分
printf("%d/%d = %d.", a, b, d[0]);
if (len <= 50) {
for (int k = 1; k <= head; k++) printf("%d", d[k]);
printf("(");
for (int k = head + 1; k <= tail; k++) printf("%d", d[k]);
printf(")\n");
} else {
for (int k = 1; k <= head; k++) printf("%d", d[k]);
printf("(");
for (int k = head + 1; k <= head + 50; k++) printf("%d", d[k]);
printf("...)\n");
}

printf("   %d = number of digits in repeating cycle\n\n", len);
}

return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: