clarified singleton_fixate: intersection with supersort is identity, only replace actual type inference parameters;
authorwenzelm
Wed, 09 Nov 2011 22:43:14 +0100
changeset 45432 12cc89f1eb0c
parent 45431 924c2f6dcd05
child 45433 4283f3a57cf5
clarified singleton_fixate: intersection with supersort is identity, only replace actual type inference parameters; tuned reject_other, after_infer_fixate;
src/Pure/Isar/class_declaration.ML
--- a/src/Pure/Isar/class_declaration.ML	Wed Nov 09 21:44:06 2011 +0100
+++ b/src/Pure/Isar/class_declaration.ML	Wed Nov 09 22:43:14 2011 +0100
@@ -116,38 +116,41 @@
     val base_constraints = (map o apsnd)
       (map_type_tfree (K (TVar ((Name.aT, 0), proto_base_sort))) o fst o snd)
         (Class.these_operations thy sups);
-    val reject_bcd_etc = (map o map_atyps) (fn T as TFree (a, _) =>
-          if a = Name.aT then T
-          else error ("No type variable other than " ^ Name.aT ^ " allowed in class specification")
-      | T => T);
+    val reject_other =
+      (tap o exists o Term.exists_subtype)
+        (fn TFree (a, _) =>
+          a <> Name.aT andalso
+            error ("No type variable other than " ^ Name.aT ^ " allowed in class specification")
+        | _ => false);
     fun singleton_fixate Ts =
       let
-        fun extract f = (fold o fold_atyps) f Ts [];
-        val tfrees = extract (fn TFree (v, sort) => insert (op =) (v, sort) | _ => I);
-        val inferred_sort = extract (fn TVar (_, sort) => inter_sort sort | _ => I);
+        val tfrees = fold Term.add_tfreesT Ts [];
+        val inferred_sort = (fold o Term.fold_atyps) (fn TVar (_, S) => inter_sort S | _ => I) Ts [];
         val fixate_sort =
-          if null tfrees then inferred_sort
-          else
-            (case tfrees of
-              [(_, a_sort)] =>
-                if Sorts.sort_le algebra (a_sort, inferred_sort) then
-                  inter_sort a_sort inferred_sort
-                else
-                  error ("Type inference imposes additional sort constraint " ^
-                    Syntax.string_of_sort_global thy inferred_sort ^
-                    " of type parameter " ^ Name.aT ^ " of sort " ^
-                    Syntax.string_of_sort_global thy a_sort)
-            | _ => error "Multiple type variables in class specification");
-      in (map o map_atyps) (K (TFree (Name.aT, fixate_sort))) Ts end;
+          (case tfrees of
+            [] => inferred_sort
+          | [(_, S)] =>
+              if Sorts.sort_le algebra (S, inferred_sort) then S
+              else
+                error ("Type inference imposes additional sort constraint " ^
+                  Syntax.string_of_sort_global thy inferred_sort ^
+                  " of type parameter " ^ Name.aT ^ " of sort " ^
+                  Syntax.string_of_sort_global thy S)
+          | _ => error "Multiple type variables in class specification");
+        val fixateT = TFree (Name.aT, fixate_sort);
+      in
+        (map o map_atyps)
+          (fn T as TVar (xi, _) => if Type_Infer.is_param xi then fixateT else T | T => T) Ts
+      end;
     fun after_infer_fixate Ts =
       let
-        val S' =
+        val fixate_sort =
           (fold o fold_atyps)
             (fn TVar (xi, S) => if Type_Infer.is_param xi then inter_sort S else I | _ => I) Ts [];
       in
         (map o map_atyps)
           (fn T as TVar (xi, _) =>
-              if Type_Infer.is_param xi then Type_Infer.param 0 (Name.aT, S') else T
+              if Type_Infer.is_param xi then Type_Infer.param 0 (Name.aT, fixate_sort) else T
             | T => T) Ts
       end;
 
@@ -157,7 +160,7 @@
     val init_class_body =
       fold (Proof_Context.add_const_constraint o apsnd SOME) base_constraints
       #> Class.redeclare_operations thy sups
-      #> Context.proof_map (Syntax_Phases.typ_check 10 "reject_bcd_etc" (K reject_bcd_etc))
+      #> Context.proof_map (Syntax_Phases.typ_check 10 "reject_other" (K reject_other))
       #> Context.proof_map (Syntax_Phases.typ_check ~10 "singleton_fixate" (K singleton_fixate));
     val ((raw_supparams, _, raw_inferred_elems), _) =
       Proof_Context.init_global thy