]> www.ginac.de Git - cln.git/blob - src/modinteger/cl_MI_int.h
2004-01-01 Richard B. Kreckel <kreckel@ginac.de>
[cln.git] / src / modinteger / cl_MI_int.h
1 // m = 0 : Z/mZ \isomorph Z
2
3 namespace cln {
4
5 static void int_fprint (cl_heap_modint_ring* R, std::ostream& stream, const _cl_MI &x)
6 {
7         fprint(stream,R->_retract(x));
8 }
9
10 static const cl_I int_reduce_modulo (cl_heap_modint_ring* R, const cl_I& x)
11 {
12         unused R;
13         return x; // reducing modulo 0 does nothing
14 }
15
16 // This is the only case where canonhom is injective.
17 static const _cl_MI int_canonhom (cl_heap_modint_ring* R, const cl_I& x)
18 {
19         return _cl_MI(R, x);
20 }
21
22 // This is the only case where retract is surjective.
23 static const cl_I int_retract (cl_heap_modint_ring* R, const _cl_MI& x)
24 {
25         unused R;
26         return x.rep;
27 }
28
29 // This is the only case where random yields an error.
30 static const _cl_MI int_random (cl_heap_modint_ring* R, random_state& randomstate)
31 {
32         unused R;
33         unused randomstate;
34         fprint(std::cerr, "Z / 0 Z not a finite set - no equidistributed random function.\n");
35         cl_abort();
36 #if ((defined(__sparc__) || defined(__sparc64__)) && !defined(__GNUC__)) // Sun CC wants a return value
37         return _cl_MI(R, 0);
38 #endif
39 }
40
41 static const _cl_MI int_zero (cl_heap_modint_ring* R)
42 {
43         return _cl_MI(R, 0);
44 }
45
46 static cl_boolean int_zerop (cl_heap_modint_ring* R, const _cl_MI& x)
47 {
48         unused R;
49         return zerop(x.rep);
50 }
51
52 static const _cl_MI int_plus (cl_heap_modint_ring* R, const _cl_MI& x, const _cl_MI& y)
53 {
54         return _cl_MI(R, x.rep + y.rep);
55 }
56
57 static const _cl_MI int_minus (cl_heap_modint_ring* R, const _cl_MI& x, const _cl_MI& y)
58 {
59         return _cl_MI(R, x.rep - y.rep);
60 }
61
62 static const _cl_MI int_uminus (cl_heap_modint_ring* R, const _cl_MI& x)
63 {
64         return _cl_MI(R, - x.rep);
65 }
66
67 static const _cl_MI int_one (cl_heap_modint_ring* R)
68 {
69         return _cl_MI(R, 1);
70 }
71
72 static const _cl_MI int_mul (cl_heap_modint_ring* R, const _cl_MI& x, const _cl_MI& y)
73 {
74         return _cl_MI(R, x.rep * y.rep);
75 }
76
77 static const _cl_MI int_square (cl_heap_modint_ring* R, const _cl_MI& x)
78 {
79         return _cl_MI(R, square(x.rep));
80 }
81
82 static const cl_MI_x int_recip (cl_heap_modint_ring* R, const _cl_MI& x)
83 {
84         var const cl_I& xr = x.rep;
85         if (eq(xr,1) || eq(xr,-1)) { return cl_MI(R,x); }
86         if (zerop(xr)) { cl_error_division_by_0(); }
87         return cl_notify_composite(R,xr);
88 }
89
90 static const cl_MI_x int_div (cl_heap_modint_ring* R, const _cl_MI& x, const _cl_MI& y)
91 {
92         var const cl_I& yr = y.rep;
93         if (eq(yr,1)) { return cl_MI(R,x.rep); }
94         if (eq(yr,-1)) { return cl_MI(R,-x.rep); }
95         if (zerop(yr)) { cl_error_division_by_0(); }
96         return cl_notify_composite(R,yr);
97 }
98
99 static const _cl_MI int_expt_pos (cl_heap_modint_ring* R, const _cl_MI& x, const cl_I& y)
100 {
101         return _cl_MI(R, expt_pos(x.rep,y));
102 }
103
104 static const cl_MI_x int_expt (cl_heap_modint_ring* R, const _cl_MI& x, const cl_I& y)
105 {
106         if (eq(x.rep,1)) { return cl_MI(R,1); }
107         if (eq(x.rep,-1)) { return cl_MI(R,evenp(y)?1:-1); }
108         if (!minusp(y)) {
109                 if (zerop(y))
110                         return cl_MI(R,1);
111                 else
112                         return cl_MI(R,expt_pos(x.rep,y));
113         }
114         // y < 0, x nonunit.
115         if (zerop(x.rep)) { cl_error_division_by_0(); }
116         return cl_notify_composite(R,x.rep);
117 }
118
119 static cl_modint_setops int_setops = {
120         int_fprint,
121         modint_equal,
122         int_random
123 };
124 static cl_modint_addops int_addops = {
125         int_zero,
126         int_zerop,
127         int_plus,
128         int_minus,
129         int_uminus
130 };
131 static cl_modint_mulops int_mulops = {
132         int_one,
133         int_canonhom,
134         int_mul,
135         int_square,
136         int_expt_pos,
137         int_recip,
138         int_div,
139         int_expt,
140         int_reduce_modulo,
141         int_retract
142 };
143
144 class cl_heap_modint_ring_int : public cl_heap_modint_ring {
145         SUBCLASS_cl_heap_modint_ring()
146 public:
147         // Constructor.
148         cl_heap_modint_ring_int () : cl_heap_modint_ring (0, &int_setops, &int_addops, &int_mulops) {}
149         // Virtual destructor.
150         ~cl_heap_modint_ring_int () {}
151 };
152
153 }  // namespace cln