1 /* Test mpz_perfect_square_p.
3 Copyright 2000, 2001, 2002 Free Software Foundation, Inc.
5 This file is part of the GNU MP Library.
7 The GNU MP Library is free software; you can redistribute it and/or modify
8 it under the terms of the GNU Lesser General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or (at your
10 option) any later version.
12 The GNU MP Library is distributed in the hope that it will be useful, but
13 WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
14 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
15 License for more details.
17 You should have received a copy of the GNU Lesser General Public License
18 along with the GNU MP Library. If not, see http://www.gnu.org/licenses/. */
27 #include "mpn/perfsqr.h"
30 /* check_modulo() exercises mpz_perfect_square_p on squares which cover each
31 possible quadratic residue to each divisor used within
32 mpn_perfect_square_p, ensuring those residues aren't incorrectly claimed
35 Each divisor is taken separately. It's arranged that n is congruent to 0
36 modulo the other divisors, 0 of course being a quadratic residue to any
39 The values "(j*others)^2" cover all quadratic residues mod divisor[i],
40 but in no particular order. j is run from 1<=j<=divisor[i] so that zero
41 is excluded. A literal n==0 doesn't reach the residue tests. */
46 static const unsigned long divisor[] = PERFSQR_DIVISORS;
49 mpz_t alldiv, others, n;
55 /* product of all divisors */
56 mpz_set_ui (alldiv, 1L);
57 for (i = 0; i < numberof (divisor); i++)
58 mpz_mul_ui (alldiv, alldiv, divisor[i]);
60 for (i = 0; i < numberof (divisor); i++)
62 /* product of all divisors except i */
63 mpz_set_ui (others, 1L);
64 for (j = 0; j < numberof (divisor); j++)
66 mpz_mul_ui (others, others, divisor[j]);
68 for (j = 1; j <= divisor[i]; j++)
71 mpz_mul_ui (n, others, j);
73 if (! mpz_perfect_square_p (n))
75 printf ("mpz_perfect_square_p got 0, want 1\n");
88 /* Exercise mpz_perfect_square_p compared to what mpz_sqrt says. */
97 gmp_randstate_ptr rands = RANDS;
106 for (i = 0; i < reps; i++)
108 mpz_urandomb (bs, rands, 9);
109 x2n = mpz_get_ui (bs);
110 mpz_rrandomb (x2, rands, x2n);
111 /* mpz_out_str (stdout, -16, x2); puts (""); */
113 res = mpz_perfect_square_p (x2);
117 if (res != (mpz_cmp (x2, x2t) == 0))
119 printf ("mpz_perfect_square_p and mpz_sqrt differ\n");
120 mpz_trace (" x ", x);
121 mpz_trace (" x2 ", x2);
122 mpz_trace (" x2t", x2t);
123 printf (" mpz_perfect_square_p %d\n", res);
124 printf (" mpz_sqrt %d\n", mpz_cmp (x2, x2t) == 0);
128 /* cnt += res != 0; */
130 /* printf ("%d/%d perfect squares\n", cnt, reps); */
140 main (int argc, char **argv)
148 reps = atoi (argv[1]);