- added prefix and postfix increment and decrement operators for class numeric
[ginac.git] / ginac / operators.cpp
1 /** @file operators.cpp
2  *
3  *  Implementation of GiNaC's overloaded operators. */
4
5 /*
6  *  GiNaC Copyright (C) 1999 Johannes Gutenberg University Mainz, Germany
7  *
8  *  This program is free software; you can redistribute it and/or modify
9  *  it under the terms of the GNU General Public License as published by
10  *  the Free Software Foundation; either version 2 of the License, or
11  *  (at your option) any later version.
12  *
13  *  This program is distributed in the hope that it will be useful,
14  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
15  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  *  GNU General Public License for more details.
17  *
18  *  You should have received a copy of the GNU General Public License
19  *  along with this program; if not, write to the Free Software
20  *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
21  */
22
23 #include <iostream>
24 #include <stdexcept>
25
26 #include "operators.h"
27 #include "basic.h"
28 #include "ex.h"
29 #include "numeric.h"
30 #include "power.h"
31 #include "relational.h"
32 #include "debugmsg.h"
33
34 namespace GiNaC {
35
36 // binary arithmetic operators ex with ex
37
38 ex operator+(ex const & lh, ex const & rh)
39 {
40     debugmsg("operator+(ex,ex)",LOGLEVEL_OPERATOR);
41     return lh.exadd(rh);
42 }
43
44 ex operator-(ex const & lh, ex const & rh)
45 {
46     debugmsg("operator-(ex,ex)",LOGLEVEL_OPERATOR);
47     return lh.exadd(rh.exmul(exMINUSONE()));
48 }
49
50 ex operator*(ex const & lh, ex const & rh)
51 {
52     debugmsg("operator*(ex,ex)",LOGLEVEL_OPERATOR);
53     return lh.exmul(rh);
54 }
55
56 ex operator/(ex const & lh, ex const & rh)
57 {
58     debugmsg("operator*(ex,ex)",LOGLEVEL_OPERATOR);
59     return lh.exmul(power(rh,exMINUSONE()));
60 }
61
62 ex operator%(ex const & lh, ex const & rh)
63 {
64     debugmsg("operator%(ex,ex)",LOGLEVEL_OPERATOR);
65     return lh.exncmul(rh);
66 }
67
68 /*
69
70 // binary arithmetic operators ex with numeric
71
72 ex operator+(ex const & lh, numeric const & rh)
73 {
74     debugmsg("operator+(ex,numeric)",LOGLEVEL_OPERATOR);
75     return lh+ex(rh);
76 }
77
78 ex operator-(ex const & lh, numeric const & rh)
79 {
80     debugmsg("operator-(ex,numeric)",LOGLEVEL_OPERATOR);
81     return lh-ex(rh);
82 }
83
84 ex operator*(ex const & lh, numeric const & rh)
85 {
86     debugmsg("operator*(ex,numeric)",LOGLEVEL_OPERATOR);
87     return lh*ex(rh);
88 }
89
90 ex operator/(ex const & lh, numeric const & rh)
91 {
92     debugmsg("operator/(ex,numeric)",LOGLEVEL_OPERATOR);
93     return lh/ex(rh);
94 }
95
96 ex operator%(ex const & lh, numeric const & rh)
97 {
98     debugmsg("operator%(ex,numeric)",LOGLEVEL_OPERATOR);
99     return lh%ex(rh);
100 }
101
102 // binary arithmetic operators numeric with ex
103
104 ex operator+(numeric const & lh, ex const & rh)
105 {
106     debugmsg("operator+(numeric,ex)",LOGLEVEL_OPERATOR);
107     return ex(lh)+rh;
108 }
109
110 ex operator-(numeric const & lh, ex const & rh)
111 {
112     debugmsg("operator-(numeric,ex)",LOGLEVEL_OPERATOR);
113     return ex(lh)-rh;
114 }
115
116 ex operator*(numeric const & lh, ex const & rh)
117 {
118     debugmsg("operator*(numeric,ex)",LOGLEVEL_OPERATOR);
119     return ex(lh)*rh;
120 }
121
122 ex operator/(numeric const & lh, ex const & rh)
123 {
124     debugmsg("operator/(numeric,ex)",LOGLEVEL_OPERATOR);
125     return ex(lh)/rh;
126 }
127
128 ex operator%(numeric const & lh, ex const & rh)
129 {
130     debugmsg("operator%(numeric,ex)",LOGLEVEL_OPERATOR);
131     return ex(lh)%rh;
132 }
133
134 */
135
136 // binary arithmetic operators numeric with numeric
137
138 numeric operator+(numeric const & lh, numeric const & rh)
139 {
140     debugmsg("operator+(numeric,numeric)",LOGLEVEL_OPERATOR);
141     return lh.add(rh);
142 }
143
144 numeric operator-(numeric const & lh, numeric const & rh)
145 {
146     debugmsg("operator-(numeric,numeric)",LOGLEVEL_OPERATOR);
147     return lh.sub(rh);
148 }
149
150 numeric operator*(numeric const & lh, numeric const & rh)
151 {
152     debugmsg("operator*(numeric,numeric)",LOGLEVEL_OPERATOR);
153     return lh.mul(rh);
154 }
155
156 numeric operator/(numeric const & lh, numeric const & rh)
157 {
158     debugmsg("operator/(numeric,ex)",LOGLEVEL_OPERATOR);
159     return lh.div(rh);
160 }
161
162 // binary arithmetic assignment operators with ex
163
164 ex const & operator+=(ex & lh, ex const & rh)
165 {
166     debugmsg("operator+=(ex,ex)",LOGLEVEL_OPERATOR);
167     return (lh=lh+rh);
168 }
169
170 ex const & operator-=(ex & lh, ex const & rh)
171 {
172     debugmsg("operator-=(ex,ex)",LOGLEVEL_OPERATOR);
173     return (lh=lh-rh);
174 }
175
176 ex const & operator*=(ex & lh, ex const & rh)
177 {
178     debugmsg("operator*=(ex,ex)",LOGLEVEL_OPERATOR);
179     return (lh=lh*rh);
180 }
181
182 ex const & operator/=(ex & lh, ex const & rh)
183 {
184     debugmsg("operator/=(ex,ex)",LOGLEVEL_OPERATOR);
185     return (lh=lh/rh);
186 }
187
188 ex const & operator%=(ex & lh, ex const & rh)
189 {
190     debugmsg("operator%=(ex,ex)",LOGLEVEL_OPERATOR);
191     return (lh=lh%rh);
192 }
193
194 /*
195
196 // binary arithmetic assignment operators with numeric
197
198 ex const & operator+=(ex & lh, numeric const & rh)
199 {
200     debugmsg("operator+=(ex,numeric)",LOGLEVEL_OPERATOR);
201     return (lh=lh+ex(rh));
202 }
203
204 ex const & operator-=(ex & lh, numeric const & rh)
205 {
206     debugmsg("operator-=(ex,numeric)",LOGLEVEL_OPERATOR);
207     return (lh=lh-ex(rh));
208 }
209
210 ex const & operator*=(ex & lh, numeric const & rh)
211 {
212     debugmsg("operator*=(ex,numeric)",LOGLEVEL_OPERATOR);
213     return (lh=lh*ex(rh));
214 }
215
216 ex const & operator/=(ex & lh, numeric const & rh)
217 {
218     debugmsg("operator/=(ex,numeric)",LOGLEVEL_OPERATOR);
219     return (lh=lh/ex(rh));
220 }
221
222 ex const & operator%=(ex & lh, numeric const & rh)
223 {
224     debugmsg("operator%=(ex,numeric)",LOGLEVEL_OPERATOR);
225     return (lh=lh%ex(rh));
226 }
227
228 */
229
230 // binary arithmetic assignment operators with numeric
231
232 numeric const & operator+=(numeric & lh, numeric const & rh)
233 {
234     debugmsg("operator+=(numeric,numeric)",LOGLEVEL_OPERATOR);
235     return (lh=lh.add(rh));
236 }
237
238 numeric const & operator-=(numeric & lh, numeric const & rh)
239 {
240     debugmsg("operator-=(numeric,numeric)",LOGLEVEL_OPERATOR);
241     return (lh=lh.sub(rh));
242 }
243
244 numeric const & operator*=(numeric & lh, numeric const & rh)
245 {
246     debugmsg("operator*=(numeric,numeric)",LOGLEVEL_OPERATOR);
247     return (lh=lh.mul(rh));
248 }
249
250 numeric const & operator/=(numeric & lh, numeric const & rh)
251 {
252     debugmsg("operator/=(numeric,numeric)",LOGLEVEL_OPERATOR);
253     return (lh=lh.div(rh));
254 }
255
256 // unary operators
257
258 ex operator+(ex const & lh)
259 {
260     return lh;
261 }
262
263 ex operator-(ex const & lh)
264 {
265     return exMINUSONE()*lh;
266 }
267
268 numeric operator+(numeric const & lh)
269 {
270     return lh;
271 }
272
273 numeric operator-(numeric const & lh)
274 {
275     return numMINUSONE()*lh;
276 }
277
278 /** Numeric prefix increment.  Adds 1 and returns incremented number. */
279 numeric& operator++(numeric & rh)
280 {
281     rh = rh+numONE();
282     return rh;
283 }
284
285 /** Numeric prefix decrement.  Subtracts 1 and returns decremented number. */
286 numeric& operator--(numeric & rh)
287 {
288     rh = rh-numONE();
289     return rh;
290 }
291
292 /** Numeric postfix increment.  Returns the number and leaves the original
293  *  incremented by 1. */
294 numeric operator++(numeric & lh, int)
295 {
296     numeric tmp = lh;
297     lh = lh+numONE();
298     return tmp;
299 }
300
301 /** Numeric Postfix decrement.  Returns the number and leaves the original
302  *  decremented by 1. */
303 numeric operator--(numeric & lh, int)
304 {
305     numeric tmp = lh;
306     lh = lh-numONE();
307     return tmp;
308 }
309
310 // binary relational operators ex with ex
311
312 relational operator==(ex const & lh, ex const & rh)
313 {
314     debugmsg("operator==(ex,ex)",LOGLEVEL_OPERATOR);
315     return relational(lh,rh,relational::equal);
316 }
317
318 relational operator!=(ex const & lh, ex const & rh)
319 {
320     debugmsg("operator!=(ex,ex)",LOGLEVEL_OPERATOR);
321     return relational(lh,rh,relational::not_equal);
322 }
323
324 relational operator<(ex const & lh, ex const & rh)
325 {
326     debugmsg("operator<(ex,ex)",LOGLEVEL_OPERATOR);
327     return relational(lh,rh,relational::less);
328 }
329
330 relational operator<=(ex const & lh, ex const & rh)
331 {
332     debugmsg("operator<=(ex,ex)",LOGLEVEL_OPERATOR);
333     return relational(lh,rh,relational::less_or_equal);
334 }
335
336 relational operator>(ex const & lh, ex const & rh)
337 {
338     debugmsg("operator>(ex,ex)",LOGLEVEL_OPERATOR);
339     return relational(lh,rh,relational::greater);
340 }
341
342 relational operator>=(ex const & lh, ex const & rh)
343 {
344     debugmsg("operator>=(ex,ex)",LOGLEVEL_OPERATOR);
345     return relational(lh,rh,relational::greater_or_equal);
346 }
347
348 /*
349
350 // binary relational operators ex with numeric
351
352 relational operator==(ex const & lh, numeric const & rh)
353 {
354     debugmsg("operator==(ex,numeric)",LOGLEVEL_OPERATOR);
355     return relational(lh,rh,relational::equal);
356 }
357
358 relational operator!=(ex const & lh, numeric const & rh)
359 {
360     debugmsg("operator!=(ex,numeric)",LOGLEVEL_OPERATOR);
361     return relational(lh,rh,relational::not_equal);
362 }
363
364 relational operator<(ex const & lh, numeric const & rh)
365 {
366     debugmsg("operator<(ex,numeric)",LOGLEVEL_OPERATOR);
367     return relational(lh,rh,relational::less);
368 }
369
370 relational operator<=(ex const & lh, numeric const & rh)
371 {
372     debugmsg("operator<=(ex,numeric)",LOGLEVEL_OPERATOR);
373     return relational(lh,rh,relational::less_or_equal);
374 }
375
376 relational operator>(ex const & lh, numeric const & rh)
377 {
378     debugmsg("operator>(ex,numeric)",LOGLEVEL_OPERATOR);
379     return relational(lh,rh,relational::greater);
380 }
381
382 relational operator>=(ex const & lh, numeric const & rh)
383 {
384     debugmsg("operator>=(ex,numeric)",LOGLEVEL_OPERATOR);
385     return relational(lh,rh,relational::greater_or_equal);
386 }
387
388 // binary relational operators numeric with ex
389
390 relational operator==(numeric const & lh, ex const & rh)
391 {
392     debugmsg("operator==(numeric,ex)",LOGLEVEL_OPERATOR);
393     return relational(lh,rh,relational::equal);
394 }
395
396 relational operator!=(numeric const & lh, ex const & rh)
397 {
398     debugmsg("operator!=(numeric,ex)",LOGLEVEL_OPERATOR);
399     return relational(lh,rh,relational::not_equal);
400 }
401
402 relational operator<(numeric const & lh, ex const & rh)
403 {
404     debugmsg("operator<(numeric,ex)",LOGLEVEL_OPERATOR);
405     return relational(lh,rh,relational::less);
406 }
407
408 relational operator<=(numeric const & lh, ex const & rh)
409 {
410     debugmsg("operator<=(numeric,ex)",LOGLEVEL_OPERATOR);
411     return relational(lh,rh,relational::less_or_equal);
412 }
413
414 relational operator>(numeric const & lh, ex const & rh)
415 {
416     debugmsg("operator>(numeric,ex)",LOGLEVEL_OPERATOR);
417     return relational(lh,rh,relational::greater);
418 }
419
420 relational operator>=(numeric const & lh, ex const & rh)
421 {
422     debugmsg("operator>=(numeric,ex)",LOGLEVEL_OPERATOR);
423     return relational(lh,rh,relational::greater_or_equal);
424 }
425
426 */
427
428 // input/output stream operators
429
430 ostream & operator<<(ostream & os, ex const & e)
431 {
432     e.print(os);
433     return os;
434 }
435
436 istream & operator>>(istream & is, ex & e)
437 {
438     throw(std::logic_error("input from streams not yet implemented"));
439 }
440
441 } // namespace GiNaC