如何在编程中求解线性丢番图方程

How to solve Linear Diophantine equations in programming?

本文关键字:线性 方程 编程      更新时间:2023-10-16

我读过关于线性丢番图方程的信息,例如ax+by=c被称为丢番图方程,只有在gcd(a,b) divides c时才给出整数解。

这些方程在编程竞赛中非常重要。当我遇到这个问题时,我只是在互联网上搜索。我认为这是丢番图方程的变体。

问题:

我有两个人,人X和人Y都站在绳子中间。人X可以在一个动作中向左或向右跳A或B单位。人Y可以在一个动作中向左或向右跳C或D单位。现在,我得到了一个数字K,我必须找到数字。绳索上 [-K,K] 范围内可能的位置,以便两个人都可以使用各自的电影多次到达该位置。(A、B、C、D 和 K 有问题(。

我的解决方案:

我认为这个问题可以用丢番图方程在数学上解决。

我可以像A x_1 + B y_1 = C_1 where C_1 belongs to [-K,K]一样为人 X 形成一个方程,对像 C x_2 + D y_2 = C_2 where C_2 belongs to [-K,K] 这样的人 Y 形成一个方程。

现在,我的搜索空间减少到仅查找C_1和C_2相同的可能值的数量。这将是我对这个问题的回答。

为了找到这些值,我只是找到gcd(A,B)gcd(C,D),然后取这两个 gcdlcm 得到LCM(gcd(A,B),gcd(C,D)),然后简单地计算范围 [1,K] 中的点数,这是这个 lcm 的倍数。

我的最终答案将是2*no_of_multiples in [1,K] + 1.

我尝试在C++代码中使用相同的技术,但它不起作用(错误答案(。

这是我的代码:http://pastebin.com/XURQzymA

我的问题是:谁能告诉我我是否正确使用了丢番图方程?

如果是,谁能告诉我我的逻辑失败的可能情况。

这些是在网站上给出的一些测试用例,并带有问题陈述。

A B C D K 作为输入以相同的顺序给出,相应的输出在下一行给出:

2 4 3 6 7

3

1

2 4 5 1

3

10 12 3 9 16

5

这是原始问题的链接。我用简单的语言写了原始问题。您可能会发现这很困难,但如果需要,可以检查一下:

http://www.codechef.com/APRIL12/problems/DUMPLING/

请给我一些测试用例,以便我找出我做错了哪里?

提前谢谢。

求解线性丢番图方程

ax + by = cgcd(a, b)划分c.

  1. 将 a、b 和 c 除以 gcd(a,b(。
  2. 现在 gcd(a,b( == 1
  3. 使用扩展欧几里得算法找到 aU + bV = 1 的解
  4. 将方程乘以 c。现在你有 a(Uc( + b (Vc( = c
  5. 您找到了解决方案x = U*cy = V * c

问题是输入值是 64 位(最多 10^18(,因此 LCM 最多可以 128 位大,因此l可能会溢出。 由于k是 64 位的,溢出l表示 k = 0(因此答案为 1(。 您需要检查此情况。

例如:

unsigned long long l=g1/g; // cannot overflow
unsigned long long res;
if ((l * g2) / g2 != l)
{
    // overflow case - l*g2 is very large, so k/(l*g2) is 0
    res = 0;
}
else
{
    l *= g2;
    res = k / l;
}