number.scm 1.5 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283
  1. ; Copyright (c) 1993-2008 by Richard Kelsey and Jonathan Rees. See file COPYING.
  2. ; This is file number.scm.
  3. ;;;; Numbers
  4. (define (inexact? n) (not (exact? n)))
  5. (define (modulo x y)
  6. (let ((r (remainder x y)))
  7. (if (> y 0)
  8. (if (< r 0)
  9. (+ r y)
  10. r)
  11. (if (> r 0)
  12. (+ r y)
  13. r))))
  14. (define (ceiling x)
  15. (- 0 (floor (- 0 x)))) ;floor is primitive
  16. (define (truncate x)
  17. (if (< x 0)
  18. (ceiling x)
  19. (floor x)))
  20. (define (round x)
  21. (let* ((x+1/2 (+ x (/ 1 2)))
  22. (r (floor x+1/2)))
  23. (if (and (= r x+1/2)
  24. (odd? r))
  25. (- r 1)
  26. r)))
  27. ; GCD
  28. (define (gcd . integers)
  29. (reduce (lambda (x y)
  30. (cond ((< x 0) (gcd (- 0 x) y))
  31. ((< y 0) (gcd x (- 0 y)))
  32. ((< x y) (euclid y x))
  33. (else (euclid x y))))
  34. 0
  35. integers))
  36. (define (euclid x y)
  37. (if (= y 0)
  38. (if (and (inexact? y)
  39. (exact? x))
  40. (exact->inexact x)
  41. x)
  42. (euclid y (remainder x y))))
  43. ; LCM
  44. (define (lcm . integers)
  45. (reduce (lambda (x y)
  46. (let ((g (gcd x y)))
  47. (cond ((= g 0) g)
  48. (else (* (quotient (abs x) g) (abs y))))))
  49. 1
  50. integers))
  51. ; Exponentiation.
  52. (define (expt x n)
  53. (if (and (integer? n) (exact? n))
  54. (if (>= n 0)
  55. (raise-to-integer-power x n)
  56. (/ 1 (raise-to-integer-power x (- 0 n))))
  57. (exp (* n (log x)))))
  58. (define (raise-to-integer-power x n)
  59. (if (= n 0)
  60. 1
  61. (let loop ((s x) (i n) (a 1)) ;invariant: a * s^i = x^n
  62. (let ((a (if (odd? i) (* a s) a))
  63. (i (quotient i 2)))
  64. (if (= i 0)
  65. a
  66. (loop (* s s) i a))))))