278 text {* |
278 text {* |
279 which indeed proves the lemma. |
279 which indeed proves the lemma. |
280 |
280 |
281 While the generic proof for the induction principle is relatively simple, |
281 While the generic proof for the induction principle is relatively simple, |
282 it is a bit harder to set up the goals just from the given introduction |
282 it is a bit harder to set up the goals just from the given introduction |
283 rules. For this we have to construct |
283 rules. For this we have to construct for each predicate @{text "pred"} |
284 |
284 |
285 @{text [display] |
285 @{text [display] |
286 "\<And>\<^raw:$zs$>. pred \<^raw:$zs$> \<Longrightarrow> rules[preds := \<^raw:$Ps$>] \<Longrightarrow> \<^raw:$P$> \<^raw:$zs$>"} |
286 "\<And>\<^raw:$zs$>. pred \<^raw:$zs$> \<Longrightarrow> rules[preds := \<^raw:$Ps$>] \<Longrightarrow> \<^raw:$P$>\<^raw:$zs$>"} |
287 |
287 |
288 where the given predicates are replaced by new ones written |
288 where the given predicates @{text preds} are replaced by new distinct |
289 as @{text "\<^raw:$Ps$>"}, and also generate new variables |
289 ones written as @{text "\<^raw:$Ps$>"}, and also need to be applied to |
290 @{text "\<^raw:$zs$>"}. |
290 new variables @{text "\<^raw:$zs$>"}. |
291 *} |
291 |
292 |
292 The function below expects that the rules are already appropriately |
293 ML %linenosgray{* fun prove_induction lthy defs rules cnewpreds ((pred, newpred), tys) = |
293 replaced. The argument @{text "mrules"} stands for these modified |
|
294 introduction rules; @{text cnewpreds} are the certified terms coresponding |
|
295 to the variables @{text "\<^raw:$Ps$>"}; @{text "pred"} is the predicate for |
|
296 which we prove the introduction principle; @{text "newpred"} is its |
|
297 replacement and @{text "tys"} are the types of its argument. |
|
298 *} |
|
299 |
|
300 ML %linenosgray{* fun prove_induction lthy defs mrules cnewpreds ((pred, newpred), tys) = |
294 let |
301 let |
295 val zs = replicate (length tys) "z" |
302 val zs = replicate (length tys) "z" |
296 val (newargnames, lthy') = Variable.variant_fixes zs lthy; |
303 val (newargnames, lthy') = Variable.variant_fixes zs lthy; |
297 val newargs = map Free (newargnames ~~ tys) |
304 val newargs = map Free (newargnames ~~ tys) |
298 |
305 |
299 val prem = HOLogic.mk_Trueprop (list_comb (pred, newargs)) |
306 val prem = HOLogic.mk_Trueprop (list_comb (pred, newargs)) |
300 val goal = Logic.list_implies |
307 val goal = Logic.list_implies |
301 (rules, HOLogic.mk_Trueprop (list_comb (newpred, newargs))) |
308 (mrules, HOLogic.mk_Trueprop (list_comb (newpred, newargs))) |
302 in |
309 in |
303 Goal.prove lthy' [] [prem] goal |
310 Goal.prove lthy' [] [prem] goal |
304 (fn {prems, ...} => induction_tac defs prems cnewpreds) |
311 (fn {prems, ...} => induction_tac defs prems cnewpreds) |
305 |> singleton (ProofContext.export lthy' lthy) |
312 |> singleton (ProofContext.export lthy' lthy) |
306 end *} |
313 end *} |
307 |
314 |
308 text {* *} |
315 text {* |
|
316 In Line 3 we produce a list of names @{text "\<^raw:$zs$>"} according to the type |
|
317 list. Line 4 makes these names unique and declare them as \emph{free} (but fixed) |
|
318 variables. These variables are free in the new theory @{text "lthy'"}. In Line 5 |
|
319 we just construct the terms corresponding to the variables. The term variables are |
|
320 applied to the predicate in Line 7 (this is the first premise |
|
321 @{text "pred \<^raw:$zs$>"} of the induction principle). In Line 8 and 9 |
|
322 we first the term @{text "\<^raw:$P$>\<^raw:$zs$>"} and then add |
|
323 the (modified) introduction rules as premises. |
|
324 |
|
325 In Line 11 we set up the goal to be proved; call the induction tactic in |
|
326 Line 13. This returns a theorem. However, it is a theorem proved inside |
|
327 the local theory @{text "lthy'"} where the variables @{text "\<^raw:$zs$>"} are |
|
328 fixed, but free. By exporting this theorem from @{text "lthy'"} (which does contain |
|
329 the @{text "\<^raw:$zs$>"} as free) to @{text "lthy"} (which does not), we |
|
330 obtain the desired quantifications @{text "\<And>\<^raw:$zs$>"}. |
|
331 |
|
332 So it is left to produce the modified rules and |
|
333 *} |
309 |
334 |
310 ML %linenosgray{*fun inductions rules defs preds tyss lthy1 = |
335 ML %linenosgray{*fun inductions rules defs preds tyss lthy1 = |
311 let |
336 let |
312 val Ps = replicate (length preds) "P" |
337 val Ps = replicate (length preds) "P" |
313 val (newprednames, lthy2) = Variable.variant_fixes Ps lthy1 |
338 val (newprednames, lthy2) = Variable.variant_fixes Ps lthy1 |