rat.fun 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960
  1. #comment -[
  2. Here are some operations on rational numbers, represented as
  3. (numerator,denominator) of types integer and natural,
  4. respectively. The compiler recognizes rationals in this form as type
  5. q, making them printable with %qP, among other things.
  6. Copyright (C) 2007-2009 Dennis Furey]-
  7. #import std
  8. #import nat
  9. #import int
  10. #library+
  11. #optimize+
  12. abs = ^|/int-abs ~&
  13. difference = sum^|/~& negation
  14. inverse = ^\int-abs@l (-1?=l/int-negation@r ~&r)^/int-sgn@l ~&r
  15. negation = ^|/int-negation ~&
  16. quotient = product^|/~& inverse
  17. product = int-quotient^~brlXPlrGO(gcd^|/int-abs ~&,~&)+ @bbI ^|/int-product nat-product
  18. sum = int-quotient^~brlXPlrGO(gcd^|/int-abs ~&,~&)+ ^\nat-product@br int-sum+ int-product~~llPrrPXlrPrlPXX
  19. rleq = ^(int-sgn~~bl,~&); ~&l-={(0,1),(-1,0),(-1,1),(0,0)}!| ==@l&& zleq+ int-product~~rllPrrPXlrPrlPXX
  20. simplified = (==?l/~&r @r ^|\~& ~&i&& --<0>)^/int-sgn~~ int-abs~~; int-quotient^~brlXPlrGO/gcd ~&
  21. power = # returns a^b for rational a and b if the result is rational, () otherwise
  22. (int-sgn== -1)^?arl/(^|R(~&,^|/~& abs); ~&i&& inverse) @a -!sgn@ll~=-1,odd@rr!-&& -+
  23. ~&r&& ~&l?(negation@r,~&r); int-quotient^~brlXPlrGO/gcd ~&,
  24. ^/-&sgn@ll==-1,odd@rl&- abs~~; (both ^E/~&ll nat-power@rlrPX)&&~&br+ (@rlX ^/~& root)^~G/~&rr ~~rlPlG nat-power@rlX+-
  25. #library-
  26. smag = int-sgn==-1?l\~&NiX ~&NNX+ abs
  27. #library+
  28. fixed =
  29. "n". smag; ~&rlZrB?/<'0.'--(`0!* iota "n")>! :\<>+ -+
  30. @NxX ~&/"n"; -+^T/(~&rrx||'0'!) :/`.+ ~&rl,~&l-> ^|/predecessor ~&r?/~&rhPlCrrPX ~&\''+ @l ~&/`0+-,
  31. ~&h+ %nP+ nat-quotient^\~&rr @rl ~&/"n"; ~&r+ ~&l-> ^|/predecessor tenfold+-
  32. scientific = # takes a number to a rational printer in scientific notation with that number of decimal places
  33. successor; "n". smag; ~&rlZrB?/<'0.'--(~&itB `0!* iota "n")--'e+0'>! :\<>+ -+
  34. ^T(^T/~&rll :/`.+ ~&rlr,^T\-+~&t?/~& :/`0,~&h,%nP,~&rrPlY+- ~&rr?/'e-'! 'e+'!),
  35. (->~&lrllryPXPrXPX ~&rlr; //leql 0!* iota "n")+ ~&rllPllt2B-> ^/successor+~&l ~&rllyPlzPrCXPrX,
  36. ~&l-> ^/predecessor+~&l ~&r; ~&llPllt2B?/~&llyPlzPrCXPrX ^/~&l successor+~&r,
  37. ^(~&l,~&r; ~&\0+ ~&lrtPX+ ~=`.-~)^/~&lr ~&NllPrXX; ~&rlZrB?/<'0.'--(`0!* iota "n")>! -+
  38. @NxX ~&/"n"; -+^T/(~&rrx||'0'!) :/`.+ ~&rl,~&l-> ^|/predecessor ~&r?/~&rhPlCrrPX ~&\''+ @l ~&/`0+-,
  39. ~&h+ %nP+ nat-quotient^\~&rr @rl ~&/"n"; ~&r+ ~&l-> ^|/predecessor tenfold+-,
  40. ~&r; ^\~&r ~&l+ (leql+~&llPrX-> ^\~&r ^/tenfold+~&ll successor+~&lr)^/~&lNX ~&r; //-- iota double double successor "n"+-
  41. engineering = # takes a number to a rational printer in engineering notation with that number of decimal places
  42. iota2?<(2!,~&); scientific; //+ :^\~&t @h -+
  43. ^T(^T/~&ll :/`.+ ~&lr,^T\-+~&t?/~& :/`0,~&h,%nP,~&rr+- :/`e+ ~&rl|| '+'!),
  44. (remainder\3+ ~&rr)-> ^\^(~&rl,~&rl?/successor@rr predecessor@rr) @l ~&r?/~&lrhPNCTrtPX ^\~&r --'0'+ ~&l,
  45. ~=`e~-; ^/(~&lrtPX+ ~=`.-~+ ~&ly) @r ^|(~&,%np+~&iNC)+ `-?=h/~&hNCtX ~&NtX+-