26 Reciprocal Cycles
对于有理数,分成有限小数和无限循环小数。比如
对于无限循环小数,循环节表示后续循环的部分。比如 ,循环节是 6,长度是 1。,循环节是 142857,长度是 6。
欧拉项目的第二十六题很有意思。基于以上知识,对于任意 ,找到分数 循环节最长的那个 。
如何计算循环节长度呢?
想想我们手算,如果余数比除数小,我们会在后面补 0 然后再除。也就是说补零之后的数是下一次的被除数。如果被除数重复出现,除数确定的,那么商和余数也就是一样的。这时,循环节就出现了。
下面的函数分为两部分 1. 补零操作 2. 查找有没有同样的被除数存在,如果有,就找到了循环节,计算循环节长度并返回。在没有找到的前提下,把当前被除数记录下来,并得到余数作为下一次的被除数。
这里需要注意,如果某一次出现了除尽的情况,说明该分数是有限小数,循环节长度是 0。
下面是函数代码:
// n/m
static int GetRecurringCycle(int n, int m)
{
List<int> dividends = new List<int>();
while (true)
{
while (n < m)
{
n *= 10;
}
// search pattern.
int index = dividends.IndexOf(n);
if (index >= 0)
{
return dividends.Count - index;
}
dividends.Add(n);
n %= m;
// n is divisible by m.
if (n == 0)
{
return 0;
}
}
}
能够计算循环节长度,得到循环节最长的那个就易如反掌了。