(* Title: HOL/MicroJava/Comp/Index.thy ID: $Id: Index.thy,v 1.5 2005/06/17 14:13:08 haftmann Exp $ Author: Martin Strecker *) (* Index of variable in list of parameter names and local variables *) theory Index imports AuxLemmas DefsComp begin (*indexing a variable name among all variable declarations in a method body*) constdefs index :: "java_mb => vname => nat" "index == λ (pn,lv,blk,res) v. if v = This then 0 else Suc (length (takeWhile (λ z. z~=v) (pn @ map fst lv)))" lemma index_length_pns: " [| i = index (pns,lvars,blk,res) vn; wf_java_mdecl G C ((mn,pTs),rT, (pns,lvars,blk,res)); vn ∈ set pns|] ==> 0 < i ∧ i < Suc (length pns)" apply (simp add: wf_java_mdecl_def index_def) apply (subgoal_tac "vn ≠ This") apply (auto intro: length_takeWhile) done lemma index_length_lvars: " [| i = index (pns,lvars,blk,res) vn; wf_java_mdecl G C ((mn,pTs),rT, (pns,lvars,blk,res)); vn ∈ set (map fst lvars)|] ==> (length pns) < i ∧ i < Suc((length pns) + (length lvars))" apply (simp add: wf_java_mdecl_def index_def) apply (subgoal_tac "vn ≠ This") apply simp apply (subgoal_tac "∀ x ∈ set pns. (λz. z ≠ vn) x") apply (simp add: takeWhile_append2) apply (subgoal_tac "length (takeWhile (λz. z ≠ vn) (map fst lvars)) < length (map fst lvars)") apply simp apply (rule length_takeWhile) apply simp apply (simp add: map_of_in_set) apply (intro strip notI) apply simp apply blast done (*** index ***) lemma select_at_index : "x ∈ set (gjmb_plns (gmb G C S)) ∨ x = This ==> (the (loc This) # glvs (gmb G C S) loc) ! (index (gmb G C S) x) = the (loc x)" apply (simp only: index_def gjmb_plns_def) apply (case_tac "(gmb G C S)") apply (simp add: galldefs del: set_append map_append) apply (case_tac b, simp add: gmb_def gjmb_lvs_def del: set_append map_append) apply (intro strip) apply (simp del: set_append map_append) apply (frule length_takeWhile) apply (frule_tac f = "(the o loc)" in nth_map) apply simp done lemma lift_if: "(f (if b then t else e)) = (if b then (f t) else (f e))" apply auto done lemma update_at_index: " [| distinct (gjmb_plns (gmb G C S)); x ∈ set (gjmb_plns (gmb G C S)); x ≠ This |] ==> locvars_xstate G C S (Norm (h, l))[index (gmb G C S) x := val] = locvars_xstate G C S (Norm (h, l(x\<mapsto>val)))" apply (simp only: locvars_xstate_def locvars_locals_def index_def) apply (case_tac "(gmb G C S)", simp) apply (case_tac b, simp) apply (rule conjI) apply (simp add: gl_def) apply (intro strip, simp) apply (simp add: galldefs del: set_append map_append) done (* !!!! incomprehensible: why can't List.takeWhile_append2 be applied the same way in the second case as in the first case ? *) lemma index_of_var: "[| xvar ∉ set pns; xvar ∉ set (map fst zs); xvar ≠ This |] ==> index (pns, zs @ ((xvar, xval) # xys), blk, res) xvar = Suc (length pns + length zs)" apply (simp add: index_def) apply (subgoal_tac "(!!x. ((x ∈ (set pns)) ==> ((λz. (z ≠ xvar))x)))") apply (simp add: List.takeWhile_append2) apply (subgoal_tac "(takeWhile (λz. z ≠ xvar) (map fst zs @ xvar # map fst xys)) = map fst zs @ (takeWhile (λz. z ≠ xvar) (xvar # map fst xys))") apply simp apply (rule List.takeWhile_append2) apply auto done (* The following def should replace the conditions in WellType.thy / wf_java_mdecl *) constdefs disjoint_varnames :: "[vname list, (vname × ty) list] => bool" (* This corresponds to the original def in wf_java_mdecl: "disjoint_varnames pns lvars ≡ nodups pns ∧ unique lvars ∧ This ∉ set pns ∧ This ∉ set (map fst lvars) ∧ (∀pn∈set pns. map_of lvars pn = None)" *) "disjoint_varnames pns lvars ≡ distinct pns ∧ unique lvars ∧ This ∉ set pns ∧ This ∉ set (map fst lvars) ∧ (∀pn∈set pns. pn ∉ set (map fst lvars))" lemma index_of_var2: " disjoint_varnames pns (lvars_pre @ (vn, ty) # lvars_post) ==> index (pns, lvars_pre @ (vn, ty) # lvars_post, blk, res) vn = Suc (length pns + length lvars_pre)" apply (simp add: disjoint_varnames_def index_def unique_def distinct_append) apply (subgoal_tac "vn ≠ This", simp) apply (subgoal_tac "takeWhile (λz. z ≠ vn) (map fst lvars_pre @ vn # map fst lvars_post) = map fst lvars_pre @ takeWhile (λz. z ≠ vn) (vn # map fst lvars_post)") apply simp apply (rule List.takeWhile_append2) apply auto done lemma wf_java_mdecl_disjoint_varnames: "wf_java_mdecl G C (S,rT,(pns,lvars,blk,res)) ==> disjoint_varnames pns lvars" apply (case_tac S) apply (simp add: wf_java_mdecl_def disjoint_varnames_def map_of_in_set) done lemma wf_java_mdecl_length_pTs_pns: "wf_java_mdecl G C ((mn, pTs), rT, pns, lvars, blk, res) ==> length pTs = length pns" by (simp add: wf_java_mdecl_def) end
lemma index_length_pns:
[| i = index (pns, lvars, blk, res) vn; wf_java_mdecl G C ((mn, pTs), rT, pns, lvars, blk, res); vn ∈ set pns |] ==> 0 < i ∧ i < Suc (length pns)
lemma index_length_lvars:
[| i = index (pns, lvars, blk, res) vn; wf_java_mdecl G C ((mn, pTs), rT, pns, lvars, blk, res); vn ∈ set (map fst lvars) |] ==> length pns < i ∧ i < Suc (length pns + length lvars)
lemma select_at_index:
x ∈ set (gjmb_plns (gmb G C S)) ∨ x = This ==> (the (loc This) # glvs (gmb G C S) loc) ! index (gmb G C S) x = the (loc x)
lemma lift_if:
f (if b then t else e) = (if b then f t else f e)
lemma update_at_index:
[| distinct (gjmb_plns (gmb G C S)); x ∈ set (gjmb_plns (gmb G C S)); x ≠ This |] ==> locvars_xstate G C S (Norm (h, l))[index (gmb G C S) x := val] = locvars_xstate G C S (Norm (h, l(x |-> val)))
lemma index_of_var:
[| xvar ∉ set pns; xvar ∉ set (map fst zs); xvar ≠ This |] ==> index (pns, zs @ (xvar, xval) # xys, blk, res) xvar = Suc (length pns + length zs)
lemma index_of_var2:
disjoint_varnames pns (lvars_pre @ (vn, ty) # lvars_post) ==> index (pns, lvars_pre @ (vn, ty) # lvars_post, blk, res) vn = Suc (length pns + length lvars_pre)
lemma wf_java_mdecl_disjoint_varnames:
wf_java_mdecl G C (S, rT, pns, lvars, blk, res) ==> disjoint_varnames pns lvars
lemma wf_java_mdecl_length_pTs_pns:
wf_java_mdecl G C ((mn, pTs), rT, pns, lvars, blk, res) ==> length pTs = length pns