今天在庞果网做了一道题,倒水问题,题目如下,有两个容器,容积分别为A升和B升,有无限多的水,现在需要C升水。 我们还有一个足够大的水缸,足够容纳C升水。起初它是空的,我们只能往水缸里倒入水,而不能倒出。 可以进行的操作是: 把一个容器灌满; 把一个容器清空(容器里剩余的水全部倒掉,或者倒入水缸); 用一个容器的水倒入另外一个容器,直到倒出水的容器空或者倒入水的容器满。问是否能够通过有限次操作,使得水缸最后恰好有C升水。
X*A+Y*B=C
根据欧几里得算法的扩展定理
定理
对于不完全为 0 的非负整数 a,b,gcd(a,b)表示 a,b 的最大公约数,必然存在整
数对 x,y ,使得 gcd(a,b)=ax+by, 并且是能表示的最小正元素;
ax+by = gcd(a,b)+(cx+dy);a = e*gcd(a,b),b=f*g(a,b);
所以ax+by能组合的数一定是gcd(a,b) 的自然数倍;
那么只要C是gcd(a,b)的倍数就返回true,反之返回false。
java实现如下
- import java.io.*;
- import java.math.BigInteger;
- import java.util.*;
- public class Main {
- public static boolean can(int a,int b,int c) {
- int res;
- res=mod(a,b);
- if(c%res==0)
- return true;
- else
- return false;
- }
- public static void main(String args[])
- {
- System.out.print(can(0,1,1000000000));
- }
- public static int mod(int a,int b){
- if(b>=1){
- return mod(b, a%b);
- }
- else return a;
- }
- }