added module rat.ML for rational numbers
authorhaftmann
Fri, 14 Oct 2005 14:36:39 +0200
changeset 17848 de5d9d5e99f5
parent 17847 5d5cada76409
child 17849 d7619ccf22e6
added module rat.ML for rational numbers
src/Pure/General/ROOT.ML
src/Pure/General/rat.ML
src/Pure/IsaMakefile
--- a/src/Pure/General/ROOT.ML	Fri Oct 14 13:04:38 2005 +0200
+++ b/src/Pure/General/ROOT.ML	Fri Oct 14 14:36:39 2005 +0200
@@ -16,6 +16,7 @@
 use "symbol.ML";
 use "name_space.ML";
 use "seq.ML";
+use "rat.ML";
 use "position.ML";
 use "path.ML";
 use "url.ML";
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/Pure/General/rat.ML	Fri Oct 14 14:36:39 2005 +0200
@@ -0,0 +1,105 @@
+(*  Title:      Pure/General/rat.ML
+    ID:         $Id$
+    Author:     Tobias Nipkow, TU Muenchen
+
+Canonical implementation of exact rational numbers
+*)
+
+signature RAT =
+sig
+  type rat
+  exception DIVZERO
+  val zero: rat
+  val rat_of_int: int -> rat
+  val rat_of_intinf: IntInf.int -> rat
+  val rat_of_quotient: IntInf.int * IntInf.int -> rat
+  val quotient_of_rat: rat -> IntInf.int * IntInf.int
+  val string_of_rat: rat -> string
+  val eq: rat * rat -> bool
+  val le: rat * rat -> bool
+  val lt: rat * rat -> bool
+  val ord: rat * rat -> order
+  val add: rat * rat -> rat
+  val mult: rat * rat -> rat
+  val neg: rat -> rat
+  val inv: rat -> rat
+  val ge0: rat -> bool
+  val gt0: rat -> bool
+end;
+
+structure Rat: RAT =
+struct
+
+(*keep them normalized!*)
+
+datatype rat = Rat of bool * IntInf.int * IntInf.int;
+
+exception DIVZERO;
+
+val zero = Rat (true, 0, 1);
+
+fun rat_of_intinf i =
+  if i < 0
+  then Rat (false, ~i, 1)
+  else Rat (true, i, 1);
+
+fun rat_of_int i = rat_of_intinf (IntInf.fromInt i);
+
+fun norm (a, 0, q) =
+      Rat (true, 0, 1) (* is that intentional? *)
+  | norm (a, p, q) =
+      let
+        val absp = abs p
+        val m = gcd (absp, q)
+      in Rat(a = (0 <= p), absp div m, q div m) end;
+
+fun common (p1, q1, p2, q2) =
+  let val q' = lcm (q1, q2)
+  in (p1 * (q' div q1), p2 * (q' div q2), q') end
+
+fun rat_of_quotient (p, 0) =
+      raise DIVZERO
+  | rat_of_quotient (p, q) =
+      norm (0 <= q, p, abs q);
+
+fun quotient_of_rat (Rat (a, p, q)) = (if a then p else ~p, q);
+
+fun string_of_rat r =
+  let val (p, q) = quotient_of_rat r
+  in IntInf.toString p ^ "/" ^ IntInf.toString q end;
+
+fun ord (Rat (false, _, _), Rat (true, _, _)) = LESS
+  | ord (Rat (true, _, _), Rat (false, _, _)) = GREATER
+  | ord (Rat (a, p1, q1), Rat (_, p2, q2)) =
+      if p1 = p2 andalso q1 = q2 then EQUAL
+      else let val (r1, r2, _) = common (p1, q1, p2, q2)
+      in if a then IntInf.compare (r1, r2) else IntInf.compare (r2, r1) end;
+
+fun eq r = (ord r = EQUAL);
+
+fun le r = not (ord r = GREATER);
+
+fun lt r = (ord r = LESS);
+
+fun add (Rat (a1, p1, q1), Rat(a2, p2, q2)) =
+  let
+    val (r1, r2, den) = common (p1, q1, p2, q2)
+    val num = (if a1 then r1 else ~r1) + (if a2 then r2 else ~r2)
+  in norm (true, num, den) end;
+
+fun mult (Rat (a1, p1, q1), Rat (a2, p2, q2)) =
+  norm (a1=a2, p1*p2, q1*q2);
+
+fun neg (r as Rat (_, 0, _)) = r
+  | neg (Rat (b, p, q)) =
+      Rat (not b, p, q);
+
+fun inv (Rat (a, 0, q)) =
+      raise DIVZERO
+  | inv (Rat (a, p, q)) =
+      Rat (a, q, p)
+
+fun ge0 (Rat (a, _, _)) = a;
+fun gt0 (Rat (a, p, _)) = a andalso p > 0;
+
+end;
--- a/src/Pure/IsaMakefile	Fri Oct 14 13:04:38 2005 +0200
+++ b/src/Pure/IsaMakefile	Fri Oct 14 14:36:39 2005 +0200
@@ -26,11 +26,13 @@
 $(OUT)/Pure$(ML_SUFFIX): CPure.thy General/ROOT.ML General/alist.ML     \
   General/buffer.ML                                                     \
   General/file.ML General/graph.ML General/heap.ML General/history.ML   \
-  General/name_space.ML        \
+  General/name_space.ML                                                 \
   General/ord_list.ML General/output.ML General/path.ML                 \
   General/position.ML General/pretty.ML General/scan.ML General/seq.ML  \
-  General/source.ML General/stack.ML General/symbol.ML  \
-  General/table.ML General/url.ML General/xml.ML IsaPlanner/focus_term_lib.ML \
+  General/rat.ML                                                        \
+  General/source.ML General/stack.ML General/symbol.ML                  \
+  General/table.ML General/url.ML General/xml.ML                        \
+  IsaPlanner/focus_term_lib.ML                                          \
   IsaPlanner/isa_fterm.ML IsaPlanner/isand.ML IsaPlanner/isaplib.ML     \
   IsaPlanner/rw_inst.ML IsaPlanner/rw_tools.ML IsaPlanner/term_lib.ML   \
   IsaPlanner/upterm_lib.ML Isar/ROOT.ML Isar/antiquote.ML Isar/args.ML  \
@@ -40,7 +42,8 @@
   Isar/isar_syn.ML Isar/isar_thy.ML Isar/locale.ML Isar/method.ML       \
   Isar/net_rules.ML Isar/object_logic.ML Isar/obtain.ML                 \
   Isar/outer_keyword.ML Isar/outer_lex.ML Isar/outer_parse.ML           \
-  Isar/outer_syntax.ML Isar/proof.ML Isar/proof_context.ML Isar/proof_display.ML \
+  Isar/outer_syntax.ML Isar/proof.ML Isar/proof_context.ML              \
+  Isar/proof_display.ML                                                 \
   Isar/proof_history.ML Isar/rule_cases.ML Isar/session.ML              \
   Isar/skip_proof.ML Isar/term_style.ML Isar/thy_header.ML              \
   Isar/toplevel.ML ML-Systems/cpu-timer-basis.ML                        \