src/HOL/Imperative_HOL/Relational.thy
changeset 37709 70fafefbcc98
parent 36057 ca6610908ae9
child 37716 24bb91462892
equal deleted inserted replaced
37706:c63649d8d75b 37709:70fafefbcc98
     7 text {* The crel predicate states that when a computation c runs with the heap h
     7 text {* The crel predicate states that when a computation c runs with the heap h
     8   will result in return value r and a heap h' (if no exception occurs). *}  
     8   will result in return value r and a heap h' (if no exception occurs). *}  
     9 
     9 
    10 definition crel :: "'a Heap \<Rightarrow> heap \<Rightarrow> heap \<Rightarrow> 'a \<Rightarrow> bool"
    10 definition crel :: "'a Heap \<Rightarrow> heap \<Rightarrow> heap \<Rightarrow> 'a \<Rightarrow> bool"
    11 where
    11 where
    12   crel_def': "crel c h h' r \<longleftrightarrow> Heap_Monad.execute c h = (Inl r, h')"
    12   crel_def': "crel c h h' r \<longleftrightarrow> Heap_Monad.execute c h = Some (r, h')"
    13 
    13 
    14 lemma crel_def: -- FIXME
    14 lemma crel_def: -- FIXME
    15   "crel c h h' r \<longleftrightarrow> (Inl r, h') = Heap_Monad.execute c h"
    15   "crel c h h' r \<longleftrightarrow> Some (r, h') = Heap_Monad.execute c h"
    16   unfolding crel_def' by auto
    16   unfolding crel_def' by auto
    17 
    17 
    18 lemma crel_deterministic: "\<lbrakk> crel f h h' a; crel f h h'' b \<rbrakk> \<Longrightarrow> (a = b) \<and> (h' = h'')"
    18 lemma crel_deterministic: "\<lbrakk> crel f h h' a; crel f h h'' b \<rbrakk> \<Longrightarrow> (a = b) \<and> (h' = h'')"
    19 unfolding crel_def' by auto
    19 unfolding crel_def' by auto
    20 
    20 
    26 subsection {* Elimination rules for basic monadic commands *}
    26 subsection {* Elimination rules for basic monadic commands *}
    27 
    27 
    28 lemma crelE[consumes 1]:
    28 lemma crelE[consumes 1]:
    29   assumes "crel (f >>= g) h h'' r'"
    29   assumes "crel (f >>= g) h h'' r'"
    30   obtains h' r where "crel f h h' r" "crel (g r) h' h'' r'"
    30   obtains h' r where "crel f h h' r" "crel (g r) h' h'' r'"
    31   using assms
    31   using assms by (auto simp add: crel_def bindM_def split: option.split_asm)
    32   by (auto simp add: crel_def bindM_def Let_def prod_case_beta split_def Pair_fst_snd_eq split add: sum.split_asm)
       
    33 
    32 
    34 lemma crelE'[consumes 1]:
    33 lemma crelE'[consumes 1]:
    35   assumes "crel (f >> g) h h'' r'"
    34   assumes "crel (f >> g) h h'' r'"
    36   obtains h' r where "crel f h h' r" "crel g h' h'' r'"
    35   obtains h' r where "crel f h h' r" "crel g h' h'' r'"
    37   using assms
    36   using assms
    84 qed
    83 qed
    85 
    84 
    86 lemma crel_heap:
    85 lemma crel_heap:
    87   assumes "crel (Heap_Monad.heap f) h h' r"
    86   assumes "crel (Heap_Monad.heap f) h h' r"
    88   obtains "h' = snd (f h)" "r = fst (f h)"
    87   obtains "h' = snd (f h)" "r = fst (f h)"
    89   using assms
    88   using assms by (cases "f h") (simp add: crel_def)
    90   unfolding heap_def crel_def apfst_def split_def prod_fun_def by simp_all
    89 
    91 
    90 
    92 subsection {* Elimination rules for array commands *}
    91 subsection {* Elimination rules for array commands *}
    93 
    92 
    94 lemma crel_length:
    93 lemma crel_length:
    95   assumes "crel (length a) h h' r"
    94   assumes "crel (length a) h h' r"
   367 unfolding crel_def bindM_def Let_def assert_def
   366 unfolding crel_def bindM_def Let_def assert_def
   368   raise_def return_def prod_case_beta
   367   raise_def return_def prod_case_beta
   369 apply (cases f)
   368 apply (cases f)
   370 apply simp
   369 apply simp
   371 apply (simp add: expand_fun_eq split_def)
   370 apply (simp add: expand_fun_eq split_def)
       
   371 apply (auto split: option.split)
       
   372 apply (erule_tac x="x" in meta_allE)
   372 apply auto
   373 apply auto
   373 apply (case_tac "fst (fun x)")
       
   374 apply (simp_all add: Pair_fst_snd_eq)
       
   375 apply (erule_tac x="x" in meta_allE)
       
   376 apply fastsimp
       
   377 done
   374 done
   378 
   375 
   379 section {* Introduction rules *}
   376 section {* Introduction rules *}
   380 
   377 
   381 subsection {* Introduction rules for basic monadic commands *}
   378 subsection {* Introduction rules for basic monadic commands *}
   500   assumes "\<And> x h h1 h2 h' s z r. crel (f x) h h1 (Inr s) \<Longrightarrow> crel (MREC f g s) h1 h2 z \<Longrightarrow> P s h1 h2 z
   497   assumes "\<And> x h h1 h2 h' s z r. crel (f x) h h1 (Inr s) \<Longrightarrow> crel (MREC f g s) h1 h2 z \<Longrightarrow> P s h1 h2 z
   501     \<Longrightarrow> crel (g x s z) h2 h' r \<Longrightarrow> P x h h' r"
   498     \<Longrightarrow> crel (g x s z) h2 h' r \<Longrightarrow> P x h h' r"
   502   shows "P x h h' r"
   499   shows "P x h h' r"
   503 proof (rule MREC_pinduct[OF assms(1)[unfolded crel_def, symmetric]])
   500 proof (rule MREC_pinduct[OF assms(1)[unfolded crel_def, symmetric]])
   504   fix x h h1 h2 h' s z r
   501   fix x h h1 h2 h' s z r
   505   assume "Heap_Monad.execute (f x) h = (Inl (Inr s), h1)"
   502   assume "Heap_Monad.execute (f x) h = Some (Inr s, h1)"
   506     "Heap_Monad.execute (MREC f g s) h1 = (Inl z, h2)"
   503     "Heap_Monad.execute (MREC f g s) h1 = Some (z, h2)"
   507     "P s h1 h2 z"
   504     "P s h1 h2 z"
   508     "Heap_Monad.execute (g x s z) h2 = (Inl r, h')"
   505     "Heap_Monad.execute (g x s z) h2 = Some (r, h')"
   509   from assms(3)[unfolded crel_def, OF this(1)[symmetric] this(2)[symmetric] this(3) this(4)[symmetric]]
   506   from assms(3)[unfolded crel_def, OF this(1)[symmetric] this(2)[symmetric] this(3) this(4)[symmetric]]
   510   show "P x h h' r" .
   507   show "P x h h' r" .
   511 next
   508 next
   512 qed (auto simp add: assms(2)[unfolded crel_def])
   509 qed (auto simp add: assms(2)[unfolded crel_def])
   513 
   510 
   517   where we only would like to show that the computation does not result in a exception for heap h,
   514   where we only would like to show that the computation does not result in a exception for heap h,
   518   but we do not care about statements about the resulting heap and return value.*}
   515   but we do not care about statements about the resulting heap and return value.*}
   519 
   516 
   520 definition noError :: "'a Heap \<Rightarrow> heap \<Rightarrow> bool"
   517 definition noError :: "'a Heap \<Rightarrow> heap \<Rightarrow> bool"
   521 where
   518 where
   522   "noError c h \<longleftrightarrow> (\<exists>r h'. (Inl r, h') = Heap_Monad.execute c h)"
   519   "noError c h \<longleftrightarrow> (\<exists>r h'. Some (r, h') = Heap_Monad.execute c h)"
   523 
   520 
   524 lemma noError_def': -- FIXME
   521 lemma noError_def': -- FIXME
   525   "noError c h \<longleftrightarrow> (\<exists>r h'. Heap_Monad.execute c h = (Inl r, h'))"
   522   "noError c h \<longleftrightarrow> (\<exists>r h'. Heap_Monad.execute c h = Some (r, h'))"
   526   unfolding noError_def apply auto proof -
   523   unfolding noError_def apply auto proof -
   527   fix r h'
   524   fix r h'
   528   assume "(Inl r, h') = Heap_Monad.execute c h"
   525   assume "Some (r, h') = Heap_Monad.execute c h"
   529   then have "Heap_Monad.execute c h = (Inl r, h')" ..
   526   then have "Heap_Monad.execute c h = Some (r, h')" ..
   530   then show "\<exists>r h'. Heap_Monad.execute c h = (Inl r, h')" by blast
   527   then show "\<exists>r h'. Heap_Monad.execute c h = Some (r, h')" by blast
   531 qed
   528 qed
   532 
   529 
   533 subsection {* Introduction rules for basic monadic commands *}
   530 subsection {* Introduction rules for basic monadic commands *}
   534 
   531 
   535 lemma noErrorI:
   532 lemma noErrorI:
   638   by (auto intro: noError_of_list)
   635   by (auto intro: noError_of_list)
   639 
   636 
   640 (*TODO: move to HeapMonad *)
   637 (*TODO: move to HeapMonad *)
   641 lemma mapM_append:
   638 lemma mapM_append:
   642   "mapM f (xs @ ys) = mapM f xs \<guillemotright>= (\<lambda>xs. mapM f ys \<guillemotright>= (\<lambda>ys. return (xs @ ys)))"
   639   "mapM f (xs @ ys) = mapM f xs \<guillemotright>= (\<lambda>xs. mapM f ys \<guillemotright>= (\<lambda>ys. return (xs @ ys)))"
   643   by (induct xs) (simp_all add: monad_simp)
   640   by (induct xs) simp_all
   644 
   641 
   645 lemma noError_freeze:
   642 lemma noError_freeze:
   646   shows "noError (freeze a) h"
   643   shows "noError (freeze a) h"
   647 unfolding freeze_def
   644 unfolding freeze_def
   648 by (auto intro!: noErrorI noError_length noError_mapM[of _ _ _ "\<lambda>x. get_array a h ! x"]
   645 by (auto intro!: noErrorI noError_length noError_mapM[of _ _ _ "\<lambda>x. get_array a h ! x"]