1 ;;; calc-arith.el --- arithmetic functions for Calc
3 ;; Copyright (C) 1990, 1991, 1992, 1993, 2001 Free Software Foundation, Inc.
5 ;; Author: David Gillespie <daveg@synaptics.com>
6 ;; Maintainer: Colin Walters <walters@debian.org>
8 ;; This file is part of GNU Emacs.
10 ;; GNU Emacs is distributed in the hope that it will be useful,
11 ;; but WITHOUT ANY WARRANTY. No author or distributor
12 ;; accepts responsibility to anyone for the consequences of using it
13 ;; or for whether it serves any particular purpose or works at all,
14 ;; unless he says so in writing. Refer to the GNU Emacs General Public
15 ;; License for full details.
17 ;; Everyone is granted permission to copy, modify and redistribute
18 ;; GNU Emacs, but only under the conditions described in the
19 ;; GNU Emacs General Public License. A copy of this license is
20 ;; supposed to have been given to you along with GNU Emacs so you
21 ;; can know your rights and responsibilities. It should be in a
22 ;; file named COPYING. Among other things, the copyright notice
23 ;; and this notice must be preserved on all copies.
29 ;; This file is autoloaded from calc-ext.el.
34 (defun calc-Need-calc-arith () nil
)
42 (calc-binary-op "min" 'calcFunc-min arg
'(var inf var-inf
))))
47 (calc-binary-op "max" 'calcFunc-max arg
'(neg (var inf var-inf
)))))
52 (calc-unary-op "abs" 'calcFunc-abs arg
)))
55 (defun calc-idiv (arg)
58 (calc-binary-op "\\" 'calcFunc-idiv arg
1)))
61 (defun calc-floor (arg)
65 (if (calc-is-hyperbolic)
66 (calc-unary-op "ceil" 'calcFunc-fceil arg
)
67 (calc-unary-op "ceil" 'calcFunc-ceil arg
))
68 (if (calc-is-hyperbolic)
69 (calc-unary-op "flor" 'calcFunc-ffloor arg
)
70 (calc-unary-op "flor" 'calcFunc-floor arg
)))))
72 (defun calc-ceiling (arg)
77 (defun calc-round (arg)
81 (if (calc-is-hyperbolic)
82 (calc-unary-op "trnc" 'calcFunc-ftrunc arg
)
83 (calc-unary-op "trnc" 'calcFunc-trunc arg
))
84 (if (calc-is-hyperbolic)
85 (calc-unary-op "rond" 'calcFunc-fround arg
)
86 (calc-unary-op "rond" 'calcFunc-round arg
)))))
88 (defun calc-trunc (arg)
93 (defun calc-mant-part (arg)
96 (calc-unary-op "mant" 'calcFunc-mant arg
)))
98 (defun calc-xpon-part (arg)
101 (calc-unary-op "xpon" 'calcFunc-xpon arg
)))
103 (defun calc-scale-float (arg)
106 (calc-binary-op "scal" 'calcFunc-scf arg
)))
108 (defun calc-abssqr (arg)
111 (calc-unary-op "absq" 'calcFunc-abssqr arg
)))
113 (defun calc-sign (arg)
116 (calc-unary-op "sign" 'calcFunc-sign arg
)))
118 (defun calc-increment (arg)
121 (calc-enter-result 1 "incr" (list 'calcFunc-incr
(calc-top-n 1) arg
))))
123 (defun calc-decrement (arg)
126 (calc-enter-result 1 "decr" (list 'calcFunc-decr
(calc-top-n 1) arg
))))
129 (defun math-abs-approx (a)
135 (math-add (math-abs (nth 1 a
)) (math-abs (nth 2 a
))))
139 (math-abs-approx (nth 1 a
)))
141 (math-max (math-abs (nth 2 a
)) (math-abs (nth 3 a
))))
145 (math-reduce-vec 'math-add-abs-approx a
))
146 ((eq (car a
) 'calcFunc-abs
)
150 (defun math-add-abs-approx (a b
)
151 (math-add (math-abs-approx a
) (math-abs-approx b
)))
156 (defvar math-decls-cache-tag nil
)
157 (defvar math-decls-cache nil
)
158 (defvar math-decls-all nil
)
160 ;;; Math-decls-cache is an a-list where each entry is a list of the form:
161 ;;; (VAR TYPES RANGE)
162 ;;; where VAR is a variable name (with var- prefix) or function name;
163 ;;; TYPES is a list of type symbols (any, int, frac, ...)
164 ;;; RANGE is a sorted vector of intervals describing the range.
166 (defun math-setup-declarations ()
167 (or (eq math-decls-cache-tag
(calc-var-value 'var-Decls
))
168 (let ((p (calc-var-value 'var-Decls
))
170 (setq math-decls-cache-tag p
171 math-decls-cache nil
)
172 (and (eq (car-safe p
) 'vec
)
173 (while (setq p
(cdr p
))
174 (and (eq (car-safe (car p
)) 'vec
)
175 (setq vec
(nth 2 (car p
)))
177 (let ((v (nth 1 (car p
))))
178 (setq type nil range nil
)
179 (or (eq (car-safe vec
) 'vec
)
180 (setq vec
(list 'vec vec
)))
181 (while (and (setq vec
(cdr vec
))
182 (not (Math-objectp (car vec
))))
183 (and (eq (car-safe (car vec
)) 'var
)
184 (let ((st (assq (nth 1 (car vec
))
186 (cond (st (setq type
(append type st
)))
187 ((eq (nth 1 (car vec
)) 'pos
)
188 (setq type
(append type
191 '(intv 1 0 (var inf var-inf
))))
192 ((eq (nth 1 (car vec
)) 'nonneg
)
193 (setq type
(append type
197 (var inf var-inf
))))))))
199 (setq type
(append type
'(real number
))
200 range
(math-prepare-set (cons 'vec vec
))))
201 (setq type
(list type range
))
202 (or (eq (car-safe v
) 'vec
)
203 (setq v
(list 'vec v
)))
204 (while (setq v
(cdr v
))
205 (if (or (eq (car-safe (car v
)) 'var
)
206 (not (Math-primp (car v
))))
207 (setq math-decls-cache
208 (cons (cons (if (eq (car (car v
)) 'var
)
212 math-decls-cache
)))))
214 (setq math-decls-all
(assq 'var-All math-decls-cache
)))))
216 (defvar math-super-types
217 '((int numint rat real number
)
219 (frac rat real number
)
229 (defun math-known-scalarp (a &optional assume-scalar
)
230 (math-setup-declarations)
231 (if (if calc-matrix-mode
232 (eq calc-matrix-mode
'scalar
)
234 (not (math-check-known-matrixp a
))
235 (math-check-known-scalarp a
)))
237 (defun math-known-matrixp (a)
238 (and (not (Math-scalarp a
))
239 (not (math-known-scalarp a t
))))
241 ;;; Try to prove that A is a scalar (i.e., a non-vector).
242 (defun math-check-known-scalarp (a)
243 (cond ((Math-objectp a
) t
)
244 ((memq (car a
) math-scalar-functions
)
246 ((memq (car a
) math-real-scalar-functions
)
248 ((memq (car a
) math-scalar-if-args-functions
)
249 (while (and (setq a
(cdr a
))
250 (math-check-known-scalarp (car a
))))
253 (math-check-known-scalarp (nth 1 a
)))
254 ((math-const-var a
) t
)
256 (let ((decl (if (eq (car a
) 'var
)
257 (or (assq (nth 2 a
) math-decls-cache
)
259 (assq (car a
) math-decls-cache
))))
260 (memq 'scalar
(nth 1 decl
))))))
262 ;;; Try to prove that A is *not* a scalar.
263 (defun math-check-known-matrixp (a)
264 (cond ((Math-objectp a
) nil
)
265 ((memq (car a
) math-nonscalar-functions
)
267 ((memq (car a
) math-scalar-if-args-functions
)
268 (while (and (setq a
(cdr a
))
269 (not (math-check-known-matrixp (car a
)))))
272 (math-check-known-matrixp (nth 1 a
)))
273 ((math-const-var a
) nil
)
275 (let ((decl (if (eq (car a
) 'var
)
276 (or (assq (nth 2 a
) math-decls-cache
)
278 (assq (car a
) math-decls-cache
))))
279 (memq 'vector
(nth 1 decl
))))))
282 ;;; Try to prove that A is a real (i.e., not complex).
283 (defun math-known-realp (a)
284 (< (math-possible-signs a
) 8))
286 ;;; Try to prove that A is real and positive.
287 (defun math-known-posp (a)
288 (eq (math-possible-signs a
) 4))
290 ;;; Try to prove that A is real and negative.
291 (defun math-known-negp (a)
292 (eq (math-possible-signs a
) 1))
294 ;;; Try to prove that A is real and nonnegative.
295 (defun math-known-nonnegp (a)
296 (memq (math-possible-signs a
) '(2 4 6)))
298 ;;; Try to prove that A is real and nonpositive.
299 (defun math-known-nonposp (a)
300 (memq (math-possible-signs a
) '(1 2 3)))
302 ;;; Try to prove that A is nonzero.
303 (defun math-known-nonzerop (a)
304 (memq (math-possible-signs a
) '(1 4 5 8 9 12 13)))
306 ;;; Return true if A is negative, or looks negative but we don't know.
307 (defun math-guess-if-neg (a)
308 (let ((sgn (math-possible-signs a
)))
309 (if (memq sgn
'(1 3))
311 (if (memq sgn
'(2 4 6))
313 (math-looks-negp a
)))))
315 ;;; Find the possible signs of A, assuming A is a number of some kind.
316 ;;; Returns an integer with bits: 1 may be negative,
318 ;;; 4 may be positive,
319 ;;; 8 may be nonreal.
321 (defun math-possible-signs (a &optional origin
)
322 (cond ((Math-objectp a
)
323 (if origin
(setq a
(math-sub a origin
)))
324 (cond ((Math-posp a
) 4)
328 (cond ((Math-zerop (nth 2 a
)) 6)
329 ((Math-zerop (nth 3 a
)) 3)
332 (if (math-known-realp (nth 1 a
)) 7 15))
334 ((memq (car a
) '(+ -
))
335 (cond ((Math-realp (nth 1 a
))
338 (math-possible-signs (nth 2 a
)
340 (math-add origin
(nth 1 a
))
342 (math-possible-signs (nth 2 a
)
344 (math-sub origin
(nth 1 a
))
345 (math-neg (nth 1 a
))))))
346 ((Math-realp (nth 2 a
))
347 (let ((org (if (eq (car a
) '-
)
349 (math-neg (nth 2 a
)))))
350 (math-possible-signs (nth 1 a
)
352 (math-add origin org
)
355 (let ((s1 (math-possible-signs (nth 1 a
) origin
))
356 (s2 (math-possible-signs (nth 2 a
))))
357 (if (eq (car a
) '-
) (setq s2
(math-neg-signs s2
)))
358 (cond ((eq s1 s2
) s1
)
363 ((and (eq s1
4) (eq s2
6)) 4)
364 ((and (eq s2
4) (eq s1
6)) 4)
365 ((and (eq s1
1) (eq s2
3)) 1)
366 ((and (eq s2
1) (eq s1
3)) 1)
369 (math-neg-signs (math-possible-signs
371 (and origin
(math-neg origin
)))))
372 ((and origin
(Math-zerop origin
) (setq origin nil
)
374 ((and (or (eq (car a
) '*)
375 (and (eq (car a
) '/) origin
))
376 (Math-realp (nth 1 a
)))
377 (let ((s (if (eq (car a
) '*)
378 (if (Math-zerop (nth 1 a
))
379 (math-possible-signs 0 origin
)
380 (math-possible-signs (nth 2 a
)
381 (math-div (or origin
0)
384 (math-possible-signs (nth 2 a
)
387 (if (Math-negp (nth 1 a
)) (math-neg-signs s
) s
)))
388 ((and (memq (car a
) '(* /)) (Math-realp (nth 2 a
)))
389 (let ((s (math-possible-signs (nth 1 a
)
391 (math-mul (or origin
0) (nth 2 a
))
392 (math-div (or origin
0) (nth 2 a
))))))
393 (if (Math-negp (nth 2 a
)) (math-neg-signs s
) s
)))
396 (while (and (setq a
(cdr a
)) (< signs
15))
397 (setq signs
(logior signs
(math-possible-signs
402 ((memq (car a
) '(* /))
403 (let ((s1 (math-possible-signs (nth 1 a
)))
404 (s2 (math-possible-signs (nth 2 a
))))
407 ((and (eq (car a
) '/) (memq s2
'(2 3 6 7))) 15)
409 (logior (if (memq s1
'(4 5 6 7)) s2
0)
410 (if (memq s1
'(2 3 6 7)) 2 0)
411 (if (memq s1
'(1 3 5 7))
412 (math-neg-signs s2
) 0))))))
414 (let ((s1 (math-possible-signs (nth 1 a
)))
415 (s2 (math-possible-signs (nth 2 a
))))
419 ((eq s1
2) (if (eq s2
4) 2 15))
420 ((eq s2
2) (if (memq s1
'(1 5)) 2 15))
421 ((Math-integerp (nth 2 a
))
422 (if (math-evenp (nth 2 a
))
423 (if (memq s1
'(3 6 7)) 6 4)
425 ((eq s1
6) (if (eq s2
4) 6 15))
428 (let ((s2 (math-possible-signs (nth 2 a
))))
434 ((and (memq (car a
) '(calcFunc-abs calcFunc-abssqr
))
436 (let ((s1 (math-possible-signs (nth 1 a
))))
438 ((memq s1
'(1 4 5)) 4)
440 ((and (eq (car a
) 'calcFunc-exp
) (= (length a
) 2))
441 (let ((s1 (math-possible-signs (nth 1 a
))))
444 (if (or (not origin
) (math-negp origin
))
446 (setq origin
(math-sub (or origin
0) 1))
447 (if (Math-zerop origin
) (setq origin nil
))
449 ((or (and (memq (car a
) '(calcFunc-ln calcFunc-log10
))
451 (and (eq (car a
) 'calcFunc-log
)
453 (math-known-posp (nth 2 a
))))
454 (if (math-known-nonnegp (nth 1 a
))
455 (math-possible-signs (nth 1 a
) 1)
457 ((and (eq (car a
) 'calcFunc-sqrt
) (= (length a
) 2))
458 (let ((s1 (math-possible-signs (nth 1 a
))))
459 (if (memq s1
'(2 4 6)) s1
15)))
460 ((memq (car a
) math-nonnegative-functions
) 6)
461 ((memq (car a
) math-positive-functions
) 4)
462 ((memq (car a
) math-real-functions
) 7)
463 ((memq (car a
) math-real-scalar-functions
) 7)
464 ((and (memq (car a
) math-real-if-arg-functions
)
466 (if (math-known-realp (nth 1 a
)) 7 15)))))
470 (if (Math-posp origin
)
471 (if (memq sign
'(1 2 3 8 9 10 11)) 1 7)
472 (if (memq sign
'(2 4 6 8 10 12 14)) 4 7)))
475 (cond ((eq (nth 2 a
) 'var-pi
)
477 (math-possible-signs (math-pi) origin
)
479 ((eq (nth 2 a
) 'var-e
)
481 (math-possible-signs (math-e) origin
)
483 ((eq (nth 2 a
) 'var-inf
) 4)
484 ((eq (nth 2 a
) 'var-uinf
) 13)
485 ((eq (nth 2 a
) 'var-i
) 8)
488 (math-setup-declarations)
489 (let ((decl (if (eq (car a
) 'var
)
490 (or (assq (nth 2 a
) math-decls-cache
)
492 (assq (car a
) math-decls-cache
))))
494 (memq 'int
(nth 1 decl
))
495 (not (Math-num-integerp origin
)))
498 (math-possible-signs (nth 2 decl
) origin
)
499 (if (memq 'real
(nth 1 decl
))
503 (defun math-neg-signs (s1)
505 (+ 8 (math-neg-signs (- s1
8)))
506 (+ (if (memq s1
'(1 3 5 7)) 4 0)
507 (if (memq s1
'(2 3 6 7)) 2 0)
508 (if (memq s1
'(4 5 6 7)) 1 0))))
511 ;;; Try to prove that A is an integer.
512 (defun math-known-integerp (a)
513 (eq (math-possible-types a
) 1))
515 (defun math-known-num-integerp (a)
516 (<= (math-possible-types a t
) 3))
518 (defun math-known-imagp (a)
519 (= (math-possible-types a
) 16))
522 ;;; Find the possible types of A.
523 ;;; Returns an integer with bits: 1 may be integer.
524 ;;; 2 may be integer-valued float.
525 ;;; 4 may be fraction.
526 ;;; 8 may be non-integer-valued float.
527 ;;; 16 may be imaginary.
528 ;;; 32 may be non-real, non-imaginary.
529 ;;; Real infinities count as integers for the purposes of this function.
530 (defun math-possible-types (a &optional num
)
531 (cond ((Math-objectp a
)
532 (cond ((Math-integerp a
) (if num
3 1))
533 ((Math-messy-integerp a
) (if num
3 2))
534 ((eq (car a
) 'frac
) (if num
12 4))
535 ((eq (car a
) 'float
) (if num
12 8))
537 (if (equal (nth 2 a
) (nth 3 a
))
538 (math-possible-types (nth 2 a
))
541 (if (math-known-realp (nth 1 a
)) 15 63))
543 (if (math-zerop (nth 1 a
)) 16 32))
545 (if (or (Math-equal (nth 2 a
) (math-quarter-circle nil
))
546 (Math-equal (nth 2 a
)
547 (math-neg (math-quarter-circle nil
))))
551 (let* ((t1 (math-possible-types (nth 1 a
) num
))
552 (t2 (math-possible-types (nth 2 a
) num
))
553 (t12 (logior t1 t2
)))
555 (if (> (logand t12
10) 0)
557 (if (or (= t1
4) (= t2
4) calc-prefer-frac
)
563 (if (< t2
16) 16 31))
568 ((memq (car a
) '(+ -
* %
))
569 (let* ((t1 (math-possible-types (nth 1 a
) num
))
570 (t2 (math-possible-types (nth 2 a
) num
))
571 (t12 (logior t1 t2
)))
573 (setq t1
(logand t1
15) t2
(logand t2
15) t12
(logand t12
15)))
575 (let ((mask (if (<= t12
3)
577 (if (and (or (and (<= t1
3) (= (logand t2
3) 0))
578 (and (<= t2
3) (= (logand t1
3) 0)))
579 (memq (car a
) '(+ -
)))
584 (logior (if (and (> (logand t1
5) 0) (> (logand t2
5) 0))
586 (if (> (logand t12
10) 0)
592 (if (< t2
16) 16 31))
597 (if (or (and (= t1
16) (< t2
16))
598 (and (= t2
16) (< t1
16))) 32 63)))
601 (math-possible-types (nth 1 a
)))
603 (let* ((t1 (math-possible-types (nth 1 a
) num
))
604 (t2 (math-possible-types (nth 2 a
) num
))
605 (t12 (logior t1 t2
)))
606 (if (and (<= t2
3) (math-known-nonnegp (nth 2 a
)) (< t1
16))
607 (let ((mask (logior (if (> (logand t1
3) 0) 1 0)
609 (if (> (logand t1
12) 0) 5 0))))
612 (logior (if (and (> (logand t1
5) 0) (> (logand t2
5) 0))
614 (if (> (logand t12
10) 0)
616 (if (and (math-known-nonnegp (nth 1 a
))
617 (math-known-posp (nth 2 a
)))
620 ((eq (car a
) 'calcFunc-sqrt
)
621 (let ((t1 (math-possible-signs (nth 1 a
))))
622 (logior (if (> (logand t1
2) 0) 3 0)
623 (if (> (logand t1
1) 0) 16 0)
624 (if (> (logand t1
4) 0) 15 0)
625 (if (> (logand t1
8) 0) 32 0))))
628 (while (and (setq a
(cdr a
)) (< types
63))
629 (setq types
(logior types
(math-possible-types (car a
) t
))))
631 ((or (memq (car a
) math-integer-functions
)
632 (and (memq (car a
) math-rounding-functions
)
633 (math-known-nonnegp (or (nth 2 a
) 0))))
635 ((or (memq (car a
) math-num-integer-functions
)
636 (and (memq (car a
) math-float-rounding-functions
)
637 (math-known-nonnegp (or (nth 2 a
) 0))))
639 ((eq (car a
) 'calcFunc-frac
)
641 ((and (eq (car a
) 'calcFunc-float
) (= (length a
) 2))
642 (let ((t1 (math-possible-types (nth 1 a
))))
643 (logior (if (> (logand t1
3) 0) 2 0)
644 (if (> (logand t1
12) 0) 8 0)
646 ((and (memq (car a
) '(calcFunc-abs calcFunc-abssqr
))
648 (let ((t1 (math-possible-types (nth 1 a
))))
653 (cond ((memq (nth 2 a
) '(var-e var-pi var-phi var-gamma
)) 8)
654 ((eq (nth 2 a
) 'var-inf
) 1)
655 ((eq (nth 2 a
) 'var-i
) 16)
658 (math-setup-declarations)
659 (let ((decl (if (eq (car a
) 'var
)
660 (or (assq (nth 2 a
) math-decls-cache
)
662 (assq (car a
) math-decls-cache
))))
663 (cond ((memq 'int
(nth 1 decl
))
665 ((memq 'numint
(nth 1 decl
))
667 ((memq 'frac
(nth 1 decl
))
669 ((memq 'rat
(nth 1 decl
))
671 ((memq 'float
(nth 1 decl
))
674 (math-possible-types (nth 2 decl
)))
675 ((memq 'real
(nth 1 decl
))
679 (defun math-known-evenp (a)
680 (cond ((Math-integerp a
)
682 ((Math-messy-integerp a
)
684 (math-evenp (math-trunc a
))))
686 (if (math-known-evenp (nth 1 a
))
687 (math-known-num-integerp (nth 2 a
))
688 (if (math-known-num-integerp (nth 1 a
))
689 (math-known-evenp (nth 2 a
)))))
690 ((memq (car a
) '(+ -
))
691 (or (and (math-known-evenp (nth 1 a
))
692 (math-known-evenp (nth 2 a
)))
693 (and (math-known-oddp (nth 1 a
))
694 (math-known-oddp (nth 2 a
)))))
696 (math-known-evenp (nth 1 a
)))))
698 (defun math-known-oddp (a)
699 (cond ((Math-integerp a
)
701 ((Math-messy-integerp a
)
702 (and (<= (nth 2 a
) 0)
703 (math-oddp (math-trunc a
))))
704 ((memq (car a
) '(+ -
))
705 (or (and (math-known-evenp (nth 1 a
))
706 (math-known-oddp (nth 2 a
)))
707 (and (math-known-oddp (nth 1 a
))
708 (math-known-evenp (nth 2 a
)))))
710 (math-known-oddp (nth 1 a
)))))
713 (defun calcFunc-dreal (expr)
714 (let ((types (math-possible-types expr
)))
716 (if (= (logand types
15) 0) 0
717 (math-reject-arg expr
'realp
'quiet
)))))
719 (defun calcFunc-dimag (expr)
720 (let ((types (math-possible-types expr
)))
722 (if (= (logand types
16) 0) 0
723 (math-reject-arg expr
"Expected an imaginary number")))))
725 (defun calcFunc-dpos (expr)
726 (let ((signs (math-possible-signs expr
)))
728 (if (memq signs
'(1 2 3)) 0
729 (math-reject-arg expr
'posp
'quiet
)))))
731 (defun calcFunc-dneg (expr)
732 (let ((signs (math-possible-signs expr
)))
734 (if (memq signs
'(2 4 6)) 0
735 (math-reject-arg expr
'negp
'quiet
)))))
737 (defun calcFunc-dnonneg (expr)
738 (let ((signs (math-possible-signs expr
)))
739 (if (memq signs
'(2 4 6)) 1
741 (math-reject-arg expr
'posp
'quiet
)))))
743 (defun calcFunc-dnonzero (expr)
744 (let ((signs (math-possible-signs expr
)))
745 (if (memq signs
'(1 4 5 8 9 12 13)) 1
747 (math-reject-arg expr
'nonzerop
'quiet
)))))
749 (defun calcFunc-dint (expr)
750 (let ((types (math-possible-types expr
)))
752 (if (= (logand types
1) 0) 0
753 (math-reject-arg expr
'integerp
'quiet
)))))
755 (defun calcFunc-dnumint (expr)
756 (let ((types (math-possible-types expr t
)))
758 (if (= (logand types
3) 0) 0
759 (math-reject-arg expr
'integerp
'quiet
)))))
761 (defun calcFunc-dnatnum (expr)
762 (let ((res (calcFunc-dint expr
)))
764 (calcFunc-dnonneg expr
)
767 (defun calcFunc-deven (expr)
768 (if (math-known-evenp expr
)
770 (if (or (math-known-oddp expr
)
771 (= (logand (math-possible-types expr
) 3) 0))
773 (math-reject-arg expr
"Can't tell if expression is odd or even"))))
775 (defun calcFunc-dodd (expr)
776 (if (math-known-oddp expr
)
778 (if (or (math-known-evenp expr
)
779 (= (logand (math-possible-types expr
) 3) 0))
781 (math-reject-arg expr
"Can't tell if expression is odd or even"))))
783 (defun calcFunc-drat (expr)
784 (let ((types (math-possible-types expr
)))
785 (if (memq types
'(1 4 5)) 1
786 (if (= (logand types
5) 0) 0
787 (math-reject-arg expr
"Rational number expected")))))
789 (defun calcFunc-drange (expr)
790 (math-setup-declarations)
792 (if (Math-realp expr
)
794 (if (eq (car-safe expr
) 'intv
)
796 (if (eq (car-safe expr
) 'var
)
797 (setq range
(nth 2 (or (assq (nth 2 expr
) math-decls-cache
)
799 (setq range
(nth 2 (assq (car-safe expr
) math-decls-cache
))))
801 (math-clean-set (copy-sequence range
))
802 (setq range
(math-possible-signs expr
))
805 (intv 2 (neg (var inf var-inf
)) 0)
807 (intv 3 (neg (var inf var-inf
)) 0)
808 (intv 1 0 (var inf var-inf
))
809 (vec (intv 2 (neg (var inf var-inf
)) 0)
810 (intv 1 0 (var inf var-inf
)))
811 (intv 3 0 (var inf var-inf
))
812 (intv 3 (neg (var inf var-inf
)) (var inf var-inf
))] range
)
813 (math-reject-arg expr
'realp
'quiet
)))))))
815 (defun calcFunc-dscalar (a)
816 (if (math-known-scalarp a
) 1
817 (if (math-known-matrixp a
) 0
818 (math-reject-arg a
'objectp
'quiet
))))
821 ;;; The following lists are not exhaustive.
822 (defvar math-scalar-functions
'(calcFunc-det
823 calcFunc-cnorm calcFunc-rnorm
824 calcFunc-vlen calcFunc-vcount
825 calcFunc-vsum calcFunc-vprod
826 calcFunc-vmin calcFunc-vmax
))
828 (defvar math-nonscalar-functions
'(vec calcFunc-idn calcFunc-diag
829 calcFunc-cvec calcFunc-index
832 calcFunc-cons calcFunc-rcons
833 calcFunc-tail calcFunc-rhead
))
835 (defvar math-scalar-if-args-functions
'(+ -
* / neg
))
837 (defvar math-real-functions
'(calcFunc-arg
838 calcFunc-re calcFunc-im
839 calcFunc-floor calcFunc-ceil
840 calcFunc-trunc calcFunc-round
841 calcFunc-rounde calcFunc-roundu
842 calcFunc-ffloor calcFunc-fceil
843 calcFunc-ftrunc calcFunc-fround
844 calcFunc-frounde calcFunc-froundu
))
846 (defvar math-positive-functions
'())
848 (defvar math-nonnegative-functions
'(calcFunc-cnorm calcFunc-rnorm
849 calcFunc-vlen calcFunc-vcount
))
851 (defvar math-real-scalar-functions
'(% calcFunc-idiv calcFunc-abs
852 calcFunc-choose calcFunc-perm
853 calcFunc-eq calcFunc-neq
854 calcFunc-lt calcFunc-gt
855 calcFunc-leq calcFunc-geq
857 calcFunc-max calcFunc-min
))
859 (defvar math-real-if-arg-functions
'(calcFunc-sin calcFunc-cos
860 calcFunc-tan calcFunc-arctan
861 calcFunc-sinh calcFunc-cosh
862 calcFunc-tanh calcFunc-exp
863 calcFunc-gamma calcFunc-fact
))
865 (defvar math-integer-functions
'(calcFunc-idiv
866 calcFunc-isqrt calcFunc-ilog
867 calcFunc-vlen calcFunc-vcount
))
869 (defvar math-num-integer-functions
'())
871 (defvar math-rounding-functions
'(calcFunc-floor
873 calcFunc-round calcFunc-trunc
874 calcFunc-rounde calcFunc-roundu
))
876 (defvar math-float-rounding-functions
'(calcFunc-ffloor
878 calcFunc-fround calcFunc-ftrunc
879 calcFunc-frounde calcFunc-froundu
))
881 (defvar math-integer-if-args-functions
'(+ -
* % neg calcFunc-abs
882 calcFunc-min calcFunc-max
883 calcFunc-choose calcFunc-perm
))
888 (defsubst calcFunc-neg
(a)
889 (math-normalize (list 'neg a
)))
891 (defun math-neg-fancy (a)
892 (cond ((eq (car a
) 'polar
)
895 (if (math-posp (nth 2 a
))
896 (math-sub (nth 2 a
) (math-half-circle nil
))
897 (math-add (nth 2 a
) (math-half-circle nil
)))))
899 (if (math-zerop (nth 1 a
))
901 (list 'mod
(math-sub (nth 2 a
) (nth 1 a
)) (nth 2 a
))))
903 (list 'sdev
(math-neg (nth 1 a
)) (nth 2 a
)))
905 (math-make-intv (aref [0 2 1 3] (nth 1 a
))
907 (math-neg (nth 2 a
))))
908 ((and math-simplify-only
909 (not (equal a math-simplify-only
)))
912 (math-sub (math-neg (nth 1 a
)) (nth 2 a
)))
914 (math-sub (nth 2 a
) (nth 1 a
)))
915 ((and (memq (car a
) '(* /))
916 (math-okay-neg (nth 1 a
)))
917 (list (car a
) (math-neg (nth 1 a
)) (nth 2 a
)))
918 ((and (memq (car a
) '(* /))
919 (math-okay-neg (nth 2 a
)))
920 (list (car a
) (nth 1 a
) (math-neg (nth 2 a
))))
921 ((and (memq (car a
) '(* /))
922 (or (math-objectp (nth 1 a
))
923 (and (eq (car (nth 1 a
)) '*)
924 (math-objectp (nth 1 (nth 1 a
))))))
925 (list (car a
) (math-neg (nth 1 a
)) (nth 2 a
)))
926 ((and (eq (car a
) '/)
927 (or (math-objectp (nth 2 a
))
928 (and (eq (car (nth 2 a
)) '*)
929 (math-objectp (nth 1 (nth 2 a
))))))
930 (list (car a
) (nth 1 a
) (math-neg (nth 2 a
))))
931 ((and (eq (car a
) 'var
) (memq (nth 2 a
) '(var-uinf var-nan
)))
937 (defun math-okay-neg (a)
938 (or (math-looks-negp a
)
939 (eq (car-safe a
) '-
)))
941 (defun math-neg-float (a)
942 (list 'float
(Math-integer-neg (nth 1 a
)) (nth 2 a
)))
945 (defun calcFunc-add (&rest rest
)
947 (let ((a (car rest
)))
948 (while (setq rest
(cdr rest
))
949 (setq a
(list '+ a
(car rest
))))
953 (defun calcFunc-sub (&rest rest
)
955 (let ((a (car rest
)))
956 (while (setq rest
(cdr rest
))
957 (setq a
(list '- a
(car rest
))))
961 (defun math-add-objects-fancy (a b
)
962 (cond ((and (Math-numberp a
) (Math-numberp b
))
963 (let ((aa (math-complex a
))
964 (bb (math-complex b
)))
966 (let ((res (list 'cplx
967 (math-add (nth 1 aa
) (nth 1 bb
))
968 (math-add (nth 2 aa
) (nth 2 bb
)))))
969 (if (math-want-polar a b
)
972 ((or (Math-vectorp a
) (Math-vectorp b
))
973 (math-map-vec-2 'math-add a b
))
974 ((eq (car-safe a
) 'sdev
)
975 (if (eq (car-safe b
) 'sdev
)
976 (math-make-sdev (math-add (nth 1 a
) (nth 1 b
))
977 (math-hypot (nth 2 a
) (nth 2 b
)))
978 (and (or (Math-scalarp b
)
979 (not (Math-objvecp b
)))
980 (math-make-sdev (math-add (nth 1 a
) b
) (nth 2 a
)))))
981 ((and (eq (car-safe b
) 'sdev
)
983 (not (Math-objvecp a
))))
984 (math-make-sdev (math-add a
(nth 1 b
)) (nth 2 b
)))
985 ((eq (car-safe a
) 'intv
)
986 (if (eq (car-safe b
) 'intv
)
987 (math-make-intv (logior (logand (nth 1 a
) (nth 1 b
))
989 '(neg (var inf var-inf
)))
990 (logand (nth 1 a
) 2) 0)
992 '(neg (var inf var-inf
)))
993 (logand (nth 1 b
) 2) 0)
994 (if (equal (nth 3 a
) '(var inf var-inf
))
995 (logand (nth 1 a
) 1) 0)
996 (if (equal (nth 3 b
) '(var inf var-inf
))
997 (logand (nth 1 b
) 1) 0))
998 (math-add (nth 2 a
) (nth 2 b
))
999 (math-add (nth 3 a
) (nth 3 b
)))
1000 (and (or (Math-anglep b
)
1002 (not (Math-objvecp b
)))
1003 (math-make-intv (nth 1 a
)
1004 (math-add (nth 2 a
) b
)
1005 (math-add (nth 3 a
) b
)))))
1006 ((and (eq (car-safe b
) 'intv
)
1009 (not (Math-objvecp a
))))
1010 (math-make-intv (nth 1 b
)
1011 (math-add a
(nth 2 b
))
1012 (math-add a
(nth 3 b
))))
1013 ((eq (car-safe a
) 'date
)
1014 (cond ((eq (car-safe b
) 'date
)
1015 (math-add (nth 1 a
) (nth 1 b
)))
1016 ((eq (car-safe b
) 'hms
)
1017 (let ((parts (math-date-parts (nth 1 a
))))
1019 (math-add (car parts
) ; this minimizes roundoff
1021 (math-add (nth 1 parts
)
1024 (math-mul (nth 1 b
) 3600)
1025 (math-add (math-mul (nth 2 b
) 60)
1029 (list 'date
(math-add (nth 1 a
) b
)))
1031 ((eq (car-safe b
) 'date
)
1032 (math-add-objects-fancy b a
))
1033 ((and (eq (car-safe a
) 'mod
)
1034 (eq (car-safe b
) 'mod
)
1035 (equal (nth 2 a
) (nth 2 b
)))
1036 (math-make-mod (math-add (nth 1 a
) (nth 1 b
)) (nth 2 a
)))
1037 ((and (eq (car-safe a
) 'mod
)
1039 (math-make-mod (math-add (nth 1 a
) b
) (nth 2 a
)))
1040 ((and (eq (car-safe b
) 'mod
)
1042 (math-make-mod (math-add a
(nth 1 b
)) (nth 2 b
)))
1043 ((and (or (eq (car-safe a
) 'hms
) (eq (car-safe b
) 'hms
))
1044 (and (Math-anglep a
) (Math-anglep b
)))
1045 (or (eq (car-safe a
) 'hms
) (setq a
(math-to-hms a
)))
1046 (or (eq (car-safe b
) 'hms
) (setq b
(math-to-hms b
)))
1049 (math-neg (math-add (math-neg a
) (math-neg b
)))
1051 (let* ((s (math-add (nth 3 a
) (nth 3 b
)))
1052 (m (math-add (nth 2 a
) (nth 2 b
)))
1053 (h (math-add (nth 1 a
) (nth 1 b
))))
1055 (setq s
(math-add s
60)
1058 (setq m
(math-add m
60)
1063 (let* ((s (math-add (nth 3 a
) (nth 3 b
)))
1064 (m (math-add (nth 2 a
) (nth 2 b
)))
1065 (h (math-add (nth 1 a
) (nth 1 b
))))
1066 (list 'hms h m s
))))))
1067 (t (calc-record-why "*Incompatible arguments for +" a b
))))
1069 (defun math-add-symb-fancy (a b
)
1070 (or (and math-simplify-only
1071 (not (equal a math-simplify-only
))
1073 (and (eq (car-safe b
) '+)
1074 (math-add (math-add a
(nth 1 b
))
1076 (and (eq (car-safe b
) '-
)
1077 (math-sub (math-add a
(nth 1 b
))
1079 (and (eq (car-safe b
) 'neg
)
1080 (eq (car-safe (nth 1 b
)) '+)
1081 (math-sub (math-sub a
(nth 1 (nth 1 b
)))
1083 (and (or (and (Math-vectorp a
) (math-known-scalarp b
))
1084 (and (Math-vectorp b
) (math-known-scalarp a
)))
1085 (math-map-vec-2 'math-add a b
))
1086 (let ((inf (math-infinitep a
)))
1089 (let ((inf2 (math-infinitep b
)))
1091 (if (or (memq (nth 2 inf
) '(var-uinf var-nan
))
1092 (memq (nth 2 inf2
) '(var-uinf var-nan
)))
1094 (let ((dir (math-infinite-dir a inf
))
1095 (dir2 (math-infinite-dir b inf2
)))
1096 (if (and (Math-objectp dir
) (Math-objectp dir2
))
1097 (if (Math-equal dir dir2
)
1099 '(var nan var-nan
)))))
1100 (if (and (equal a
'(var inf var-inf
))
1101 (eq (car-safe b
) 'intv
)
1102 (memq (nth 1 b
) '(2 3))
1103 (equal (nth 2 b
) '(neg (var inf var-inf
))))
1104 (list 'intv
3 (nth 2 b
) a
)
1105 (if (and (equal a
'(neg (var inf var-inf
)))
1106 (eq (car-safe b
) 'intv
)
1107 (memq (nth 1 b
) '(1 3))
1108 (equal (nth 3 b
) '(var inf var-inf
)))
1109 (list 'intv
3 a
(nth 3 b
))
1112 (if (eq (car-safe a
) 'intv
)
1115 ((eq (car-safe a
) '+)
1116 (let ((temp (math-combine-sum (nth 2 a
) b nil nil t
)))
1118 (math-add (nth 1 a
) temp
))))
1119 ((eq (car-safe a
) '-
)
1120 (let ((temp (math-combine-sum (nth 2 a
) b t nil t
)))
1122 (math-add (nth 1 a
) temp
))))
1123 ((and (Math-objectp a
) (Math-objectp b
))
1126 (math-combine-sum a b nil nil nil
))))
1127 (and (Math-looks-negp b
)
1128 (list '- a
(math-neg b
)))
1129 (and (Math-looks-negp a
)
1130 (list '- b
(math-neg a
)))
1131 (and (eq (car-safe a
) 'calcFunc-idn
)
1133 (or (and (eq (car-safe b
) 'calcFunc-idn
)
1135 (list 'calcFunc-idn
(math-add (nth 1 a
) (nth 1 b
))))
1136 (and (math-square-matrixp b
)
1137 (math-add (math-mimic-ident (nth 1 a
) b
) b
))
1138 (and (math-known-scalarp b
)
1139 (math-add (nth 1 a
) b
))))
1140 (and (eq (car-safe b
) 'calcFunc-idn
)
1142 (or (and (math-square-matrixp a
)
1143 (math-add a
(math-mimic-ident (nth 1 b
) a
)))
1144 (and (math-known-scalarp a
)
1145 (math-add a
(nth 1 b
)))))
1149 (defun calcFunc-mul (&rest rest
)
1151 (let ((a (car rest
)))
1152 (while (setq rest
(cdr rest
))
1153 (setq a
(list '* a
(car rest
))))
1157 (defun math-mul-objects-fancy (a b
)
1158 (cond ((and (Math-numberp a
) (Math-numberp b
))
1160 (if (math-want-polar a b
)
1161 (let ((a (math-polar a
))
1164 (math-mul (nth 1 a
) (nth 1 b
))
1165 (math-fix-circular (math-add (nth 2 a
) (nth 2 b
)))))
1166 (setq a
(math-complex a
)
1169 (math-sub (math-mul (nth 1 a
) (nth 1 b
))
1170 (math-mul (nth 2 a
) (nth 2 b
)))
1171 (math-add (math-mul (nth 1 a
) (nth 2 b
))
1172 (math-mul (nth 2 a
) (nth 1 b
)))))))
1174 (if (Math-vectorp b
)
1175 (if (math-matrixp a
)
1176 (if (math-matrixp b
)
1177 (if (= (length (nth 1 a
)) (length b
))
1179 (math-dimension-error))
1180 (if (= (length (nth 1 a
)) 2)
1181 (if (= (length a
) (length b
))
1182 (math-mul-mats a
(list 'vec b
))
1183 (math-dimension-error))
1184 (if (= (length (nth 1 a
)) (length b
))
1185 (math-mul-mat-vec a b
)
1186 (math-dimension-error))))
1187 (if (math-matrixp b
)
1188 (if (= (length a
) (length b
))
1189 (nth 1 (math-mul-mats (list 'vec a
) b
))
1190 (math-dimension-error))
1191 (if (= (length a
) (length b
))
1192 (math-dot-product a b
)
1193 (math-dimension-error))))
1194 (math-map-vec-2 'math-mul a b
)))
1196 (math-map-vec-2 'math-mul a b
))
1197 ((eq (car-safe a
) 'sdev
)
1198 (if (eq (car-safe b
) 'sdev
)
1199 (math-make-sdev (math-mul (nth 1 a
) (nth 1 b
))
1200 (math-hypot (math-mul (nth 2 a
) (nth 1 b
))
1201 (math-mul (nth 2 b
) (nth 1 a
))))
1202 (and (or (Math-scalarp b
)
1203 (not (Math-objvecp b
)))
1204 (math-make-sdev (math-mul (nth 1 a
) b
)
1205 (math-mul (nth 2 a
) b
)))))
1206 ((and (eq (car-safe b
) 'sdev
)
1207 (or (Math-scalarp a
)
1208 (not (Math-objvecp a
))))
1209 (math-make-sdev (math-mul a
(nth 1 b
)) (math-mul a
(nth 2 b
))))
1210 ((and (eq (car-safe a
) 'intv
) (Math-anglep b
))
1212 (math-neg (math-mul a
(math-neg b
)))
1213 (math-make-intv (nth 1 a
)
1214 (math-mul (nth 2 a
) b
)
1215 (math-mul (nth 3 a
) b
))))
1216 ((and (eq (car-safe b
) 'intv
) (Math-anglep a
))
1218 ((and (eq (car-safe a
) 'intv
) (math-intv-constp a
)
1219 (eq (car-safe b
) 'intv
) (math-intv-constp b
))
1220 (let ((lo (math-mul a
(nth 2 b
)))
1221 (hi (math-mul a
(nth 3 b
))))
1222 (or (eq (car-safe lo
) 'intv
)
1223 (setq lo
(list 'intv
(if (memq (nth 1 b
) '(2 3)) 3 0) lo lo
)))
1224 (or (eq (car-safe hi
) 'intv
)
1225 (setq hi
(list 'intv
(if (memq (nth 1 b
) '(1 3)) 3 0) hi hi
)))
1226 (math-combine-intervals
1227 (nth 2 lo
) (and (or (memq (nth 1 b
) '(2 3))
1228 (math-infinitep (nth 2 lo
)))
1229 (memq (nth 1 lo
) '(2 3)))
1230 (nth 3 lo
) (and (or (memq (nth 1 b
) '(2 3))
1231 (math-infinitep (nth 3 lo
)))
1232 (memq (nth 1 lo
) '(1 3)))
1233 (nth 2 hi
) (and (or (memq (nth 1 b
) '(1 3))
1234 (math-infinitep (nth 2 hi
)))
1235 (memq (nth 1 hi
) '(2 3)))
1236 (nth 3 hi
) (and (or (memq (nth 1 b
) '(1 3))
1237 (math-infinitep (nth 3 hi
)))
1238 (memq (nth 1 hi
) '(1 3))))))
1239 ((and (eq (car-safe a
) 'mod
)
1240 (eq (car-safe b
) 'mod
)
1241 (equal (nth 2 a
) (nth 2 b
)))
1242 (math-make-mod (math-mul (nth 1 a
) (nth 1 b
)) (nth 2 a
)))
1243 ((and (eq (car-safe a
) 'mod
)
1245 (math-make-mod (math-mul (nth 1 a
) b
) (nth 2 a
)))
1246 ((and (eq (car-safe b
) 'mod
)
1248 (math-make-mod (math-mul a
(nth 1 b
)) (nth 2 b
)))
1249 ((and (eq (car-safe a
) 'hms
) (Math-realp b
))
1250 (math-with-extra-prec 2
1251 (math-to-hms (math-mul (math-from-hms a
'deg
) b
) 'deg
)))
1252 ((and (eq (car-safe b
) 'hms
) (Math-realp a
))
1254 (t (calc-record-why "*Incompatible arguments for *" a b
))))
1256 ;;; Fast function to multiply floating-point numbers.
1257 (defun math-mul-float (a b
) ; [F F F]
1258 (math-make-float (math-mul (nth 1 a
) (nth 1 b
))
1259 (+ (nth 2 a
) (nth 2 b
))))
1261 (defun math-sqr-float (a) ; [F F]
1262 (math-make-float (math-mul (nth 1 a
) (nth 1 a
))
1263 (+ (nth 2 a
) (nth 2 a
))))
1265 (defun math-intv-constp (a &optional finite
)
1266 (and (or (Math-anglep (nth 2 a
))
1267 (and (equal (nth 2 a
) '(neg (var inf var-inf
)))
1269 (memq (nth 1 a
) '(0 1)))))
1270 (or (Math-anglep (nth 3 a
))
1271 (and (equal (nth 3 a
) '(var inf var-inf
))
1273 (memq (nth 1 a
) '(0 2)))))))
1275 (defun math-mul-zero (a b
)
1276 (if (math-known-matrixp b
)
1277 (if (math-vectorp b
)
1278 (math-map-vec-2 'math-mul a b
)
1279 (math-mimic-ident 0 b
))
1280 (if (math-infinitep b
)
1282 (let ((aa nil
) (bb nil
))
1283 (if (and (eq (car-safe b
) 'intv
)
1285 (and (equal (nth 2 b
) '(neg (var inf var-inf
)))
1286 (memq (nth 1 b
) '(2 3))
1287 (setq aa
(nth 2 b
)))
1288 (and (equal (nth 3 b
) '(var inf var-inf
))
1289 (memq (nth 1 b
) '(1 3))
1290 (setq bb
(nth 3 b
)))
1292 (if (or (math-posp a
)
1294 (or (memq calc-infinite-mode
'(-1 1))
1295 (setq aa
'(neg (var inf var-inf
))
1296 bb
'(var inf var-inf
)))))
1297 (list 'intv
3 (or aa
0) (or bb
0))
1299 (math-neg (list 'intv
3 (or aa
0) (or bb
0)))
1300 '(var nan var-nan
)))
1301 (if (or (math-floatp a
) (math-floatp b
)) '(float 0 0) 0))))))
1304 (defun math-mul-symb-fancy (a b
)
1305 (or (and math-simplify-only
1306 (not (equal a math-simplify-only
))
1308 (and (Math-equal-int a
1)
1310 (and (Math-equal-int a -
1)
1312 (and (or (and (Math-vectorp a
) (math-known-scalarp b
))
1313 (and (Math-vectorp b
) (math-known-scalarp a
)))
1314 (math-map-vec-2 'math-mul a b
))
1315 (and (Math-objectp b
) (not (Math-objectp a
))
1317 (and (eq (car-safe a
) 'neg
)
1318 (math-neg (math-mul (nth 1 a
) b
)))
1319 (and (eq (car-safe b
) 'neg
)
1320 (math-neg (math-mul a
(nth 1 b
))))
1321 (and (eq (car-safe a
) '*)
1323 (math-mul (nth 2 a
) b
)))
1324 (and (eq (car-safe a
) '^
)
1325 (Math-looks-negp (nth 2 a
))
1326 (not (and (eq (car-safe b
) '^
) (Math-looks-negp (nth 2 b
))))
1327 (math-known-scalarp b t
)
1328 (math-div b
(math-normalize
1329 (list '^
(nth 1 a
) (math-neg (nth 2 a
))))))
1330 (and (eq (car-safe b
) '^
)
1331 (Math-looks-negp (nth 2 b
))
1332 (not (and (eq (car-safe a
) '^
) (Math-looks-negp (nth 2 a
))))
1333 (math-div a
(math-normalize
1334 (list '^
(nth 1 b
) (math-neg (nth 2 b
))))))
1335 (and (eq (car-safe a
) '/)
1336 (or (math-known-scalarp a t
) (math-known-scalarp b t
))
1337 (let ((temp (math-combine-prod (nth 2 a
) b t nil t
)))
1339 (math-mul (nth 1 a
) temp
)
1340 (math-div (math-mul (nth 1 a
) b
) (nth 2 a
)))))
1341 (and (eq (car-safe b
) '/)
1342 (math-div (math-mul a
(nth 1 b
)) (nth 2 b
)))
1343 (and (eq (car-safe b
) '+)
1345 (or (Math-numberp (nth 1 b
))
1346 (Math-numberp (nth 2 b
)))
1347 (math-add (math-mul a
(nth 1 b
))
1348 (math-mul a
(nth 2 b
))))
1349 (and (eq (car-safe b
) '-
)
1351 (or (Math-numberp (nth 1 b
))
1352 (Math-numberp (nth 2 b
)))
1353 (math-sub (math-mul a
(nth 1 b
))
1354 (math-mul a
(nth 2 b
))))
1355 (and (eq (car-safe b
) '*)
1356 (Math-numberp (nth 1 b
))
1357 (not (Math-numberp a
))
1358 (math-mul (nth 1 b
) (math-mul a
(nth 2 b
))))
1359 (and (eq (car-safe a
) 'calcFunc-idn
)
1361 (or (and (eq (car-safe b
) 'calcFunc-idn
)
1363 (list 'calcFunc-idn
(math-mul (nth 1 a
) (nth 1 b
))))
1364 (and (math-known-scalarp b
)
1365 (list 'calcFunc-idn
(math-mul (nth 1 a
) b
)))
1366 (and (math-known-matrixp b
)
1367 (math-mul (nth 1 a
) b
))))
1368 (and (eq (car-safe b
) 'calcFunc-idn
)
1370 (or (and (math-known-scalarp a
)
1371 (list 'calcFunc-idn
(math-mul a
(nth 1 b
))))
1372 (and (math-known-matrixp a
)
1373 (math-mul a
(nth 1 b
)))))
1374 (and (math-looks-negp b
)
1375 (math-mul (math-neg a
) (math-neg b
)))
1376 (and (eq (car-safe b
) '-
)
1378 (math-mul (math-neg a
) (math-neg b
)))
1380 ((eq (car-safe b
) '*)
1381 (let ((temp (math-combine-prod a
(nth 1 b
) nil nil t
)))
1383 (math-mul temp
(nth 2 b
)))))
1385 (math-combine-prod a b nil nil nil
)))
1386 (and (equal a
'(var nan var-nan
))
1388 (and (equal b
'(var nan var-nan
))
1390 (and (equal a
'(var uinf var-uinf
))
1392 (and (equal b
'(var uinf var-uinf
))
1394 (and (equal b
'(var inf var-inf
))
1395 (let ((s1 (math-possible-signs a
)))
1399 '(intv 3 0 (var inf var-inf
)))
1403 '(intv 3 (neg (var inf var-inf
)) 0))
1404 ((and (eq (car a
) 'intv
) (math-intv-constp a
))
1405 '(intv 3 (neg (var inf var-inf
)) (var inf var-inf
)))
1406 ((and (eq (car a
) 'cplx
)
1407 (math-zerop (nth 1 a
)))
1408 (list '* (list 'cplx
0 (calcFunc-sign (nth 2 a
))) b
))
1409 ((eq (car a
) 'polar
)
1410 (list '* (list 'polar
1 (nth 2 a
)) b
)))))
1411 (and (equal a
'(var inf var-inf
))
1416 (defun calcFunc-div (a &rest rest
)
1418 (setq a
(list '/ a
(car rest
))
1422 (defun math-div-objects-fancy (a b
)
1423 (cond ((and (Math-numberp a
) (Math-numberp b
))
1425 (cond ((math-want-polar a b
)
1426 (let ((a (math-polar a
))
1429 (math-div (nth 1 a
) (nth 1 b
))
1430 (math-fix-circular (math-sub (nth 2 a
)
1433 (setq a
(math-complex a
))
1434 (list 'cplx
(math-div (nth 1 a
) b
)
1435 (math-div (nth 2 a
) b
)))
1437 (setq a
(math-complex a
)
1441 (math-add (math-mul (nth 1 a
) (nth 1 b
))
1442 (math-mul (nth 2 a
) (nth 2 b
)))
1443 (math-sub (math-mul (nth 2 a
) (nth 1 b
))
1444 (math-mul (nth 1 a
) (nth 2 b
))))
1445 (math-add (math-sqr (nth 1 b
))
1446 (math-sqr (nth 2 b
))))))))
1448 (if (math-square-matrixp b
)
1449 (let ((n1 (length b
)))
1450 (if (Math-vectorp a
)
1451 (if (math-matrixp a
)
1452 (if (= (length a
) n1
)
1453 (math-lud-solve (math-matrix-lud b
) a b
)
1454 (if (= (length (nth 1 a
)) n1
)
1456 (math-lud-solve (math-matrix-lud
1458 (math-transpose a
) b
))
1459 (math-dimension-error)))
1460 (if (= (length a
) n1
)
1461 (math-mat-col (math-lud-solve (math-matrix-lud b
)
1462 (math-col-matrix a
) b
)
1464 (math-dimension-error)))
1465 (if (Math-equal-int a
1)
1467 (math-mul a
(calcFunc-inv b
)))))
1468 (math-reject-arg b
'square-matrixp
)))
1469 ((and (Math-vectorp a
) (Math-objectp b
))
1470 (math-map-vec-2 'math-div a b
))
1471 ((eq (car-safe a
) 'sdev
)
1472 (if (eq (car-safe b
) 'sdev
)
1473 (let ((x (math-div (nth 1 a
) (nth 1 b
))))
1475 (math-div (math-hypot (nth 2 a
)
1476 (math-mul (nth 2 b
) x
))
1478 (if (or (Math-scalarp b
)
1479 (not (Math-objvecp b
)))
1480 (math-make-sdev (math-div (nth 1 a
) b
) (math-div (nth 2 a
) b
))
1481 (math-reject-arg 'realp b
))))
1482 ((and (eq (car-safe b
) 'sdev
)
1483 (or (Math-scalarp a
)
1484 (not (Math-objvecp a
))))
1485 (let ((x (math-div a
(nth 1 b
))))
1487 (math-div (math-mul (nth 2 b
) x
) (nth 1 b
)))))
1488 ((and (eq (car-safe a
) 'intv
) (Math-anglep b
))
1490 (math-neg (math-div a
(math-neg b
)))
1491 (math-make-intv (nth 1 a
)
1492 (math-div (nth 2 a
) b
)
1493 (math-div (nth 3 a
) b
))))
1494 ((and (eq (car-safe b
) 'intv
) (Math-anglep a
))
1495 (if (or (Math-posp (nth 2 b
))
1496 (and (Math-zerop (nth 2 b
)) (or (memq (nth 1 b
) '(0 1))
1497 calc-infinite-mode
)))
1499 (math-neg (math-div (math-neg a
) b
))
1500 (let ((calc-infinite-mode 1))
1501 (math-make-intv (aref [0 2 1 3] (nth 1 b
))
1502 (math-div a
(nth 3 b
))
1503 (math-div a
(nth 2 b
)))))
1504 (if (or (Math-negp (nth 3 b
))
1505 (and (Math-zerop (nth 3 b
)) (or (memq (nth 1 b
) '(0 2))
1506 calc-infinite-mode
)))
1507 (math-neg (math-div a
(math-neg b
)))
1508 (if calc-infinite-mode
1509 '(intv 3 (neg (var inf var-inf
)) (var inf var-inf
))
1510 (math-reject-arg b
"*Division by zero")))))
1511 ((and (eq (car-safe a
) 'intv
) (math-intv-constp a
)
1512 (eq (car-safe b
) 'intv
) (math-intv-constp b
))
1513 (if (or (Math-posp (nth 2 b
))
1514 (and (Math-zerop (nth 2 b
)) (or (memq (nth 1 b
) '(0 1))
1515 calc-infinite-mode
)))
1516 (let* ((calc-infinite-mode 1)
1517 (lo (math-div a
(nth 2 b
)))
1518 (hi (math-div a
(nth 3 b
))))
1519 (or (eq (car-safe lo
) 'intv
)
1520 (setq lo
(list 'intv
(if (memq (nth 1 b
) '(2 3)) 3 0)
1522 (or (eq (car-safe hi
) 'intv
)
1523 (setq hi
(list 'intv
(if (memq (nth 1 b
) '(1 3)) 3 0)
1525 (math-combine-intervals
1526 (nth 2 lo
) (and (or (memq (nth 1 b
) '(2 3))
1527 (and (math-infinitep (nth 2 lo
))
1528 (not (math-zerop (nth 2 b
)))))
1529 (memq (nth 1 lo
) '(2 3)))
1530 (nth 3 lo
) (and (or (memq (nth 1 b
) '(2 3))
1531 (and (math-infinitep (nth 3 lo
))
1532 (not (math-zerop (nth 2 b
)))))
1533 (memq (nth 1 lo
) '(1 3)))
1534 (nth 2 hi
) (and (or (memq (nth 1 b
) '(1 3))
1535 (and (math-infinitep (nth 2 hi
))
1536 (not (math-zerop (nth 3 b
)))))
1537 (memq (nth 1 hi
) '(2 3)))
1538 (nth 3 hi
) (and (or (memq (nth 1 b
) '(1 3))
1539 (and (math-infinitep (nth 3 hi
))
1540 (not (math-zerop (nth 3 b
)))))
1541 (memq (nth 1 hi
) '(1 3)))))
1542 (if (or (Math-negp (nth 3 b
))
1543 (and (Math-zerop (nth 3 b
)) (or (memq (nth 1 b
) '(0 2))
1544 calc-infinite-mode
)))
1545 (math-neg (math-div a
(math-neg b
)))
1546 (if calc-infinite-mode
1547 '(intv 3 (neg (var inf var-inf
)) (var inf var-inf
))
1548 (math-reject-arg b
"*Division by zero")))))
1549 ((and (eq (car-safe a
) 'mod
)
1550 (eq (car-safe b
) 'mod
)
1551 (equal (nth 2 a
) (nth 2 b
)))
1552 (math-make-mod (math-div-mod (nth 1 a
) (nth 1 b
) (nth 2 a
))
1554 ((and (eq (car-safe a
) 'mod
)
1556 (math-make-mod (math-div-mod (nth 1 a
) b
(nth 2 a
)) (nth 2 a
)))
1557 ((and (eq (car-safe b
) 'mod
)
1559 (math-make-mod (math-div-mod a
(nth 1 b
) (nth 2 b
)) (nth 2 b
)))
1560 ((eq (car-safe a
) 'hms
)
1561 (if (eq (car-safe b
) 'hms
)
1562 (math-with-extra-prec 1
1563 (math-div (math-from-hms a
'deg
)
1564 (math-from-hms b
'deg
)))
1565 (math-with-extra-prec 2
1566 (math-to-hms (math-div (math-from-hms a
'deg
) b
) 'deg
))))
1567 (t (calc-record-why "*Incompatible arguments for /" a b
))))
1569 (defun math-div-by-zero (a b
)
1570 (if (math-infinitep a
)
1571 (if (or (equal a
'(var nan var-nan
))
1572 (equal b
'(var uinf var-uinf
))
1573 (memq calc-infinite-mode
'(-1 1)))
1575 '(var uinf var-uinf
))
1576 (if calc-infinite-mode
1579 (if (eq calc-infinite-mode
1)
1580 (math-mul a
'(var inf var-inf
))
1581 (if (eq calc-infinite-mode -
1)
1582 (math-mul a
'(neg (var inf var-inf
)))
1583 (if (eq (car-safe a
) 'intv
)
1584 '(intv 3 (neg (var inf var-inf
)) (var inf var-inf
))
1585 '(var uinf var-uinf
)))))
1586 (math-reject-arg a
"*Division by zero"))))
1588 (defun math-div-zero (a b
)
1589 (if (math-known-matrixp b
)
1590 (if (math-vectorp b
)
1591 (math-map-vec-2 'math-div a b
)
1592 (math-mimic-ident 0 b
))
1593 (if (equal b
'(var nan var-nan
))
1595 (if (and (eq (car-safe b
) 'intv
) (math-intv-constp b
)
1596 (not (math-posp b
)) (not (math-negp b
)))
1597 (if calc-infinite-mode
1599 (if (and (math-zerop (nth 2 b
))
1600 (memq calc-infinite-mode
'(1 -
1)))
1601 (nth 2 b
) '(neg (var inf var-inf
)))
1602 (if (and (math-zerop (nth 3 b
))
1603 (memq calc-infinite-mode
'(1 -
1)))
1604 (nth 3 b
) '(var inf var-inf
)))
1605 (math-reject-arg b
"*Division by zero"))
1608 (defun math-div-symb-fancy (a b
)
1609 (or (and math-simplify-only
1610 (not (equal a math-simplify-only
))
1612 (and (Math-equal-int b
1) a
)
1613 (and (Math-equal-int b -
1) (math-neg a
))
1614 (and (Math-vectorp a
) (math-known-scalarp b
)
1615 (math-map-vec-2 'math-div a b
))
1616 (and (eq (car-safe b
) '^
)
1617 (or (Math-looks-negp (nth 2 b
)) (Math-equal-int a
1))
1618 (math-mul a
(math-normalize
1619 (list '^
(nth 1 b
) (math-neg (nth 2 b
))))))
1620 (and (eq (car-safe a
) 'neg
)
1621 (math-neg (math-div (nth 1 a
) b
)))
1622 (and (eq (car-safe b
) 'neg
)
1623 (math-neg (math-div a
(nth 1 b
))))
1624 (and (eq (car-safe a
) '/)
1625 (math-div (nth 1 a
) (math-mul (nth 2 a
) b
)))
1626 (and (eq (car-safe b
) '/)
1627 (or (math-known-scalarp (nth 1 b
) t
)
1628 (math-known-scalarp (nth 2 b
) t
))
1629 (math-div (math-mul a
(nth 2 b
)) (nth 1 b
)))
1630 (and (eq (car-safe b
) 'frac
)
1631 (math-mul (math-make-frac (nth 2 b
) (nth 1 b
)) a
))
1632 (and (eq (car-safe a
) '+)
1633 (or (Math-numberp (nth 1 a
))
1634 (Math-numberp (nth 2 a
)))
1636 (math-add (math-div (nth 1 a
) b
)
1637 (math-div (nth 2 a
) b
)))
1638 (and (eq (car-safe a
) '-
)
1639 (or (Math-numberp (nth 1 a
))
1640 (Math-numberp (nth 2 a
)))
1642 (math-sub (math-div (nth 1 a
) b
)
1643 (math-div (nth 2 a
) b
)))
1644 (and (or (eq (car-safe a
) '-
)
1645 (math-looks-negp a
))
1647 (math-div (math-neg a
) (math-neg b
)))
1648 (and (eq (car-safe b
) '-
)
1650 (math-div (math-neg a
) (math-neg b
)))
1651 (and (eq (car-safe a
) 'calcFunc-idn
)
1653 (or (and (eq (car-safe b
) 'calcFunc-idn
)
1655 (list 'calcFunc-idn
(math-div (nth 1 a
) (nth 1 b
))))
1656 (and (math-known-scalarp b
)
1657 (list 'calcFunc-idn
(math-div (nth 1 a
) b
)))
1658 (and (math-known-matrixp b
)
1659 (math-div (nth 1 a
) b
))))
1660 (and (eq (car-safe b
) 'calcFunc-idn
)
1662 (or (and (math-known-scalarp a
)
1663 (list 'calcFunc-idn
(math-div a
(nth 1 b
))))
1664 (and (math-known-matrixp a
)
1665 (math-div a
(nth 1 b
)))))
1666 (if (and calc-matrix-mode
1667 (or (math-known-matrixp a
) (math-known-matrixp b
)))
1668 (math-combine-prod a b nil t nil
)
1669 (if (eq (car-safe a
) '*)
1670 (if (eq (car-safe b
) '*)
1671 (let ((c (math-combine-prod (nth 1 a
) (nth 1 b
) nil t t
)))
1673 (math-div (math-mul c
(nth 2 a
)) (nth 2 b
))))
1674 (let ((c (math-combine-prod (nth 1 a
) b nil t t
)))
1676 (math-mul c
(nth 2 a
)))))
1677 (if (eq (car-safe b
) '*)
1678 (let ((c (math-combine-prod a
(nth 1 b
) nil t t
)))
1680 (math-div c
(nth 2 b
))))
1681 (math-combine-prod a b nil t nil
))))
1682 (and (math-infinitep a
)
1683 (if (math-infinitep b
)
1685 (if (or (equal a
'(var nan var-nan
))
1686 (equal a
'(var uinf var-uinf
)))
1688 (if (equal a
'(var inf var-inf
))
1689 (if (or (math-posp b
)
1690 (and (eq (car-safe b
) 'intv
)
1691 (math-zerop (nth 2 b
))))
1692 (if (and (eq (car-safe b
) 'intv
)
1693 (not (math-intv-constp b t
)))
1694 '(intv 3 0 (var inf var-inf
))
1696 (if (or (math-negp b
)
1697 (and (eq (car-safe b
) 'intv
)
1698 (math-zerop (nth 3 b
))))
1699 (if (and (eq (car-safe b
) 'intv
)
1700 (not (math-intv-constp b t
)))
1701 '(intv 3 (neg (var inf var-inf
)) 0)
1703 (if (and (eq (car-safe b
) 'intv
)
1704 (math-negp (nth 2 b
)) (math-posp (nth 3 b
)))
1705 '(intv 3 (neg (var inf var-inf
))
1706 (var inf var-inf
)))))))))
1707 (and (math-infinitep b
)
1708 (if (equal b
'(var nan var-nan
))
1710 (let ((calc-infinite-mode 1))
1711 (math-mul-zero b a
))))
1715 (defun calcFunc-mod (a b
)
1716 (math-normalize (list '% a b
)))
1718 (defun math-mod-fancy (a b
)
1719 (cond ((equal b
'(var inf var-inf
))
1720 (if (or (math-posp a
) (math-zerop a
))
1724 (if (eq (car-safe a
) 'intv
)
1725 (if (math-negp (nth 2 a
))
1726 '(intv 3 0 (var inf var-inf
))
1729 ((and (eq (car-safe a
) 'mod
) (Math-realp b
) (math-posp b
))
1730 (math-make-mod (nth 1 a
) b
))
1731 ((and (eq (car-safe a
) 'intv
) (math-intv-constp a t
) (math-posp b
))
1732 (math-mod-intv a b
))
1735 (calc-record-why 'anglep b
)
1736 (calc-record-why 'anglep a
))
1740 (defun calcFunc-pow (a b
)
1741 (math-normalize (list '^ a b
)))
1743 (defun math-pow-of-zero (a b
)
1745 (if calc-infinite-mode
1747 (math-reject-arg (list '^ a b
) "*Indeterminate form"))
1748 (if (math-floatp b
) (setq a
(math-float a
)))
1753 (if (math-infinitep b
)
1755 (if (and (eq (car b
) 'intv
) (math-intv-constp b
)
1757 '(intv 3 (neg (var inf var-inf
)) (var inf var-inf
))
1758 (if (math-objectp b
)
1762 (defun math-pow-zero (a b
)
1763 (if (eq (car-safe a
) 'mod
)
1764 (math-make-mod 1 (nth 2 a
))
1765 (if (math-known-matrixp a
)
1766 (math-mimic-ident 1 a
)
1767 (if (math-infinitep a
)
1769 (if (and (eq (car a
) 'intv
) (math-intv-constp a
)
1770 (or (and (not (math-posp a
)) (not (math-negp a
)))
1771 (not (math-intv-constp a t
))))
1772 '(intv 3 (neg (var inf var-inf
)) (var inf var-inf
))
1773 (if (or (math-floatp a
) (math-floatp b
))
1774 '(float 1 0) 1))))))
1776 (defun math-pow-fancy (a b
)
1777 (cond ((and (Math-numberp a
) (Math-numberp b
))
1778 (or (if (memq (math-quarter-integer b
) '(1 2 3))
1779 (let ((sqrt (math-sqrt (if (math-floatp b
)
1780 (math-float a
) a
))))
1781 (and (Math-numberp sqrt
)
1782 (math-pow sqrt
(math-mul 2 b
))))
1783 (and (eq (car b
) 'frac
)
1784 (integerp (nth 2 b
))
1786 (let ((root (math-nth-root a
(nth 2 b
))))
1787 (and root
(math-ipow root
(nth 1 b
))))))
1788 (and (or (eq a
10) (equal a
'(float 1 1)))
1789 (math-num-integerp b
)
1790 (calcFunc-scf '(float 1 0) b
))
1791 (and calc-symbolic-mode
1793 (math-with-extra-prec 2
1795 (math-float (math-mul b
(math-ln-raw (math-float a
))))))))
1796 ((or (not (Math-objvecp a
))
1797 (not (Math-objectp b
)))
1799 (cond ((and math-simplify-only
1800 (not (equal a math-simplify-only
)))
1802 ((and (eq (car-safe a
) '*)
1803 (or (math-known-num-integerp b
)
1804 (math-known-nonnegp (nth 1 a
))
1805 (math-known-nonnegp (nth 2 a
))))
1806 (math-mul (math-pow (nth 1 a
) b
)
1807 (math-pow (nth 2 a
) b
)))
1808 ((and (eq (car-safe a
) '/)
1809 (or (math-known-num-integerp b
)
1810 (math-known-nonnegp (nth 2 a
))))
1811 (math-div (math-pow (nth 1 a
) b
)
1812 (math-pow (nth 2 a
) b
)))
1813 ((and (eq (car-safe a
) '/)
1814 (math-known-nonnegp (nth 1 a
))
1815 (not (math-equal-int (nth 1 a
) 1)))
1816 (math-mul (math-pow (nth 1 a
) b
)
1817 (math-pow (math-div 1 (nth 2 a
)) b
)))
1818 ((and (eq (car-safe a
) '^
)
1819 (or (math-known-num-integerp b
)
1820 (math-known-nonnegp (nth 1 a
))))
1821 (math-pow (nth 1 a
) (math-mul (nth 2 a
) b
)))
1822 ((and (eq (car-safe a
) 'calcFunc-sqrt
)
1823 (or (math-known-num-integerp b
)
1824 (math-known-nonnegp (nth 1 a
))))
1825 (math-pow (nth 1 a
) (math-div b
2)))
1826 ((and (eq (car-safe a
) '^
)
1827 (math-known-evenp (nth 2 a
))
1828 (memq (math-quarter-integer b
) '(1 2 3))
1829 (math-known-realp (nth 1 a
)))
1830 (math-abs (math-pow (nth 1 a
) (math-mul (nth 2 a
) b
))))
1831 ((and (math-looks-negp a
)
1832 (math-known-integerp b
)
1833 (setq temp
(or (and (math-known-evenp b
)
1834 (math-pow (math-neg a
) b
))
1835 (and (math-known-oddp b
)
1836 (math-neg (math-pow (math-neg a
)
1839 ((and (eq (car-safe a
) 'calcFunc-abs
)
1840 (math-known-realp (nth 1 a
))
1841 (math-known-evenp b
))
1842 (math-pow (nth 1 a
) b
))
1844 (cond ((equal a
'(var nan var-nan
))
1847 (math-mul (math-pow -
1 b
) (math-pow (nth 1 a
) b
)))
1851 (if (math-floatp b
) '(float 0 0) 0))
1852 ((and (eq (car-safe b
) 'intv
)
1853 (math-intv-constp b
))
1854 '(intv 3 0 (var inf var-inf
)))
1856 '(var nan var-nan
))))
1859 (cond ((math-negp b
)
1860 (math-pow (math-div 1 a
) (math-neg b
)))
1861 ((not (math-posp b
))
1863 ((math-equal-int (setq scale
(calcFunc-abssqr a
)) 1)
1865 ((Math-lessp scale
1)
1866 (if (math-floatp a
) '(float 0 0) 0))
1870 '(var uinf var-uinf
))
1871 ((and (eq (car a
) 'intv
)
1872 (math-intv-constp a
))
1873 (if (Math-lessp -
1 a
)
1874 (if (math-equal-int (nth 3 a
) 1)
1876 '(intv 3 0 (var inf var-inf
)))
1877 '(intv 3 (neg (var inf var-inf
))
1878 (var inf var-inf
))))
1879 (t (list '^ a b
)))))
1880 ((and (eq (car-safe a
) 'calcFunc-idn
)
1882 (math-known-num-integerp b
))
1883 (list 'calcFunc-idn
(math-pow (nth 1 a
) b
)))
1884 (t (if (Math-objectp a
)
1885 (calc-record-why 'objectp b
)
1886 (calc-record-why 'objectp a
))
1888 ((and (eq (car-safe a
) 'sdev
) (eq (car-safe b
) 'sdev
))
1889 (if (and (math-constp a
) (math-constp b
))
1890 (math-with-extra-prec 2
1891 (let* ((ln (math-ln-raw (math-float (nth 1 a
))))
1893 (math-float (math-mul (nth 1 b
) ln
)))))
1898 (math-hypot (math-mul (nth 2 a
)
1899 (math-div (nth 1 b
) (nth 1 a
)))
1900 (math-mul (nth 2 b
) ln
))))))
1901 (let ((pow (math-pow (nth 1 a
) (nth 1 b
))))
1905 (math-hypot (math-mul (nth 2 a
)
1906 (math-div (nth 1 b
) (nth 1 a
)))
1907 (math-mul (nth 2 b
) (calcFunc-ln
1909 ((and (eq (car-safe a
) 'sdev
) (Math-numberp b
))
1911 (math-with-extra-prec 2
1912 (let ((pow (math-pow (nth 1 a
) (math-sub b
1))))
1913 (math-make-sdev (math-mul pow
(nth 1 a
))
1914 (math-mul pow
(math-mul (nth 2 a
) b
)))))
1915 (math-make-sdev (math-pow (nth 1 a
) b
)
1916 (math-mul (math-pow (nth 1 a
) (math-add b -
1))
1917 (math-mul (nth 2 a
) b
)))))
1918 ((and (eq (car-safe b
) 'sdev
) (Math-numberp a
))
1919 (math-with-extra-prec 2
1920 (let* ((ln (math-ln-raw (math-float a
)))
1921 (pow (calcFunc-exp (math-mul (nth 1 b
) ln
))))
1922 (math-make-sdev pow
(math-mul pow
(math-mul (nth 2 b
) ln
))))))
1923 ((and (eq (car-safe a
) 'intv
) (math-intv-constp a
)
1925 (or (Math-natnump b
)
1926 (Math-posp (nth 2 a
))
1927 (and (math-zerop (nth 2 a
))
1929 (and (Math-integerp b
) calc-infinite-mode
)))
1930 (Math-negp (nth 3 a
))
1931 (and (math-zerop (nth 3 a
))
1933 (and (Math-integerp b
) calc-infinite-mode
)))))
1935 (setq a
(math-abs a
)))
1936 (let ((calc-infinite-mode (if (math-zerop (nth 3 a
)) -
1 1)))
1937 (math-sort-intv (nth 1 a
)
1938 (math-pow (nth 2 a
) b
)
1939 (math-pow (nth 3 a
) b
))))
1940 ((and (eq (car-safe b
) 'intv
) (math-intv-constp b
)
1941 (Math-realp a
) (Math-posp a
))
1942 (math-sort-intv (nth 1 b
)
1943 (math-pow a
(nth 2 b
))
1944 (math-pow a
(nth 3 b
))))
1945 ((and (eq (car-safe a
) 'intv
) (math-intv-constp a
)
1946 (eq (car-safe b
) 'intv
) (math-intv-constp b
)
1947 (or (and (not (Math-negp (nth 2 a
)))
1948 (not (Math-negp (nth 2 b
))))
1949 (and (Math-posp (nth 2 a
))
1950 (not (Math-posp (nth 3 b
))))))
1951 (let ((lo (math-pow a
(nth 2 b
)))
1952 (hi (math-pow a
(nth 3 b
))))
1953 (or (eq (car-safe lo
) 'intv
)
1954 (setq lo
(list 'intv
(if (memq (nth 1 b
) '(2 3)) 3 0) lo lo
)))
1955 (or (eq (car-safe hi
) 'intv
)
1956 (setq hi
(list 'intv
(if (memq (nth 1 b
) '(1 3)) 3 0) hi hi
)))
1957 (math-combine-intervals
1958 (nth 2 lo
) (and (or (memq (nth 1 b
) '(2 3))
1959 (math-infinitep (nth 2 lo
)))
1960 (memq (nth 1 lo
) '(2 3)))
1961 (nth 3 lo
) (and (or (memq (nth 1 b
) '(2 3))
1962 (math-infinitep (nth 3 lo
)))
1963 (memq (nth 1 lo
) '(1 3)))
1964 (nth 2 hi
) (and (or (memq (nth 1 b
) '(1 3))
1965 (math-infinitep (nth 2 hi
)))
1966 (memq (nth 1 hi
) '(2 3)))
1967 (nth 3 hi
) (and (or (memq (nth 1 b
) '(1 3))
1968 (math-infinitep (nth 3 hi
)))
1969 (memq (nth 1 hi
) '(1 3))))))
1970 ((and (eq (car-safe a
) 'mod
) (eq (car-safe b
) 'mod
)
1971 (equal (nth 2 a
) (nth 2 b
)))
1972 (math-make-mod (math-pow-mod (nth 1 a
) (nth 1 b
) (nth 2 a
))
1974 ((and (eq (car-safe a
) 'mod
) (Math-anglep b
))
1975 (math-make-mod (math-pow-mod (nth 1 a
) b
(nth 2 a
)) (nth 2 a
)))
1976 ((and (eq (car-safe b
) 'mod
) (Math-anglep a
))
1977 (math-make-mod (math-pow-mod a
(nth 1 b
) (nth 2 b
)) (nth 2 b
)))
1978 ((not (Math-numberp a
))
1979 (math-reject-arg a
'numberp
))
1981 (math-reject-arg b
'numberp
))))
1983 (defun math-quarter-integer (x)
1984 (if (Math-integerp x
)
1988 (setq x
(math-quarter-integer (math-neg x
)))
1990 (if (eq (car x
) 'frac
)
1991 (if (eq (nth 2 x
) 2)
1993 (and (eq (nth 2 x
) 4)
1996 (%
(if (consp x
) (nth 1 x
) x
) 4))))
1997 (if (eq (car x
) 'float
)
1998 (if (>= (nth 2 x
) 0)
2000 (if (= (nth 2 x
) -
1)
2003 (and (= (%
(if (consp x
) (nth 1 x
) x
) 10) 5) 2))
2004 (if (= (nth 2 x
) -
2)
2007 x
(%
(if (consp x
) (nth 1 x
) x
) 100))
2009 (if (= x
75) 3)))))))))))
2011 ;;; This assumes A < M and M > 0.
2012 (defun math-pow-mod (a b m
) ; [R R R R]
2013 (if (and (Math-integerp a
) (Math-integerp b
) (Math-integerp m
))
2015 (math-div-mod 1 (math-pow-mod a
(Math-integer-neg b
) m
) m
)
2018 (math-pow-mod-step a b m
)))
2019 (math-mod (math-pow a b
) m
)))
2021 (defun math-pow-mod-step (a n m
) ; [I I I I]
2022 (math-working "pow" a
)
2027 (let ((rest (math-pow-mod-step
2028 (math-imod (math-mul a a
) m
)
2033 (math-mod (math-mul a rest
) m
)))))))
2034 (math-working "pow" val
)
2038 ;;; Compute the minimum of two real numbers. [R R R] [Public]
2039 (defun math-min (a b
)
2040 (if (and (consp a
) (eq (car a
) 'intv
))
2041 (if (and (consp b
) (eq (car b
) 'intv
))
2042 (let ((lo (nth 2 a
))
2043 (lom (memq (nth 1 a
) '(2 3)))
2045 (him (memq (nth 1 a
) '(1 3)))
2047 (if (= (setq res
(math-compare (nth 2 b
) lo
)) -
1)
2048 (setq lo
(nth 2 b
) lom
(memq (nth 1 b
) '(2 3)))
2050 (setq lom
(or lom
(memq (nth 1 b
) '(2 3))))))
2051 (if (= (setq res
(math-compare (nth 3 b
) hi
)) -
1)
2052 (setq hi
(nth 3 b
) him
(memq (nth 1 b
) '(1 3)))
2054 (setq him
(or him
(memq (nth 1 b
) '(1 3))))))
2055 (math-make-intv (+ (if lom
2 0) (if him
1 0)) lo hi
))
2056 (math-min a
(list 'intv
3 b b
)))
2057 (if (and (consp b
) (eq (car b
) 'intv
))
2058 (math-min (list 'intv
3 a a
) b
)
2059 (let ((res (math-compare a b
)))
2066 (defun calcFunc-min (&optional a
&rest b
)
2069 (if (not (or (Math-anglep a
) (eq (car a
) 'date
)
2070 (and (eq (car a
) 'intv
) (math-intv-constp a
))
2071 (math-infinitep a
)))
2072 (math-reject-arg a
'anglep
))
2073 (math-min-list a b
)))
2075 (defun math-min-list (a b
)
2077 (if (or (Math-anglep (car b
)) (eq (car b
) 'date
)
2078 (and (eq (car (car b
)) 'intv
) (math-intv-constp (car b
)))
2079 (math-infinitep (car b
)))
2080 (math-min-list (math-min a
(car b
)) (cdr b
))
2081 (math-reject-arg (car b
) 'anglep
))
2084 ;;; Compute the maximum of two real numbers. [R R R] [Public]
2085 (defun math-max (a b
)
2086 (if (or (and (consp a
) (eq (car a
) 'intv
))
2087 (and (consp b
) (eq (car b
) 'intv
)))
2088 (math-neg (math-min (math-neg a
) (math-neg b
)))
2089 (let ((res (math-compare a b
)))
2096 (defun calcFunc-max (&optional a
&rest b
)
2098 '(neg (var inf var-inf
))
2099 (if (not (or (Math-anglep a
) (eq (car a
) 'date
)
2100 (and (eq (car a
) 'intv
) (math-intv-constp a
))
2101 (math-infinitep a
)))
2102 (math-reject-arg a
'anglep
))
2103 (math-max-list a b
)))
2105 (defun math-max-list (a b
)
2107 (if (or (Math-anglep (car b
)) (eq (car b
) 'date
)
2108 (and (eq (car (car b
)) 'intv
) (math-intv-constp (car b
)))
2109 (math-infinitep (car b
)))
2110 (math-max-list (math-max a
(car b
)) (cdr b
))
2111 (math-reject-arg (car b
) 'anglep
))
2115 ;;; Compute the absolute value of A. [O O; r r] [Public]
2117 (cond ((Math-negp a
)
2122 (math-hypot (nth 1 a
) (nth 2 a
)))
2123 ((eq (car a
) 'polar
)
2126 (if (cdr (cdr (cdr a
)))
2127 (math-sqrt (calcFunc-abssqr a
))
2129 (math-hypot (nth 1 a
) (nth 2 a
))
2131 (math-abs (nth 1 a
))
2134 (list 'sdev
(math-abs (nth 1 a
)) (nth 2 a
)))
2135 ((and (eq (car a
) 'intv
) (math-intv-constp a
))
2138 (let* ((nlo (math-neg (nth 2 a
)))
2139 (res (math-compare nlo
(nth 3 a
))))
2141 (math-make-intv (if (memq (nth 1 a
) '(0 1)) 2 3) 0 nlo
))
2143 (math-make-intv (if (eq (nth 1 a
) 0) 2 3) 0 nlo
))
2145 (math-make-intv (if (memq (nth 1 a
) '(0 2)) 2 3)
2147 ((math-looks-negp a
)
2148 (list 'calcFunc-abs
(math-neg a
)))
2149 ((let ((signs (math-possible-signs a
)))
2150 (or (and (memq signs
'(2 4 6)) a
)
2151 (and (memq signs
'(1 3)) (math-neg a
)))))
2152 ((let ((inf (math-infinitep a
)))
2154 (if (equal inf
'(var nan var-nan
))
2156 '(var inf var-inf
)))))
2157 (t (calc-record-why 'numvecp a
)
2158 (list 'calcFunc-abs a
))))
2160 (defalias 'calcFunc-abs
'math-abs
)
2162 (defun math-float-fancy (a)
2163 (cond ((eq (car a
) 'intv
)
2164 (cons (car a
) (cons (nth 1 a
) (mapcar 'math-float
(nthcdr 2 a
)))))
2165 ((and (memq (car a
) '(* /))
2166 (math-numberp (nth 1 a
)))
2167 (list (car a
) (math-float (nth 1 a
))
2168 (list 'calcFunc-float
(nth 2 a
))))
2169 ((and (eq (car a
) '/)
2170 (eq (car (nth 1 a
)) '*)
2171 (math-numberp (nth 1 (nth 1 a
))))
2172 (list '* (math-float (nth 1 (nth 1 a
)))
2173 (list 'calcFunc-float
(list '/ (nth 2 (nth 1 a
)) (nth 2 a
)))))
2174 ((math-infinitep a
) a
)
2175 ((eq (car a
) 'calcFunc-float
) a
)
2176 ((let ((func (assq (car a
) '((calcFunc-floor . calcFunc-ffloor
)
2177 (calcFunc-ceil . calcFunc-fceil
)
2178 (calcFunc-trunc . calcFunc-ftrunc
)
2179 (calcFunc-round . calcFunc-fround
)
2180 (calcFunc-rounde . calcFunc-frounde
)
2181 (calcFunc-roundu . calcFunc-froundu
)))))
2182 (and func
(cons (cdr func
) (cdr a
)))))
2183 (t (math-reject-arg a
'objectp
))))
2185 (defalias 'calcFunc-float
'math-float
)
2187 (defun math-trunc-fancy (a)
2188 (cond ((eq (car a
) 'frac
) (math-quotient (nth 1 a
) (nth 2 a
)))
2189 ((eq (car a
) 'cplx
) (math-trunc (nth 1 a
)))
2190 ((eq (car a
) 'polar
) (math-trunc (math-complex a
)))
2191 ((eq (car a
) 'hms
) (list 'hms
(nth 1 a
) 0 0))
2192 ((eq (car a
) 'date
) (list 'date
(math-trunc (nth 1 a
))))
2194 (if (math-messy-integerp (nth 2 a
))
2195 (math-trunc (math-make-mod (nth 1 a
) (math-trunc (nth 2 a
))))
2196 (math-make-mod (math-trunc (nth 1 a
)) (nth 2 a
))))
2198 (math-make-intv (+ (if (and (equal (nth 2 a
) '(neg (var inf var-inf
)))
2199 (memq (nth 1 a
) '(0 1)))
2201 (if (and (equal (nth 3 a
) '(var inf var-inf
))
2202 (memq (nth 1 a
) '(0 2)))
2204 (if (and (Math-negp (nth 2 a
))
2205 (Math-num-integerp (nth 2 a
))
2206 (memq (nth 1 a
) '(0 1)))
2207 (math-add (math-trunc (nth 2 a
)) 1)
2208 (math-trunc (nth 2 a
)))
2209 (if (and (Math-posp (nth 3 a
))
2210 (Math-num-integerp (nth 3 a
))
2211 (memq (nth 1 a
) '(0 2)))
2212 (math-add (math-trunc (nth 3 a
)) -
1)
2213 (math-trunc (nth 3 a
)))))
2214 ((math-provably-integerp a
) a
)
2216 (math-map-vec (function (lambda (x) (math-trunc x prec
))) a
))
2218 (if (or (math-posp a
) (math-negp a
))
2220 '(var nan var-nan
)))
2221 ((math-to-integer a
))
2222 (t (math-reject-arg a
'numberp
))))
2224 (defun math-trunc-special (a prec
)
2225 (if (Math-messy-integerp prec
)
2226 (setq prec
(math-trunc prec
)))
2228 (math-reject-arg prec
'fixnump
))
2229 (if (and (<= prec
0)
2230 (math-provably-integerp a
))
2232 (calcFunc-scf (math-trunc (let ((calc-prefer-frac t
))
2233 (calcFunc-scf a prec
)))
2236 (defun math-to-integer (a)
2237 (let ((func (assq (car-safe a
) '((calcFunc-ffloor . calcFunc-floor
)
2238 (calcFunc-fceil . calcFunc-ceil
)
2239 (calcFunc-ftrunc . calcFunc-trunc
)
2240 (calcFunc-fround . calcFunc-round
)
2241 (calcFunc-frounde . calcFunc-rounde
)
2242 (calcFunc-froundu . calcFunc-roundu
)))))
2243 (and func
(= (length a
) 2)
2244 (cons (cdr func
) (cdr a
)))))
2246 (defun calcFunc-ftrunc (a &optional prec
)
2247 (if (and (Math-messy-integerp a
)
2248 (or (not prec
) (and (integerp prec
)
2251 (math-float (math-trunc a prec
))))
2253 (defun math-floor-fancy (a)
2254 (cond ((math-provably-integerp a
) a
)
2256 (if (or (math-posp a
)
2257 (and (math-zerop (nth 2 a
))
2258 (math-zerop (nth 3 a
))))
2260 (math-add (math-trunc a
) -
1)))
2261 ((eq (car a
) 'date
) (list 'date
(math-floor (nth 1 a
))))
2263 (math-make-intv (+ (if (and (equal (nth 2 a
) '(neg (var inf var-inf
)))
2264 (memq (nth 1 a
) '(0 1)))
2266 (if (and (equal (nth 3 a
) '(var inf var-inf
))
2267 (memq (nth 1 a
) '(0 2)))
2269 (math-floor (nth 2 a
))
2270 (if (and (Math-num-integerp (nth 3 a
))
2271 (memq (nth 1 a
) '(0 2)))
2272 (math-add (math-floor (nth 3 a
)) -
1)
2273 (math-floor (nth 3 a
)))))
2275 (math-map-vec (function (lambda (x) (math-floor x prec
))) a
))
2277 (if (or (math-posp a
) (math-negp a
))
2279 '(var nan var-nan
)))
2280 ((math-to-integer a
))
2281 (t (math-reject-arg a
'anglep
))))
2283 (defun math-floor-special (a prec
)
2284 (if (Math-messy-integerp prec
)
2285 (setq prec
(math-trunc prec
)))
2287 (math-reject-arg prec
'fixnump
))
2288 (if (and (<= prec
0)
2289 (math-provably-integerp a
))
2291 (calcFunc-scf (math-floor (let ((calc-prefer-frac t
))
2292 (calcFunc-scf a prec
)))
2295 (defun calcFunc-ffloor (a &optional prec
)
2296 (if (and (Math-messy-integerp a
)
2297 (or (not prec
) (and (integerp prec
)
2300 (math-float (math-floor a prec
))))
2302 ;;; Coerce A to be an integer (by truncation toward plus infinity). [I N]
2303 (defun math-ceiling (a &optional prec
) ; [Public]
2305 (if (Math-messy-integerp prec
)
2306 (setq prec
(math-trunc prec
)))
2308 (math-reject-arg prec
'fixnump
))
2309 (if (and (<= prec
0)
2310 (math-provably-integerp a
))
2312 (calcFunc-scf (math-ceiling (let ((calc-prefer-frac t
))
2313 (calcFunc-scf a prec
)))
2315 ((Math-integerp a
) a
)
2316 ((Math-messy-integerp a
) (math-trunc a
))
2319 (math-add (math-trunc a
) 1)
2321 ((math-provably-integerp a
) a
)
2323 (if (or (math-negp a
)
2324 (and (math-zerop (nth 2 a
))
2325 (math-zerop (nth 3 a
))))
2327 (math-add (math-trunc a
) 1)))
2328 ((eq (car a
) 'date
) (list 'date
(math-ceiling (nth 1 a
))))
2330 (math-make-intv (+ (if (and (equal (nth 2 a
) '(neg (var inf var-inf
)))
2331 (memq (nth 1 a
) '(0 1)))
2333 (if (and (equal (nth 3 a
) '(var inf var-inf
))
2334 (memq (nth 1 a
) '(0 2)))
2336 (if (and (Math-num-integerp (nth 2 a
))
2337 (memq (nth 1 a
) '(0 1)))
2338 (math-add (math-floor (nth 2 a
)) 1)
2339 (math-ceiling (nth 2 a
)))
2340 (math-ceiling (nth 3 a
))))
2342 (math-map-vec (function (lambda (x) (math-ceiling x prec
))) a
))
2344 (if (or (math-posp a
) (math-negp a
))
2346 '(var nan var-nan
)))
2347 ((math-to-integer a
))
2348 (t (math-reject-arg a
'anglep
))))
2350 (defalias 'calcFunc-ceil
'math-ceiling
)
2352 (defun calcFunc-fceil (a &optional prec
)
2353 (if (and (Math-messy-integerp a
)
2354 (or (not prec
) (and (integerp prec
)
2357 (math-float (math-ceiling a prec
))))
2359 (defvar math-rounding-mode nil
)
2361 ;;; Coerce A to be an integer (by rounding to nearest integer). [I N] [Public]
2362 (defun math-round (a &optional prec
)
2364 (if (Math-messy-integerp prec
)
2365 (setq prec
(math-trunc prec
)))
2367 (math-reject-arg prec
'fixnump
))
2368 (if (and (<= prec
0)
2369 (math-provably-integerp a
))
2371 (calcFunc-scf (math-round (let ((calc-prefer-frac t
))
2372 (calcFunc-scf a prec
)))
2375 (if (Math-num-integerp a
)
2377 (if (and (Math-negp a
) (not (eq math-rounding-mode
'up
)))
2378 (math-neg (math-round (math-neg a
)))
2379 (setq a
(let ((calc-angle-mode 'deg
)) ; in case of HMS forms
2380 (math-add a
(if (Math-ratp a
)
2383 (if (and (Math-num-integerp a
) (eq math-rounding-mode
'even
))
2385 (setq a
(math-floor a
))
2387 (setq a
(math-sub a
1)))
2390 ((math-provably-integerp a
) a
)
2391 ((eq (car a
) 'date
) (list 'date
(math-round (nth 1 a
))))
2393 (math-floor (math-add a
'(frac 1 2))))
2395 (math-map-vec (function (lambda (x) (math-round x prec
))) a
))
2397 (if (or (math-posp a
) (math-negp a
))
2399 '(var nan var-nan
)))
2400 ((math-to-integer a
))
2401 (t (math-reject-arg a
'anglep
))))
2403 (defalias 'calcFunc-round
'math-round
)
2405 (defsubst calcFunc-rounde
(a &optional prec
)
2406 (let ((math-rounding-mode 'even
))
2407 (math-round a prec
)))
2409 (defsubst calcFunc-roundu
(a &optional prec
)
2410 (let ((math-rounding-mode 'up
))
2411 (math-round a prec
)))
2413 (defun calcFunc-fround (a &optional prec
)
2414 (if (and (Math-messy-integerp a
)
2415 (or (not prec
) (and (integerp prec
)
2418 (math-float (math-round a prec
))))
2420 (defsubst calcFunc-frounde
(a &optional prec
)
2421 (let ((math-rounding-mode 'even
))
2422 (calcFunc-fround a prec
)))
2424 (defsubst calcFunc-froundu
(a &optional prec
)
2425 (let ((math-rounding-mode 'up
))
2426 (calcFunc-fround a prec
)))
2428 ;;; Pull floating-point values apart into mantissa and exponent.
2429 (defun calcFunc-mant (x)
2431 (if (or (Math-ratp x
)
2434 (list 'float
(nth 1 x
) (- 1 (math-numdigs (nth 1 x
)))))
2435 (calc-record-why 'realp x
)
2436 (list 'calcFunc-mant x
)))
2438 (defun calcFunc-xpon (x)
2440 (if (or (Math-ratp x
)
2443 (math-normalize (+ (nth 2 x
) (1- (math-numdigs (nth 1 x
))))))
2444 (calc-record-why 'realp x
)
2445 (list 'calcFunc-xpon x
)))
2447 (defun calcFunc-scf (x n
)
2453 (math-scale-int x n
)
2454 (math-div x
(math-scale-int 1 (- n
)))))
2457 (math-make-frac (math-scale-int (nth 1 x
) n
) (nth 2 x
))
2458 (math-make-frac (nth 1 x
) (math-scale-int (nth 2 x
) (- n
)))))
2459 ((eq (car x
) 'float
)
2460 (math-make-float (nth 1 x
) (+ (nth 2 x
) n
)))
2461 ((memq (car x
) '(cplx sdev
))
2464 (calcFunc-scf (nth 1 x
) n
)
2465 (calcFunc-scf (nth 2 x
) n
))))
2466 ((memq (car x
) '(polar mod
))
2469 (calcFunc-scf (nth 1 x
) n
)
2475 (calcFunc-scf (nth 2 x
) n
)
2476 (calcFunc-scf (nth 3 x
) n
))))
2478 (math-map-vec (function (lambda (x) (calcFunc-scf x n
))) x
))
2482 (calc-record-why 'realp x
)
2483 (list 'calcFunc-scf x n
)))
2484 (if (math-messy-integerp n
)
2485 (if (< (nth 2 n
) 10)
2486 (calcFunc-scf x
(math-trunc n
))
2488 (if (math-integerp n
)
2490 (calc-record-why 'integerp n
)
2491 (list 'calcFunc-scf x n
)))))
2494 (defun calcFunc-incr (x &optional step relative-to
)
2495 (or step
(setq step
1))
2496 (cond ((not (Math-integerp step
))
2497 (math-reject-arg step
'integerp
))
2500 ((eq (car x
) 'float
)
2501 (if (and (math-zerop x
)
2502 (eq (car-safe relative-to
) 'float
))
2504 (calcFunc-scf relative-to
(- 1 calc-internal-prec
)))
2505 (math-add-float x
(math-make-float
2508 (- (math-numdigs (nth 1 x
))
2509 calc-internal-prec
))))))
2511 (if (Math-integerp (nth 1 x
))
2513 (math-add x
(list 'hms
0 0 step
))))
2515 (math-reject-arg x
'realp
))))
2517 (defsubst calcFunc-decr
(x &optional step relative-to
)
2518 (calcFunc-incr x
(math-neg (or step
1)) relative-to
))
2520 (defun calcFunc-percent (x)
2521 (if (math-objectp x
)
2522 (let ((calc-prefer-frac nil
))
2524 (list 'calcFunc-percent x
)))
2526 (defun calcFunc-relch (x y
)
2527 (if (and (math-objectp x
) (math-objectp y
))
2528 (math-div (math-sub y x
) x
)
2529 (list 'calcFunc-relch x y
)))
2531 ;;; Compute the absolute value squared of A. [F N] [Public]
2532 (defun calcFunc-abssqr (a)
2533 (cond ((Math-realp a
)
2536 (math-add (math-sqr (nth 1 a
))
2537 (math-sqr (nth 2 a
))))
2538 ((eq (car a
) 'polar
)
2539 (math-sqr (nth 1 a
)))
2540 ((and (memq (car a
) '(sdev intv
)) (math-constp a
))
2541 (math-sqr (math-abs a
)))
2543 (math-reduce-vec 'math-add
(math-map-vec 'calcFunc-abssqr a
)))
2544 ((math-known-realp a
)
2546 ((let ((inf (math-infinitep a
)))
2548 (math-mul (calcFunc-abssqr (math-infinite-dir a inf
)) inf
))))
2549 (t (calc-record-why 'numvecp a
)
2550 (list 'calcFunc-abssqr a
))))
2552 (defsubst math-sqr
(a)
2557 (defun calcFunc-idiv (a b
) ; [I I I] [Public]
2558 (cond ((and (Math-natnump a
) (Math-natnump b
) (not (eq b
0)))
2559 (math-quotient a b
))
2562 (let ((calc-prefer-frac t
))
2563 (math-floor (math-div a b
)))
2564 (math-reject-arg b
'realp
)))
2565 ((eq (car-safe a
) 'hms
)
2566 (if (eq (car-safe b
) 'hms
)
2567 (let ((calc-prefer-frac t
))
2568 (math-floor (math-div a b
)))
2569 (math-reject-arg b
'hmsp
)))
2570 ((and (or (eq (car-safe a
) 'intv
) (Math-realp a
))
2571 (or (eq (car-safe b
) 'intv
) (Math-realp b
)))
2572 (math-floor (math-div a b
)))
2573 ((or (math-infinitep a
)
2576 (t (math-reject-arg a
'anglep
))))
2579 ;;; Combine two terms being added, if possible.
2580 (defun math-combine-sum (a b nega negb scalar-okay
)
2581 (if (and scalar-okay
(Math-objvecp a
) (Math-objvecp b
))
2582 (math-add-or-sub a b nega negb
)
2583 (let ((amult 1) (bmult 1))
2585 (cond ((and (eq (car a
) '*)
2586 (Math-objectp (nth 1 a
)))
2587 (setq amult
(nth 1 a
)
2589 ((and (eq (car a
) '/)
2590 (Math-objectp (nth 2 a
)))
2591 (setq amult
(if (Math-integerp (nth 2 a
))
2592 (list 'frac
1 (nth 2 a
))
2593 (math-div 1 (nth 2 a
)))
2599 (cond ((and (eq (car b
) '*)
2600 (Math-objectp (nth 1 b
)))
2601 (setq bmult
(nth 1 b
)
2603 ((and (eq (car b
) '/)
2604 (Math-objectp (nth 2 b
)))
2605 (setq bmult
(if (Math-integerp (nth 2 b
))
2606 (list 'frac
1 (nth 2 b
))
2607 (math-div 1 (nth 2 b
)))
2612 (and (if math-simplifying
2616 (if nega
(setq amult
(math-neg amult
)))
2617 (if negb
(setq bmult
(math-neg bmult
)))
2618 (setq amult
(math-add amult bmult
))
2619 (math-mul amult a
))))))
2621 (defun math-add-or-sub (a b aneg bneg
)
2622 (if aneg
(setq a
(math-neg a
)))
2623 (if bneg
(setq b
(math-neg b
)))
2624 (if (or (Math-vectorp a
) (Math-vectorp b
))
2625 (math-normalize (list '+ a b
))
2628 (defvar math-combine-prod-e
'(var e var-e
))
2630 ;;; The following is expanded out four ways for speed.
2631 (defun math-combine-prod (a b inva invb scalar-okay
)
2633 ((or (and inva
(Math-zerop a
))
2634 (and invb
(Math-zerop b
)))
2636 ((and scalar-okay
(Math-objvecp a
) (Math-objvecp b
))
2637 (setq a
(math-mul-or-div a b inva invb
))
2638 (and (Math-objvecp a
)
2640 ((and (eq (car-safe a
) '^
)
2642 (math-looks-negp (nth 2 a
)))
2643 (math-mul (math-pow (nth 1 a
) (math-neg (nth 2 a
))) b
))
2644 ((and (eq (car-safe b
) '^
)
2646 (math-looks-negp (nth 2 b
)))
2647 (math-mul a
(math-pow (nth 1 b
) (math-neg (nth 2 b
)))))
2648 (t (let ((apow 1) (bpow 1))
2650 (cond ((and (eq (car a
) '^
)
2651 (or math-simplifying
2652 (Math-numberp (nth 2 a
))))
2653 (setq apow
(nth 2 a
)
2655 ((eq (car a
) 'calcFunc-sqrt
)
2656 (setq apow
'(frac 1 2)
2658 ((and (eq (car a
) 'calcFunc-exp
)
2659 (or math-simplifying
2660 (Math-numberp (nth 1 a
))))
2661 (setq apow
(nth 1 a
)
2662 a math-combine-prod-e
))))
2663 (and (consp a
) (eq (car a
) 'frac
)
2664 (Math-lessp (nth 1 a
) (nth 2 a
))
2665 (setq a
(math-div 1 a
) apow
(math-neg apow
)))
2667 (cond ((and (eq (car b
) '^
)
2668 (or math-simplifying
2669 (Math-numberp (nth 2 b
))))
2670 (setq bpow
(nth 2 b
)
2672 ((eq (car b
) 'calcFunc-sqrt
)
2673 (setq bpow
'(frac 1 2)
2675 ((and (eq (car b
) 'calcFunc-exp
)
2676 (or math-simplifying
2677 (Math-numberp (nth 1 b
))))
2678 (setq bpow
(nth 1 b
)
2679 b math-combine-prod-e
))))
2680 (and (consp b
) (eq (car b
) 'frac
)
2681 (Math-lessp (nth 1 b
) (nth 2 b
))
2682 (setq b
(math-div 1 b
) bpow
(math-neg bpow
)))
2683 (if inva
(setq apow
(math-neg apow
)))
2684 (if invb
(setq bpow
(math-neg bpow
)))
2685 (or (and (if math-simplifying
2686 (math-commutative-equal a b
)
2688 (let ((sumpow (math-add apow bpow
)))
2689 (and (or (not (Math-integerp a
))
2691 (eq (eq (car-safe apow
) 'frac
)
2692 (eq (car-safe bpow
) 'frac
)))
2694 (and (math-looks-negp sumpow
)
2695 (Math-ratp a
) (Math-posp a
)
2696 (setq a
(math-div 1 a
)
2697 sumpow
(math-neg sumpow
)))
2698 (cond ((equal sumpow
'(frac 1 2))
2699 (list 'calcFunc-sqrt a
))
2700 ((equal sumpow
'(frac -
1 2))
2701 (math-div 1 (list 'calcFunc-sqrt a
)))
2702 ((and (eq a math-combine-prod-e
)
2704 (list 'calcFunc-exp sumpow
))
2708 (inexact-result (list '^ a sumpow
)))))))))
2709 (and math-simplifying-units
2710 math-combining-units
2711 (let* ((ua (math-check-unit-name a
))
2714 (eq ua
(setq ub
(math-check-unit-name b
)))
2716 (setq ua
(if (eq (nth 1 a
) (car ua
))
2718 (nth 1 (assq (aref (symbol-name (nth 1 a
))
2720 math-unit-prefixes
)))
2721 ub
(if (eq (nth 1 b
) (car ub
))
2723 (nth 1 (assq (aref (symbol-name (nth 1 b
))
2725 math-unit-prefixes
))))
2726 (if (Math-lessp ua ub
)
2728 (setq temp a a b b temp
2729 temp ua ua ub ub temp
2730 temp apow apow bpow bpow temp
)))
2731 (math-mul (math-pow (math-div ua ub
) apow
)
2732 (math-pow b
(math-add apow bpow
)))))))
2733 (and (equal apow bpow
)
2734 (Math-natnump a
) (Math-natnump b
)
2735 (cond ((equal apow
'(frac 1 2))
2736 (list 'calcFunc-sqrt
(math-mul a b
)))
2737 ((equal apow
'(frac -
1 2))
2738 (math-div 1 (list 'calcFunc-sqrt
(math-mul a b
))))
2740 (setq a
(math-mul a b
))
2743 (inexact-result (list '^ a apow
)))))))))))
2745 (defun math-mul-or-div (a b ainv binv
)
2746 (if (or (Math-vectorp a
) (Math-vectorp b
))
2750 (list '/ (math-div 1 a
) b
)
2757 (math-div (math-div 1 a
) b
)
2763 (defun math-commutative-equal (a b
)
2764 (if (memq (car-safe a
) '(+ -
))
2765 (and (memq (car-safe b
) '(+ -
))
2766 (let ((bterms nil
) aterms p
)
2767 (math-commutative-collect b nil
)
2768 (setq aterms bterms bterms nil
)
2769 (math-commutative-collect a nil
)
2770 (and (= (length aterms
) (length bterms
))
2775 (while (and p
(not (equal (car aterms
)
2779 (setq bterms
(delq (car p
) bterms
)
2780 aterms
(cdr aterms
)))
2784 (defun math-commutative-collect (b neg
)
2785 (if (eq (car-safe b
) '+)
2787 (math-commutative-collect (nth 1 b
) neg
)
2788 (math-commutative-collect (nth 2 b
) neg
))
2789 (if (eq (car-safe b
) '-
)
2791 (math-commutative-collect (nth 1 b
) neg
)
2792 (math-commutative-collect (nth 2 b
) (not neg
)))
2793 (setq bterms
(cons (if neg
(math-neg b
) b
) bterms
)))))
2795 ;;; calc-arith.el ends here