157 |
157 |
158 |
158 |
159 (* print translation *) |
159 (* print translation *) |
160 |
160 |
161 fun case_tr' (_ :: x :: t :: ts) = |
161 fun case_tr' (_ :: x :: t :: ts) = |
162 let |
162 let |
163 fun mk_clause (Const (@{const_syntax case_abs}, _) $ Abs (s, T, t)) xs used = |
163 fun mk_clause (Const (@{const_syntax case_abs}, _) $ Abs (s, T, t)) xs used = |
164 let val (s', used') = Name.variant s used |
164 let val (s', used') = Name.variant s used |
165 in mk_clause t ((s', T) :: xs) used' end |
165 in mk_clause t ((s', T) :: xs) used' end |
166 | mk_clause (Const (@{const_syntax case_elem}, _) $ pat $ rhs) xs _ = |
166 | mk_clause (Const (@{const_syntax case_elem}, _) $ pat $ rhs) xs _ = |
167 Syntax.const @{syntax_const "_case1"} $ |
167 Syntax.const @{syntax_const "_case1"} $ |
168 subst_bounds (map Syntax_Trans.mark_bound_abs xs, pat) $ |
168 subst_bounds (map Syntax_Trans.mark_bound_abs xs, pat) $ |
169 subst_bounds (map Syntax_Trans.mark_bound_body xs, rhs); |
169 subst_bounds (map Syntax_Trans.mark_bound_body xs, rhs) |
170 |
170 | mk_clause _ _ _ = raise Match; |
171 fun mk_clauses (Const (@{const_syntax case_nil}, _)) = [] |
171 |
172 | mk_clauses (Const (@{const_syntax case_cons}, _) $ t $ u) = |
172 fun mk_clauses (Const (@{const_syntax case_nil}, _)) = [] |
173 mk_clause t [] (Term.declare_term_frees t Name.context) :: |
173 | mk_clauses (Const (@{const_syntax case_cons}, _) $ t $ u) = |
174 mk_clauses u |
174 mk_clause t [] (Term.declare_term_frees t Name.context) :: mk_clauses u |
175 in |
175 | mk_clauses _ = raise Match; |
176 list_comb (Syntax.const @{syntax_const "_case_syntax"} $ x $ |
176 in |
177 foldr1 (fn (t, u) => Syntax.const @{syntax_const "_case2"} $ t $ u) |
177 list_comb (Syntax.const @{syntax_const "_case_syntax"} $ x $ |
178 (mk_clauses t), ts) |
178 foldr1 (fn (t, u) => Syntax.const @{syntax_const "_case2"} $ t $ u) |
179 end; |
179 (mk_clauses t), ts) |
|
180 end |
|
181 | case_tr' _ = raise Match; |
180 |
182 |
181 val trfun_setup' = Sign.print_translation [(@{const_syntax "case_guard"}, K case_tr')]; |
183 val trfun_setup' = Sign.print_translation [(@{const_syntax "case_guard"}, K case_tr')]; |
182 |
184 |
183 |
185 |
184 (* declarations *) |
186 (* declarations *) |
210 |
212 |
211 (*Each pattern carries with it a tag i, which denotes the clause it |
213 (*Each pattern carries with it a tag i, which denotes the clause it |
212 came from. i = ~1 indicates that the clause was added by pattern |
214 came from. i = ~1 indicates that the clause was added by pattern |
213 completion.*) |
215 completion.*) |
214 |
216 |
215 fun add_row_used ((prfx, pats), (tm, tag)) = |
217 fun add_row_used ((prfx, pats), (tm, _)) = |
216 fold Term.declare_term_frees (tm :: pats @ map Free prfx); |
218 fold Term.declare_term_frees (tm :: pats @ map Free prfx); |
217 |
219 |
218 (*try to preserve names given by user*) |
220 (*try to preserve names given by user*) |
219 fun default_name "" (Free (name', _)) = name' |
221 fun default_name "" (Free (name', _)) = name' |
220 | default_name name _ = name; |
222 | default_name name _ = name; |
296 |
298 |
297 fun mk_case ctxt used range_ty = |
299 fun mk_case ctxt used range_ty = |
298 let |
300 let |
299 val get_info = lookup_by_constr_permissive ctxt; |
301 val get_info = lookup_by_constr_permissive ctxt; |
300 |
302 |
301 fun expand constructors used ty ((_, []), _) = raise CASE_ERROR ("mk_case: expand", ~1) |
303 fun expand _ _ _ ((_, []), _) = raise CASE_ERROR ("mk_case: expand", ~1) |
302 | expand constructors used ty (row as ((prfx, p :: ps), (rhs, tag))) = |
304 | expand constructors used ty (row as ((prfx, p :: ps), (rhs, tag))) = |
303 if is_Free p then |
305 if is_Free p then |
304 let |
306 let |
305 val used' = add_row_used row used; |
307 val used' = add_row_used row used; |
306 fun expnd c = |
308 fun expnd c = |
311 |
313 |
312 val (name, _) = Name.variant "a" used; |
314 val (name, _) = Name.variant "a" used; |
313 |
315 |
314 fun mk _ [] = raise CASE_ERROR ("no rows", ~1) |
316 fun mk _ [] = raise CASE_ERROR ("no rows", ~1) |
315 | mk [] (((_, []), (tm, tag)) :: _) = ([tag], tm) (* Done *) |
317 | mk [] (((_, []), (tm, tag)) :: _) = ([tag], tm) (* Done *) |
316 | mk path (rows as ((row as ((_, [Free _]), _)) :: _ :: _)) = mk path [row] |
318 | mk path ((row as ((_, [Free _]), _)) :: _ :: _) = mk path [row] |
317 | mk (u :: us) (rows as ((_, _ :: _), _) :: _) = |
319 | mk (u :: us) (rows as ((_, _ :: _), _) :: _) = |
318 let val col0 = map (fn ((_, p :: _), (_, i)) => (p, i)) rows in |
320 let val col0 = map (fn ((_, p :: _), (_, i)) => (p, i)) rows in |
319 (case Option.map (apfst head_of) (find_first (not o is_Free o fst) col0) of |
321 (case Option.map (apfst head_of) (find_first (not o is_Free o fst) col0) of |
320 NONE => |
322 NONE => |
321 let |
323 let |