93 have "x\<sharp>L" by fact |
93 have "x\<sharp>L" by fact |
94 show "Var z[x::=N][y::=L] = Var z[y::=L][x::=N[y::=L]]" (is "?LHS = ?RHS") |
94 show "Var z[x::=N][y::=L] = Var z[y::=L][x::=N[y::=L]]" (is "?LHS = ?RHS") |
95 proof - |
95 proof - |
96 { (*Case 1.1*) |
96 { (*Case 1.1*) |
97 assume "z=x" |
97 assume "z=x" |
98 have "(1)": "?LHS = N[y::=L]" using `z=x` by simp |
98 have "(1)": "?LHS = N[y::=L]" using \<open>z=x\<close> by simp |
99 have "(2)": "?RHS = N[y::=L]" using `z=x` `x\<noteq>y` by simp |
99 have "(2)": "?RHS = N[y::=L]" using \<open>z=x\<close> \<open>x\<noteq>y\<close> by simp |
100 from "(1)" "(2)" have "?LHS = ?RHS" by simp |
100 from "(1)" "(2)" have "?LHS = ?RHS" by simp |
101 } |
101 } |
102 moreover |
102 moreover |
103 { (*Case 1.2*) |
103 { (*Case 1.2*) |
104 assume "z=y" and "z\<noteq>x" |
104 assume "z=y" and "z\<noteq>x" |
105 have "(1)": "?LHS = L" using `z\<noteq>x` `z=y` by simp |
105 have "(1)": "?LHS = L" using \<open>z\<noteq>x\<close> \<open>z=y\<close> by simp |
106 have "(2)": "?RHS = L[x::=N[y::=L]]" using `z=y` by simp |
106 have "(2)": "?RHS = L[x::=N[y::=L]]" using \<open>z=y\<close> by simp |
107 have "(3)": "L[x::=N[y::=L]] = L" using `x\<sharp>L` by (simp add: forget) |
107 have "(3)": "L[x::=N[y::=L]] = L" using \<open>x\<sharp>L\<close> by (simp add: forget) |
108 from "(1)" "(2)" "(3)" have "?LHS = ?RHS" by simp |
108 from "(1)" "(2)" "(3)" have "?LHS = ?RHS" by simp |
109 } |
109 } |
110 moreover |
110 moreover |
111 { (*Case 1.3*) |
111 { (*Case 1.3*) |
112 assume "z\<noteq>x" and "z\<noteq>y" |
112 assume "z\<noteq>x" and "z\<noteq>y" |
113 have "(1)": "?LHS = Var z" using `z\<noteq>x` `z\<noteq>y` by simp |
113 have "(1)": "?LHS = Var z" using \<open>z\<noteq>x\<close> \<open>z\<noteq>y\<close> by simp |
114 have "(2)": "?RHS = Var z" using `z\<noteq>x` `z\<noteq>y` by simp |
114 have "(2)": "?RHS = Var z" using \<open>z\<noteq>x\<close> \<open>z\<noteq>y\<close> by simp |
115 from "(1)" "(2)" have "?LHS = ?RHS" by simp |
115 from "(1)" "(2)" have "?LHS = ?RHS" by simp |
116 } |
116 } |
117 ultimately show "?LHS = ?RHS" by blast |
117 ultimately show "?LHS = ?RHS" by blast |
118 qed |
118 qed |
119 next |
119 next |
123 have "x\<sharp>L" by fact |
123 have "x\<sharp>L" by fact |
124 have fs: "z\<sharp>x" "z\<sharp>y" "z\<sharp>N" "z\<sharp>L" by fact+ |
124 have fs: "z\<sharp>x" "z\<sharp>y" "z\<sharp>N" "z\<sharp>L" by fact+ |
125 hence "z\<sharp>N[y::=L]" by (simp add: fresh_fact) |
125 hence "z\<sharp>N[y::=L]" by (simp add: fresh_fact) |
126 show "(Lam [z].M1)[x::=N][y::=L] = (Lam [z].M1)[y::=L][x::=N[y::=L]]" (is "?LHS=?RHS") |
126 show "(Lam [z].M1)[x::=N][y::=L] = (Lam [z].M1)[y::=L][x::=N[y::=L]]" (is "?LHS=?RHS") |
127 proof - |
127 proof - |
128 have "?LHS = Lam [z].(M1[x::=N][y::=L])" using `z\<sharp>x` `z\<sharp>y` `z\<sharp>N` `z\<sharp>L` by simp |
128 have "?LHS = Lam [z].(M1[x::=N][y::=L])" using \<open>z\<sharp>x\<close> \<open>z\<sharp>y\<close> \<open>z\<sharp>N\<close> \<open>z\<sharp>L\<close> by simp |
129 also from ih have "\<dots> = Lam [z].(M1[y::=L][x::=N[y::=L]])" using `x\<noteq>y` `x\<sharp>L` by simp |
129 also from ih have "\<dots> = Lam [z].(M1[y::=L][x::=N[y::=L]])" using \<open>x\<noteq>y\<close> \<open>x\<sharp>L\<close> by simp |
130 also have "\<dots> = (Lam [z].(M1[y::=L]))[x::=N[y::=L]]" using `z\<sharp>x` `z\<sharp>N[y::=L]` by simp |
130 also have "\<dots> = (Lam [z].(M1[y::=L]))[x::=N[y::=L]]" using \<open>z\<sharp>x\<close> \<open>z\<sharp>N[y::=L]\<close> by simp |
131 also have "\<dots> = ?RHS" using `z\<sharp>y` `z\<sharp>L` by simp |
131 also have "\<dots> = ?RHS" using \<open>z\<sharp>y\<close> \<open>z\<sharp>L\<close> by simp |
132 finally show "?LHS = ?RHS" . |
132 finally show "?LHS = ?RHS" . |
133 qed |
133 qed |
134 next |
134 next |
135 case (App M1 M2) (* case 3: applications *) |
135 case (App M1 M2) (* case 3: applications *) |
136 thus "(App M1 M2)[x::=N][y::=L] = (App M1 M2)[y::=L][x::=N[y::=L]]" by simp |
136 thus "(App M1 M2)[x::=N][y::=L] = (App M1 M2)[y::=L][x::=N[y::=L]]" by simp |
141 shows "M[x::=N][y::=L] = M[y::=L][x::=N[y::=L]]" |
141 shows "M[x::=N][y::=L] = M[y::=L][x::=N[y::=L]]" |
142 using asm |
142 using asm |
143 by (nominal_induct M avoiding: x y N L rule: lam.strong_induct) |
143 by (nominal_induct M avoiding: x y N L rule: lam.strong_induct) |
144 (auto simp add: fresh_fact forget) |
144 (auto simp add: fresh_fact forget) |
145 |
145 |
146 section {* Beta Reduction *} |
146 section \<open>Beta Reduction\<close> |
147 |
147 |
148 inductive |
148 inductive |
149 "Beta" :: "lam\<Rightarrow>lam\<Rightarrow>bool" (" _ \<longrightarrow>\<^sub>\<beta> _" [80,80] 80) |
149 "Beta" :: "lam\<Rightarrow>lam\<Rightarrow>bool" (" _ \<longrightarrow>\<^sub>\<beta> _" [80,80] 80) |
150 where |
150 where |
151 b1[intro]: "s1\<longrightarrow>\<^sub>\<beta>s2 \<Longrightarrow> (App s1 t)\<longrightarrow>\<^sub>\<beta>(App s2 t)" |
151 b1[intro]: "s1\<longrightarrow>\<^sub>\<beta>s2 \<Longrightarrow> (App s1 t)\<longrightarrow>\<^sub>\<beta>(App s2 t)" |
171 and a2: "M2\<longrightarrow>\<^sub>\<beta>\<^sup>* M3" |
171 and a2: "M2\<longrightarrow>\<^sub>\<beta>\<^sup>* M3" |
172 shows "M1 \<longrightarrow>\<^sub>\<beta>\<^sup>* M3" |
172 shows "M1 \<longrightarrow>\<^sub>\<beta>\<^sup>* M3" |
173 using a2 a1 |
173 using a2 a1 |
174 by (induct) (auto) |
174 by (induct) (auto) |
175 |
175 |
176 section {* One-Reduction *} |
176 section \<open>One-Reduction\<close> |
177 |
177 |
178 inductive |
178 inductive |
179 One :: "lam\<Rightarrow>lam\<Rightarrow>bool" (" _ \<longrightarrow>\<^sub>1 _" [80,80] 80) |
179 One :: "lam\<Rightarrow>lam\<Rightarrow>bool" (" _ \<longrightarrow>\<^sub>1 _" [80,80] 80) |
180 where |
180 where |
181 o1[intro!]: "M\<longrightarrow>\<^sub>1M" |
181 o1[intro!]: "M\<longrightarrow>\<^sub>1M" |
285 (\<exists>s1 s2. M = s1[a::=s2] \<and> t1 \<longrightarrow>\<^sub>1 s1 \<and> t2 \<longrightarrow>\<^sub>1 s2)" |
285 (\<exists>s1 s2. M = s1[a::=s2] \<and> t1 \<longrightarrow>\<^sub>1 s1 \<and> t2 \<longrightarrow>\<^sub>1 s2)" |
286 using a |
286 using a |
287 by (cases rule: One.strong_cases [where a="a" and aa="a"]) |
287 by (cases rule: One.strong_cases [where a="a" and aa="a"]) |
288 (auto dest: one_abs simp add: lam.inject abs_fresh alpha fresh_prod) |
288 (auto dest: one_abs simp add: lam.inject abs_fresh alpha fresh_prod) |
289 |
289 |
290 text {* first case in Lemma 3.2.4*} |
290 text \<open>first case in Lemma 3.2.4\<close> |
291 |
291 |
292 lemma one_subst_aux: |
292 lemma one_subst_aux: |
293 assumes a: "N\<longrightarrow>\<^sub>1N'" |
293 assumes a: "N\<longrightarrow>\<^sub>1N'" |
294 shows "M[x::=N] \<longrightarrow>\<^sub>1 M[x::=N']" |
294 shows "M[x::=N] \<longrightarrow>\<^sub>1 M[x::=N']" |
295 using a |
295 using a |