http://acm.hdu.edu.cn/showproblem.php?pid=2394

题目的大概意思就是,判断关于x的二次同余方程 a x^2 + b x + c = 0 ( mod 2 ^32 ) 是否有解

看到这道题目的时候刚好看了一些二次互反律之类的知识,思维被定向到了那边,又在网上找了一些资料,但是都不能解决此题(起码我没有想出来怎么办,大牛勿鄙视)。跟haozi讨论了一下,也没什么结果,后来haozi用java的大数把这题过了,我也不知道他怎么做的,他只说是很暴力的方法。今天在ACM_DIY群里请教了一下 UESTC 的 love8909 大牛,原来只要分来讨论 a b c 的奇偶性一共8种情况,比如:abc都是偶数,那么方程等价于 a/2 x^2 + b/2 x + c/2 = 0 ( mod 2 ^31 ), 通过讨论可以将mod的数降下来,一直到2^0为止,若能达到,必然有解,还有一些情况详见我代码:

hdu_2394
 1#include <cstdio>
 2#include <iostream>
 3#include <map>
 4#include <queue>
 5#include <complex>
 6#include <algorithm>
 7#include <cmath>
 8#include <cstring>
 9using namespace std;
10typedef __int64 ll;
11
12bool solve( ll a, ll b, ll c, int k )
13{
14    if( k == 0 )
15    {
16        return true;
17    }

18    if( a % 2 == 0 )
19    {
20        if( b % 2 == 0 )
21        {
22            if( c % 2 == 0 ) // 0 0 0
23            {
24                return solve( a / 2, b / 2, c / 2, k - 1 );
25            }

26            else             // 0 0 1
27            {
28                return false;
29            }

30        }

31        else
32        {
33            if( c % 2 == 0 ) // 0 1 0
34            {
35                return solve( 2 * a, b, c / 2, k - 1 );
36            }

37            else             // 0 1 1
38            {
39                return solve( 4 * a, 4 * a + 2 * b, a + b + c, k -1 );
40            }

41        }

42    }

43    else 
44    {
45        if( b % 2 == 0 )
46        {
47            if( c % 2 == 0 ) // 1 0 0
48            {
49                return solve( 2 * a, b, c / 2, k - 1 );
50            }

51            else            // 1 0 1
52            {
53                return solve( 4 * a, 4 * a + 2 * b, a + b + c, k - 1 );
54            }

55        }

56        else 
57        {
58            if( c % 2 == 0 ) // 1 1 0
59            {
60                return solve( 2 * a, b, c / 2, k - 1 ) ||
61                       solve( 4 * a, 4 * a + 2 * b, a + b + c, k - 1 );
62            }

63            else             // 1 1 1
64            {
65                return false;
66            }

67        }

68    }

69}

70
71int main(int argc, char *argv[])
72{
73    int n;
74    ll a, b, c;
75    scanf("%d",&n);
76    while( n-- )
77    {
78        scanf("%I64d%I64d%I64d",&a,&b,&c);
79        if( solve( a, b, c, 32 ) )printf("YES\n");
80        else printf("NO\n");
81    }

82    return 0;
83}

84