洛谷:P1029:最大公约数和最小公倍数问题


洛谷:P1029:最大公约数和最小公倍数问题

题目

P1029:最大公约数和最小公倍数问题

分析

让我们用这道题目来回顾一些数论中的基本概念。

最大公约数

如果\(a_1\)\(a_2\)是两个整数,而且\(d|a_1, d|a_2\)(或者写成\(a_1\%d=a_2\%d=0\)),那么\(d\)就是\(a_1\)\(a_2\)的公约数。这样的d可能有好几个,其中最大的那个就是“最大公约数”(Greatest Common Divisor,简称gcd)。特别地,如果GCD(a, b)=1,那么这两个数互质。

求两个数的gcd有最完美的解法,也就是欧几里得发明的辗转相除法:

int gcd(int a, int b)
{
    return b == 0 ? a : gcd(b, a % b);
}

最小公倍数

gcd对应的是“最小公倍数”(Least Common Multiple,简称lcm)。求出gcd后,可以这样求lcm\(LCM=(a\times b) / GCD\)

GCD的一个重要性质

如果有很多数字,怎么求最大公约数呢?这里需要用到gcd的一个重要性质:

对于\(a_1, a_2, ..., a_i, a_{i+1}, ..., a_n\)而言,如果它们的GCD是某个数,那么:

\(gcd(a_1, a_2, ..., a_i, a_{i+1}, ..., a_n)=gcd(gcd(a_1, a_2, ..., a_i), gcd(a_{i+1}, ..., a_n))\)

也就是说,在求多个数字的gcd的时候,完全可以分组求出。

本题思路

回到本题,已经给出了gcd\(x_0\))和lcm\(y_0\)),要求一对数P/Q,且\(gcd(P, Q)=x_0, lcm(P, Q)=y_0\)

可见:

\( \begin{cases} P=gcd*a \\Q=gcd*b \\P\times Q=gcd*lcm \end{cases} \)

其中:\(gcd=x_0, lcm=y_0, gcd(a, b)=1\)

由于求出P后就能得到Q,我们只要进行一个循环即可。考虑到P的公式,我们循环的上限可以限制在\(m=y_0/x_0\)。为什么呢?因为对于a来说,它的上限不会超过m。证明如下:

\(\begin{align*} & P\times Q = gcd\times lcm = x_0\times y_0 \\ & P = gcd\times a, Q = gcd\times b \\ & P = x_0\times a, Q = x_0\times b \\ & x_0\times a\times x_0\times b = x_0\times y_0 \\ & \therefore a\times b = y_0/x_0 \end{align*}\)

我们找到了P就知道了Q,但在计数的时候要考虑一下两个数是否相等的问题。

答案

Solution

思考

这道题目不是很难,关键是确定a的上限。

上一篇 下一篇