1 (* ========================================================================= *)
2 (* Analysis of solutions to Pell equation *)
3 (* ========================================================================= *)
5 needs "Library/analysis.ml";;
6 needs "Library/transc.ml";;
7 needs "Library/prime.ml";;
11 let PELL_INDUCTION = prove
12 (`P 0 /\ P 1 /\ (!n. P n /\ P (n + 1) ==> P(n + 2)) ==> !n. P n`,
14 SUBGOAL_THEN `!n. P n /\ P(n + 1)` (fun th -> REWRITE_TAC[th]) THEN
15 INDUCT_TAC THEN ASM_REWRITE_TAC[ADD_CLAUSES] THEN
16 ASM_SIMP_TAC[ADD1; ARITH_RULE `SUC(n + 1) = n + 2`]);;
18 (* ------------------------------------------------------------------------- *)
19 (* Useful number-theoretic basics *)
20 (* ------------------------------------------------------------------------- *)
22 let ROOT_NONPOWER = prove
23 (`!p q d n. ~(q = 0) /\ (p EXP n = d * q EXP n) ==> ?a. d = a EXP n`,
25 ASM_CASES_TAC `n = 0` THEN ASM_SIMP_TAC[EXP; MULT_CLAUSES] THEN
27 MP_TAC(SPECL [`n:num`; `q:num`; `p:num`] DIVIDES_EXP2_REV) THEN
28 ASM_REWRITE_TAC[divides; LEFT_IMP_EXISTS_THM] THEN
29 DISCH_THEN(MP_TAC o SPEC `d:num`) THEN
30 REWRITE_TAC[EQT_INTRO(SPEC_ALL MULT_SYM)] THEN
31 ONCE_REWRITE_TAC[MULT_SYM] THEN
32 DISCH_THEN(X_CHOOSE_THEN `a:num` SUBST_ALL_TAC) THEN
33 EXISTS_TAC `a:num` THEN
34 UNDISCH_TAC `(a * q) EXP n = d * q EXP n` THEN
35 ASM_SIMP_TAC[MULT_EXP; EQ_MULT_RCANCEL; EXP_EQ_0]);;
37 let INTEGER_SUB_LEMMA = prove
38 (`!x y. ?n. (&x - &y) pow 2 = &n pow 2`,
40 DISJ_CASES_THEN MP_TAC (SPECL [`&x`; `&y`] REAL_LE_TOTAL) THEN
41 REWRITE_TAC[REAL_OF_NUM_LE] THEN DISCH_TAC THENL
42 [EXISTS_TAC `y - x:num`; EXISTS_TAC `x - y:num`] THEN
43 ASM_SIMP_TAC[GSYM REAL_OF_NUM_SUB] THEN
44 REWRITE_TAC[REAL_POW_2] THEN REAL_ARITH_TAC);;
46 let SQRT_LINEAR_EQ = prove
49 ==> ((&u + &v * sqrt(&a pow 2 - &1) = &x + &y * sqrt(&a pow 2 - &1)) <=>
51 REPEAT STRIP_TAC THEN EQ_TAC THEN SIMP_TAC[] THEN
52 REWRITE_TAC[REAL_ARITH `(a + b = c + d) <=> (a - c = d - b)`] THEN
53 REWRITE_TAC[GSYM REAL_SUB_RDISTRIB] THEN
54 DISCH_THEN(MP_TAC o C AP_THM `2` o AP_TERM `(pow)`) THEN
55 REWRITE_TAC[REAL_POW_MUL] THEN
56 ASM_SIMP_TAC[SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1; REAL_OF_NUM_LE;
57 ARITH_RULE `2 <= a ==> 1 <= a`] THEN
58 X_CHOOSE_TAC `p:num` (SPECL [`u:num`; `x:num`] INTEGER_SUB_LEMMA) THEN
59 X_CHOOSE_TAC `q:num` (SPECL [`y:num`; `v:num`] INTEGER_SUB_LEMMA) THEN
60 ASM_REWRITE_TAC[] THEN
61 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` SUBST1_TAC THENL
62 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
63 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
64 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
65 ARITH_RULE `2 <= a ==> 1 <= a`]; ALL_TAC] THEN
66 REWRITE_TAC[REAL_OF_NUM_POW; REAL_OF_NUM_MUL; REAL_OF_NUM_EQ] THEN
68 MP_TAC(SPECL [`p:num`; `q:num`; `a EXP 2 - 1`; `2`] ROOT_NONPOWER) THEN
69 ASM_REWRITE_TAC[EQT_INTRO(SPEC_ALL MULT_SYM)] THEN
70 MATCH_MP_TAC(TAUT `~b /\ (a ==> c) ==> ((~a ==> b) ==> c)`) THEN
72 [DISCH_THEN(X_CHOOSE_THEN `b:num` MP_TAC) THEN
73 DISCH_THEN(MP_TAC o MATCH_MP
74 (ARITH_RULE `(a - 1 = b) ==> 1 < a ==> (a - b = 1)`)) THEN
75 SUBST1_TAC(SYM(SPEC `a:num` (CONJUNCT1 EXP))) THEN
76 ASM_REWRITE_TAC[LT_EXP; ARITH_LE; ARITH_LT] THEN
78 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
79 `(a - b = 1) ==> (a = b + 1)`)) THEN
80 REWRITE_TAC[GSYM REAL_OF_NUM_EQ; GSYM REAL_OF_NUM_ADD; GSYM
82 REWRITE_TAC[REAL_POW_2] THEN
83 DISCH_THEN(MP_TAC o MATCH_MP
84 (REAL_ARITH `(a * a = b * b + &1) ==> ((a + b) * (a - b) = &1)`)) THEN
85 DISCH_THEN(MP_TAC o C AP_THM `2` o AP_TERM `(pow)`) THEN
86 REWRITE_TAC[REAL_POW_MUL] THEN
87 X_CHOOSE_TAC `c:num` (SPECL [`a:num`; `b:num`] INTEGER_SUB_LEMMA) THEN
88 ASM_REWRITE_TAC[] THEN
89 REWRITE_TAC[GSYM REAL_POW_MUL] THEN
90 REWRITE_TAC[REAL_OF_NUM_POW; REAL_OF_NUM_MUL; REAL_OF_NUM_ADD] THEN
91 REWRITE_TAC[REAL_OF_NUM_EQ; EXP_ONE; EXP_EQ_1; MULT_EQ_1; ARITH_EQ] THEN
92 UNDISCH_TAC `2 <= a` THEN ARITH_TAC;
93 DISCH_THEN SUBST_ALL_TAC THEN
94 UNDISCH_TAC `p EXP 2 = 0 EXP 2 * (a EXP 2 - 1)` THEN
95 REWRITE_TAC[ARITH; MULT_CLAUSES; EXP_EQ_0] THEN
96 DISCH_THEN SUBST_ALL_TAC THEN
97 UNDISCH_TAC `(&u - &x) pow 2 = &0 pow 2` THEN
98 UNDISCH_TAC `(&y - &v) pow 2 = &0 pow 2` THEN
99 CONV_TAC REAL_RAT_REDUCE_CONV THEN
100 REWRITE_TAC[REAL_POW_EQ_0; ARITH_EQ; REAL_SUB_0] THEN
101 SIMP_TAC[REAL_OF_NUM_EQ]]);;
103 (* ------------------------------------------------------------------------- *)
104 (* Recurrence defining the solutions. *)
105 (* ------------------------------------------------------------------------- *)
109 (`!a. ?X. !n. X n = if n = 0 then 1
111 else 2 * a * X(n-1) - X(n-2)`,
112 GEN_TAC THEN MATCH_MP_TAC(MATCH_MP WF_REC WF_num) THEN
113 REPEAT STRIP_TAC THEN
114 REPEAT(COND_CASES_TAC THEN ASM_REWRITE_TAC[]) THEN
116 ASM_SIMP_TAC[ARITH_RULE `n - m < n <=> ~(m = 0) /\ ~(n = 0)`; ARITH_EQ]) in
117 new_specification ["X"] (REWRITE_RULE[SKOLEM_THM] th);;
119 let X_CLAUSES = prove
122 (!a n. X a (n + 2) = 2 * a * X a (n + 1) - X a (n))`,
123 REPEAT STRIP_TAC THEN GEN_REWRITE_TAC LAND_CONV [X_DEF] THEN
124 REWRITE_TAC[ARITH_EQ; ADD_EQ_0; ARITH_RULE `~(n + 2 = 1)`] THEN
125 REWRITE_TAC[ARITH_RULE `((n + 2) - 2 = n) /\ ((n + 2) - 1 = n + 1)`]);;
129 (`!a. ?Y. !n. Y n = if n = 0 then 0
131 else 2 * a * Y(n-1) - Y(n-2)`,
132 GEN_TAC THEN MATCH_MP_TAC(MATCH_MP WF_REC WF_num) THEN
133 REPEAT STRIP_TAC THEN
134 REPEAT(COND_CASES_TAC THEN ASM_REWRITE_TAC[]) THEN
136 ASM_SIMP_TAC[ARITH_RULE `n - m < n <=> ~(m = 0) /\ ~(n = 0)`; ARITH_EQ]) in
137 new_specification ["Y"] (REWRITE_RULE[SKOLEM_THM] th);;
139 let Y_CLAUSES = prove
142 (!a n. Y a (n + 2) = 2 * a * Y a (n + 1) - Y a (n))`,
143 REPEAT STRIP_TAC THEN GEN_REWRITE_TAC LAND_CONV [Y_DEF] THEN
144 REWRITE_TAC[ARITH_EQ; ADD_EQ_0; ARITH_RULE `~(n + 2 = 1)`] THEN
145 REWRITE_TAC[ARITH_RULE `((n + 2) - 2 = n) /\ ((n + 2) - 1 = n + 1)`]);;
147 (* ------------------------------------------------------------------------- *)
148 (* An obvious but tiresome lemma: the Xs and Ys increase. *)
149 (* ------------------------------------------------------------------------- *)
151 let X_INCREASES = prove
152 (`!a n. ~(a = 0) ==> X a n <= X a (n + 1)`,
153 GEN_TAC THEN REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN DISCH_TAC THEN
154 MATCH_MP_TAC num_WF THEN REPEAT STRIP_TAC THEN
155 ASM_CASES_TAC `n = 0` THEN
156 ASM_REWRITE_TAC[X_CLAUSES; ADD_CLAUSES;
157 ARITH_RULE `1 <= a <=> ~(a = 0)`] THEN
158 GEN_REWRITE_TAC RAND_CONV [X_DEF] THEN
159 ASM_REWRITE_TAC[ADD_EQ_0; ARITH_EQ;
160 ARITH_RULE `(n + 1 = 1) <=> (n = 0)`] THEN
161 REWRITE_TAC[ADD_SUB] THEN
162 MATCH_MP_TAC(ARITH_RULE `a + b <= c ==> a <= c - b:num`) THEN
163 MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `2 * X a n` THEN CONJ_TAC THENL
165 REWRITE_TAC[LE_MULT_LCANCEL; ARITH_EQ] THEN
166 UNDISCH_TAC `~(a = 0)` THEN SPEC_TAC(`a:num`,`a:num`) THEN
167 INDUCT_TAC THEN REWRITE_TAC[ADD_CLAUSES; MULT_CLAUSES] THEN
168 REWRITE_TAC[ARITH_RULE `a <= b + a:num`]] THEN
169 MATCH_MP_TAC(ARITH_RULE `b <= a ==> a + b <= 2 * a`) THEN
170 SUBGOAL_THEN `n = (n - 1) + 1` SUBST1_TAC THENL
171 [UNDISCH_TAC `~(n = 0)` THEN ARITH_TAC; ALL_TAC] THEN
172 REWRITE_TAC[ARITH_RULE `((n + 1) + 1) - 2 = n`] THEN
173 FIRST_ASSUM MATCH_MP_TAC THEN
174 UNDISCH_TAC `~(n = 0)` THEN ARITH_TAC);;
176 let Y_INCREASES = prove
177 (`!a n. ~(a = 0) ==> Y a n <= Y a (n + 1)`,
178 GEN_TAC THEN REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN DISCH_TAC THEN
179 MATCH_MP_TAC num_WF THEN REPEAT STRIP_TAC THEN
180 ASM_CASES_TAC `n = 0` THEN
181 ASM_REWRITE_TAC[Y_CLAUSES; ADD_CLAUSES; LE_0] THEN
182 GEN_REWRITE_TAC RAND_CONV [Y_DEF] THEN
183 ASM_REWRITE_TAC[ADD_EQ_0; ARITH_EQ;
184 ARITH_RULE `(n + 1 = 1) <=> (n = 0)`] THEN
185 REWRITE_TAC[ADD_SUB] THEN
186 MATCH_MP_TAC(ARITH_RULE `a + b <= c ==> a <= c - b:num`) THEN
187 MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `2 * Y a n` THEN CONJ_TAC THENL
189 REWRITE_TAC[LE_MULT_LCANCEL; ARITH_EQ] THEN
190 UNDISCH_TAC `~(a = 0)` THEN SPEC_TAC(`a:num`,`a:num`) THEN
191 INDUCT_TAC THEN REWRITE_TAC[ADD_CLAUSES; MULT_CLAUSES] THEN
192 REWRITE_TAC[ARITH_RULE `a <= b + a:num`]] THEN
193 MATCH_MP_TAC(ARITH_RULE `b <= a ==> a + b <= 2 * a`) THEN
194 SUBGOAL_THEN `n = (n - 1) + 1` SUBST1_TAC THENL
195 [UNDISCH_TAC `~(n = 0)` THEN ARITH_TAC; ALL_TAC] THEN
196 REWRITE_TAC[ARITH_RULE `((n + 1) + 1) - 2 = n`] THEN
197 FIRST_ASSUM MATCH_MP_TAC THEN
198 UNDISCH_TAC `~(n = 0)` THEN ARITH_TAC);;
200 (* ------------------------------------------------------------------------- *)
201 (* Show that the expression is a power of the basis. *)
202 (* ------------------------------------------------------------------------- *)
204 let XY_POWER_POS = prove
205 (`!a n. ~(a = 0) ==> (&(X a n) + &(Y a n) * sqrt(&a pow 2 - &1) =
206 (&a + sqrt(&a pow 2 - &1)) pow n)`,
207 GEN_TAC THEN REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN DISCH_TAC THEN
208 MATCH_MP_TAC num_WF THEN GEN_TAC THEN DISCH_TAC THEN
209 ONCE_REWRITE_TAC[X_DEF; Y_DEF] THEN
210 COND_CASES_TAC THEN ASM_REWRITE_TAC[ARITH_EQ] THEN
211 REWRITE_TAC[REAL_MUL_LZERO; REAL_ADD_RID; real_pow] THEN
212 COND_CASES_TAC THEN ASM_REWRITE_TAC[REAL_POW_1; REAL_MUL_LID] THEN
213 REWRITE_TAC[REAL_OF_NUM_ADD] THEN
215 `(&(2 * a * X a (n - 1) - X a (n - 2)) =
216 &(2 * a * X a (n - 1)) - &(X a (n - 2))) /\
217 (&(2 * a * Y a (n - 1) - Y a (n - 2)) =
218 &(2 * a * Y a (n - 1)) - &(Y a (n - 2)))`
219 (CONJUNCTS_THEN SUBST1_TAC)
221 [CONJ_TAC THEN MATCH_MP_TAC(GSYM REAL_OF_NUM_SUB) THEN
222 MATCH_MP_TAC(ARITH_RULE
223 `x <= y /\ y <= 2 * a * y ==> x <= 2 * a * y`) THEN
224 ASM_SIMP_TAC[ARITH_RULE
225 `~(n = 0) /\ ~(n = 1) ==> (n - 1 = (n - 2) + 1)`] THEN
226 ASM_SIMP_TAC[X_INCREASES; Y_INCREASES] THEN
227 REWRITE_TAC[MULT_ASSOC] THEN
228 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `n = 1 * n`] THEN
229 REWRITE_TAC[LE_MULT_RCANCEL] THEN DISJ1_TAC THEN
230 UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC; ALL_TAC] THEN
231 REWRITE_TAC[REAL_ARITH
232 `(x1 - x2) + (y1 - y2) * a = (x1 + y1 * a) - (x2 + y2 * a)`] THEN
233 REWRITE_TAC[GSYM REAL_OF_NUM_MUL] THEN
234 REWRITE_TAC[GSYM REAL_MUL_ASSOC; GSYM REAL_ADD_LDISTRIB] THEN
235 ASM_SIMP_TAC[ARITH_RULE
236 `~(n = 0) /\ ~(n = 1) ==> n - 2 < n /\ n - 1 < n`] THEN
237 ASM_SIMP_TAC[ARITH_RULE
238 `~(n = 0) /\ ~(n = 1) ==> (n - 1 = 1 + (n - 2))`] THEN
239 REWRITE_TAC[REAL_POW_ADD; REAL_MUL_ASSOC; REAL_POW_1] THEN
240 REWRITE_TAC[REAL_ARITH `a * b - b = (a - &1) * b`] THEN
241 SUBGOAL_THEN `n = 2 + (n - 2)`
242 (fun th -> GEN_REWRITE_TAC (RAND_CONV o RAND_CONV) [th])
244 [MAP_EVERY UNDISCH_TAC [`~(n = 0)`; `~(n = 1)`] THEN ARITH_TAC;
246 REWRITE_TAC[REAL_POW_ADD] THEN AP_THM_TAC THEN AP_TERM_TAC THEN
247 REWRITE_TAC[REAL_POW_2; REAL_ADD_LDISTRIB; REAL_ADD_RDISTRIB] THEN
248 REWRITE_TAC[GSYM REAL_POW_2] THEN
249 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE;
250 REAL_POW_LE_1; REAL_OF_NUM_LE;
251 ARITH_RULE `1 <= a <=> ~(a = 0)`] THEN
252 REWRITE_TAC[REAL_POW_2] THEN REAL_ARITH_TAC);;
254 let XY_POWER_NEG = prove
255 (`!a n. ~(a = 0) ==> (&(X a n) - &(Y a n) * sqrt(&a pow 2 - &1) =
256 (&a - sqrt(&a pow 2 - &1)) pow n)`,
257 GEN_TAC THEN REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN DISCH_TAC THEN
258 MATCH_MP_TAC num_WF THEN GEN_TAC THEN DISCH_TAC THEN
259 ONCE_REWRITE_TAC[X_DEF; Y_DEF] THEN
260 COND_CASES_TAC THEN ASM_REWRITE_TAC[ARITH_EQ] THEN
261 REWRITE_TAC[REAL_MUL_LZERO; REAL_SUB_RZERO; real_pow] THEN
262 COND_CASES_TAC THEN ASM_REWRITE_TAC[REAL_POW_1; REAL_MUL_LID] THEN
263 REWRITE_TAC[REAL_OF_NUM_ADD] THEN
265 `(&(2 * a * X a (n - 1) - X a (n - 2)) =
266 &(2 * a * X a (n - 1)) - &(X a (n - 2))) /\
267 (&(2 * a * Y a (n - 1) - Y a (n - 2)) =
268 &(2 * a * Y a (n - 1)) - &(Y a (n - 2)))`
269 (CONJUNCTS_THEN SUBST1_TAC)
271 [CONJ_TAC THEN MATCH_MP_TAC(GSYM REAL_OF_NUM_SUB) THEN
272 MATCH_MP_TAC(ARITH_RULE
273 `x <= y /\ y <= 2 * a * y ==> x <= 2 * a * y`) THEN
274 ASM_SIMP_TAC[ARITH_RULE
275 `~(n = 0) /\ ~(n = 1) ==> (n - 1 = (n - 2) + 1)`] THEN
276 ASM_SIMP_TAC[X_INCREASES; Y_INCREASES] THEN
277 REWRITE_TAC[MULT_ASSOC] THEN
278 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `n = 1 * n`] THEN
279 REWRITE_TAC[LE_MULT_RCANCEL] THEN DISJ1_TAC THEN
280 UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC; ALL_TAC] THEN
281 REWRITE_TAC[REAL_ARITH
282 `(x1 - x2) - (y1 - y2) * a = (x1 - y1 * a) - (x2 - y2 * a)`] THEN
283 REWRITE_TAC[GSYM REAL_OF_NUM_MUL] THEN
284 REWRITE_TAC[GSYM REAL_MUL_ASSOC; GSYM REAL_SUB_LDISTRIB] THEN
285 ASM_SIMP_TAC[ARITH_RULE
286 `~(n = 0) /\ ~(n = 1) ==> n - 2 < n /\ n - 1 < n`] THEN
287 ASM_SIMP_TAC[ARITH_RULE
288 `~(n = 0) /\ ~(n = 1) ==> (n - 1 = 1 + (n - 2))`] THEN
289 REWRITE_TAC[REAL_POW_ADD; REAL_MUL_ASSOC; REAL_POW_1] THEN
290 REWRITE_TAC[REAL_ARITH `a * b - b = (a - &1) * b`] THEN
291 SUBGOAL_THEN `n = 2 + (n - 2)`
292 (fun th -> GEN_REWRITE_TAC (RAND_CONV o RAND_CONV) [th])
294 [MAP_EVERY UNDISCH_TAC [`~(n = 0)`; `~(n = 1)`] THEN ARITH_TAC;
296 REWRITE_TAC[REAL_POW_ADD] THEN AP_THM_TAC THEN AP_TERM_TAC THEN
297 REWRITE_TAC[REAL_POW_2; REAL_SUB_LDISTRIB; REAL_SUB_RDISTRIB] THEN
298 REWRITE_TAC[GSYM REAL_POW_2] THEN
299 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE;
300 REAL_POW_LE_1; REAL_OF_NUM_LE;
301 ARITH_RULE `1 <= a <=> ~(a = 0)`] THEN
302 REWRITE_TAC[REAL_POW_2] THEN REAL_ARITH_TAC);;
304 (* ------------------------------------------------------------------------- *)
305 (* Hence all members of recurrence relations are Pell solutions. *)
306 (* ------------------------------------------------------------------------- *)
308 let XY_ARE_SOLUTIONS = prove
310 ==> ((X a n) EXP 2 = (a EXP 2 - 1) * (Y a n) EXP 2 + 1)`,
311 REPEAT STRIP_TAC THEN
312 FIRST_ASSUM(MP_TAC o SPEC `n:num` o MATCH_MP XY_POWER_NEG) THEN
313 FIRST_ASSUM(MP_TAC o SPEC `n:num` o MATCH_MP XY_POWER_POS) THEN
314 REWRITE_TAC[IMP_IMP] THEN
316 MP_TAC(MK_COMB(AP_TERM `( * )` (CONJUNCT1 th),CONJUNCT2 th))) THEN
317 REWRITE_TAC[GSYM REAL_POW_MUL] THEN
318 REWRITE_TAC[REAL_ARITH `(x + y) * (x - y) = x * x - y * y`] THEN
319 ONCE_REWRITE_TAC[AC REAL_MUL_AC
320 `(a * b) * (c * d) = (a * c) * (b * d)`] THEN
321 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE;
322 REAL_POW_LE_1; REAL_OF_NUM_LE;
323 ARITH_RULE `1 <= a <=> ~(a = 0)`] THEN
324 REWRITE_TAC[REAL_ARITH `a - (a - &1) = &1`; REAL_POW_ONE] THEN
325 REWRITE_TAC[REAL_EQ_SUB_RADD] THEN
326 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` SUBST1_TAC THENL
327 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
328 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
329 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
330 ARITH_RULE `1 <= a <=> ~(a = 0)`];
331 REWRITE_TAC[REAL_OF_NUM_ADD; REAL_OF_NUM_MUL; REAL_OF_NUM_EQ;
332 REAL_OF_NUM_POW] THEN
333 REWRITE_TAC[MULT_AC; ADD_AC]]);;
335 (* ------------------------------------------------------------------------- *)
336 (* And they are all solutions. *)
337 (* ------------------------------------------------------------------------- *)
339 let X_DEGENERATE = prove
341 MATCH_MP_TAC PELL_INDUCTION THEN SIMP_TAC[X_CLAUSES; ARITH]);;
343 let Y_DEGENERATE = prove
345 MATCH_MP_TAC PELL_INDUCTION THEN SIMP_TAC[Y_CLAUSES] THEN
346 REPEAT STRIP_TAC THEN ARITH_TAC);;
348 let REAL_ARCH_POW = prove
349 (`!x y. &1 < x /\ &1 < y
350 ==> ?n. x pow n <= y /\ y < x pow (SUC n)`,
351 REPEAT STRIP_TAC THEN
352 MP_TAC(SPEC `ln(x)` REAL_ARCH_LEAST) THEN ASM_SIMP_TAC[LN_POS_LT] THEN
353 DISCH_THEN(MP_TAC o SPEC `ln(y)`) THEN
354 ASM_SIMP_TAC[LN_POS_LT; REAL_LT_IMP_LE] THEN
355 ASM_SIMP_TAC[GSYM LN_POW; REAL_ARITH `&1 < x ==> &0 < x`;
356 REAL_POW_LT; LN_MONO_LT; LN_MONO_LE]);;
358 let SOLUTIONS_INDUCTION = prove
360 ~(a = 0) /\ ~(a = 1) /\ ~(y = 0) /\
361 (x EXP 2 = (a EXP 2 - 1) * y EXP 2 + 1)
362 ==> ?x' y'. x' < x /\ y' < y /\
363 (x' EXP 2 = (a EXP 2 - 1) * y' EXP 2 + 1) /\
364 (&x + &y * sqrt(&a pow 2 - &1) =
365 (&x' + &y' * sqrt(&a pow 2 - &1)) *
366 (&a + sqrt(&a pow 2 - &1)))`,
367 REPEAT STRIP_TAC THEN
368 EXISTS_TAC `a * x - (a EXP 2 - 1) * y` THEN
369 EXISTS_TAC `a * y - x:num` THEN
370 SUBGOAL_THEN `x <= a * y:num` ASSUME_TAC THENL
371 [ONCE_REWRITE_TAC[GSYM(SPECL [`x:num`; `y:num`; `1`] EXP_MONO_LE_SUC)] THEN
372 ASM_REWRITE_TAC[ARITH_SUC] THEN
373 REWRITE_TAC[GSYM ADD1; LE_SUC_LT] THEN
374 REWRITE_TAC[MULT_EXP; LT_MULT_RCANCEL] THEN
375 REWRITE_TAC[ARITH_RULE `a - 1 < a <=> ~(a = 0)`] THEN
376 ASM_REWRITE_TAC[EXP_EQ_0]; ALL_TAC] THEN
377 SUBGOAL_THEN `(a EXP 2 - 1) * y <= a * x:num` ASSUME_TAC THENL
378 [SUBGOAL_THEN `(a EXP 2 - 1) * y EXP 2 < a * x * y` MP_TAC THENL
380 ASM_SIMP_TAC[MULT_ASSOC; EXP_2; LT_MULT_RCANCEL; LT_IMP_LE]] THEN
381 REWRITE_TAC[GSYM LE_SUC_LT; ADD1] THEN
382 FIRST_ASSUM(fun th -> GEN_REWRITE_TAC LAND_CONV [SYM th]) THEN
383 GEN_REWRITE_TAC RAND_CONV [MULT_SYM] THEN
384 REWRITE_TAC[EXP_2; GSYM MULT_ASSOC; LE_MULT_LCANCEL] THEN
385 DISJ2_TAC THEN ONCE_REWRITE_TAC[MULT_SYM] THEN ASM_REWRITE_TAC[];
387 MATCH_MP_TAC(TAUT `d /\ (d ==> a /\ b /\ c)
388 ==> a /\ b /\ c /\ d`) THEN
390 [MATCH_MP_TAC REAL_EQ_RCANCEL_IMP THEN
391 EXISTS_TAC `&a - sqrt(&a pow 2 - &1)` THEN CONJ_TAC THENL
392 [REWRITE_TAC[REAL_SUB_0] THEN
393 DISCH_THEN(MP_TAC o C AP_THM `2` o AP_TERM `(pow)`) THEN
394 ASM_SIMP_TAC[SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1; REAL_OF_NUM_LE;
395 ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
396 REAL_ARITH_TAC; ALL_TAC] THEN
397 REWRITE_TAC[GSYM REAL_MUL_ASSOC] THEN
398 REWRITE_TAC[REAL_ARITH `(a + b) * (a - b) = a * a - b * b`] THEN
399 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1;
400 REAL_OF_NUM_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
401 REWRITE_TAC[REAL_ARITH `a - (a - b) = b`; REAL_MUL_RID] THEN
402 ASM_SIMP_TAC[GSYM REAL_OF_NUM_SUB] THEN
403 REWRITE_TAC[REAL_ARITH
404 `(x + y * s) * (a - s) = (a * x - (s * s) * y) + (a * y - x) * s`] THEN
405 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1;
406 REAL_OF_NUM_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
407 REWRITE_TAC[GSYM REAL_OF_NUM_MUL] THEN
408 AP_THM_TAC THEN AP_TERM_TAC THEN AP_TERM_TAC THEN
409 AP_THM_TAC THEN AP_TERM_TAC THEN
410 REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
411 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
412 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
413 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
414 DISCH_THEN(fun th -> ASSUME_TAC th THEN MP_TAC th) THEN
416 `(&x - &y * sqrt(&a pow 2 - &1)) =
417 (&(a * x - (a EXP 2 - 1) * y) - &(a * y - x) * sqrt (&a pow 2 - &1)) *
418 (&a - sqrt(&a pow 2 - &1))`
420 [MATCH_MP_TAC REAL_EQ_RCANCEL_IMP THEN
421 EXISTS_TAC `&a + sqrt(&a pow 2 - &1)` THEN CONJ_TAC THENL
422 [MATCH_MP_TAC(REAL_ARITH `~(a = --b) ==> ~(a + b = &0)`) THEN
423 DISCH_THEN(MP_TAC o C AP_THM `2` o AP_TERM `(pow)`) THEN
424 REWRITE_TAC[REAL_POW_NEG; ARITH] THEN
425 ASM_SIMP_TAC[SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1; REAL_OF_NUM_LE;
426 ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
427 REAL_ARITH_TAC; ALL_TAC] THEN
428 REWRITE_TAC[GSYM REAL_MUL_ASSOC] THEN
429 REWRITE_TAC[REAL_ARITH `(a - b) * (a + b) = a * a - b * b`] THEN
430 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1;
431 REAL_OF_NUM_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
432 REWRITE_TAC[REAL_ARITH `a - (a - b) = b`; REAL_MUL_RID] THEN
433 ASM_SIMP_TAC[GSYM REAL_OF_NUM_SUB] THEN
434 REWRITE_TAC[REAL_ARITH
435 `(x - y * s) * (a + s) = (a * x - (s * s) * y) - (a * y - x) * s`] THEN
436 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1;
437 REAL_OF_NUM_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
438 REWRITE_TAC[GSYM REAL_OF_NUM_MUL] THEN
439 AP_THM_TAC THEN AP_TERM_TAC THEN AP_TERM_TAC THEN
440 AP_THM_TAC THEN AP_TERM_TAC THEN
441 REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
442 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
443 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
444 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
445 DISCH_THEN(fun th1 -> DISCH_THEN (fun th2 ->
446 MP_TAC(MK_COMB(AP_TERM `( * )` th1,th2)))) THEN
447 ONCE_REWRITE_TAC[AC REAL_MUL_AC
448 `(a * b) * (c * d) = (c * a) * (d * b)`] THEN
449 REWRITE_TAC[REAL_ARITH `(a + b) * (a - b) = a * a - b * b`] THEN
450 REWRITE_TAC[REAL_ARITH `(a - b) * (a + b) = a * a - b * b`] THEN
451 ONCE_REWRITE_TAC[AC REAL_MUL_AC
452 `(a * b) * (c * b) = (c * a) * (b * b)`] THEN
453 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1;
454 REAL_OF_NUM_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
455 REWRITE_TAC[REAL_ARITH `a - (a - b) = b`; REAL_MUL_RID] THEN
456 ASM_REWRITE_TAC[REAL_OF_NUM_POW] THEN
457 REWRITE_TAC[GSYM REAL_OF_NUM_POW; GSYM REAL_OF_NUM_ADD;
458 GSYM REAL_OF_NUM_MUL] THEN
459 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` (SUBST1_TAC o SYM) THENL
460 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
461 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
462 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
463 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
464 DISCH_THEN(MP_TAC o MATCH_MP (REAL_ARITH
465 `((a * b + &1) - b * a = x - y) ==> (x = y + &1)`)) THEN
466 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` SUBST1_TAC THENL
467 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
468 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
469 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
470 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
471 ASM_SIMP_TAC[REAL_OF_NUM_SUB; REAL_OF_NUM_ADD; REAL_OF_NUM_EQ;
472 REAL_OF_NUM_POW; REAL_OF_NUM_MUL] THEN
473 ABBREV_TAC `u = a * x - (a EXP 2 - 1) * y` THEN
474 ABBREV_TAC `v = a * y - x:num` THEN
475 DISCH_THEN(ASSUME_TAC o ONCE_REWRITE_RULE[MULT_SYM]) THEN
476 REWRITE_TAC[MULT_AC] THEN
477 MATCH_MP_TAC(TAUT `(a <=> b) /\ (~a /\ ~b ==> F) ==> a /\ b`) THEN
479 [GEN_REWRITE_TAC LAND_CONV [GSYM(SPEC `1` EXP_MONO_LT_SUC)] THEN
480 ASM_REWRITE_TAC[ARITH_SUC] THEN
481 REWRITE_TAC[LT_ADD_RCANCEL; LT_MULT_LCANCEL] THEN
482 REWRITE_TAC[num_CONV `2`; EXP_MONO_LT_SUC] THEN
483 MATCH_MP_TAC(TAUT `a ==> (a /\ b <=> b)`) THEN
484 REWRITE_TAC[SUB_EQ_0; ARITH_SUC; NOT_LE] THEN
485 SUBST1_TAC(SYM(SPEC `a:num` (CONJUNCT1 EXP))) THEN
486 REWRITE_TAC[LT_EXP] THEN REWRITE_TAC[ARITH] THEN
487 MATCH_MP_TAC(ARITH_RULE `~(a = 0) /\ ~(a = 1) ==> 2 <= a`) THEN
488 ASM_REWRITE_TAC[]; ALL_TAC] THEN
489 REWRITE_TAC[NOT_LT] THEN STRIP_TAC THEN
491 `&x + &y * sqrt (&a pow 2 - &1) =
492 (&u + &v * sqrt (&a pow 2 - &1)) * (&a + sqrt (&a pow 2 - &1))` THEN
494 MATCH_MP_TAC(REAL_ARITH `a < b ==> ~(a = b)`) THEN
495 MATCH_MP_TAC REAL_LET_TRANS THEN
496 EXISTS_TAC `(&u + &v * sqrt (&a pow 2 - &1)) * &1` THEN CONJ_TAC THENL
497 [REWRITE_TAC[REAL_MUL_RID] THEN MATCH_MP_TAC REAL_LE_ADD2 THEN
498 ASM_REWRITE_TAC[REAL_OF_NUM_LE] THEN
499 MATCH_MP_TAC REAL_LE_RMUL THEN
500 ASM_SIMP_TAC[REAL_OF_NUM_LE; SQRT_POS_LE; REAL_POW_LE_1;
501 REAL_SUB_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`];
503 MATCH_MP_TAC REAL_LT_LMUL THEN CONJ_TAC THENL
504 [MATCH_MP_TAC REAL_LTE_ADD THEN CONJ_TAC THENL
505 [REWRITE_TAC[REAL_OF_NUM_LT; LT_NZ] THEN DISCH_THEN SUBST_ALL_TAC THEN
506 UNDISCH_TAC `0 EXP 2 = (a EXP 2 - 1) * v EXP 2 + 1` THEN
507 DISCH_THEN(MP_TAC o SYM) THEN CONV_TAC NUM_REDUCE_CONV THEN
508 REWRITE_TAC[ADD_EQ_0; ARITH_EQ]; ALL_TAC] THEN
509 MATCH_MP_TAC REAL_LE_MUL THEN REWRITE_TAC[REAL_POS] THEN
510 ASM_SIMP_TAC[REAL_OF_NUM_LE; SQRT_POS_LE; REAL_POW_LE_1;
511 REAL_SUB_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`];
513 MATCH_MP_TAC(REAL_ARITH `&1 < x /\ &0 <= y ==> &1 < x + y`) THEN
514 ASM_SIMP_TAC[REAL_OF_NUM_LE; SQRT_POS_LE; REAL_POW_LE_1;
515 REAL_SUB_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
516 REWRITE_TAC[REAL_OF_NUM_LT] THEN
517 MATCH_MP_TAC(ARITH_RULE `~(a = 0) /\ ~(a = 1) ==> 1 < a`) THEN
520 let SOLUTIONS_ARE_XY = prove
523 (x EXP 2 = (a EXP 2 - 1) * y EXP 2 + 1)
524 ==> ?n. (x = X a n) /\ (y = Y a n)`,
525 REPEAT GEN_TAC THEN ASM_CASES_TAC `a = 1` THENL
526 [ASM_REWRITE_TAC[ARITH; MULT_CLAUSES; ADD_CLAUSES; EXP_2] THEN
527 SIMP_TAC[MULT_EQ_1; X_DEGENERATE; Y_DEGENERATE; GSYM EXISTS_REFL];
530 SUBGOAL_THEN `?n. &x + &y * sqrt(&a pow 2 - &1) =
531 (&a + sqrt(&a pow 2 - &1)) pow n`
533 [UNDISCH_TAC `x EXP 2 = (a EXP 2 - 1) * y EXP 2 + 1` THEN
534 SPEC_TAC(`x:num`,`x:num`) THEN SPEC_TAC(`y:num`,`y:num`) THEN
535 MATCH_MP_TAC num_WF THEN X_GEN_TAC `y0:num` THEN DISCH_TAC THEN
536 X_GEN_TAC `x0:num` THEN
537 ASM_CASES_TAC `y0 = 0` THENL
538 [ASM_REWRITE_TAC[EXP_2; MULT_CLAUSES; ADD_CLAUSES; MULT_EQ_1] THEN
539 DISCH_THEN SUBST1_TAC THEN EXISTS_TAC `0` THEN
540 REWRITE_TAC[REAL_MUL_LZERO; REAL_ADD_RID; real_pow]; ALL_TAC] THEN
542 MP_TAC(SPECL [`a:num`; `x0:num`; `y0:num`] SOLUTIONS_INDUCTION) THEN
543 ASM_REWRITE_TAC[] THEN
544 DISCH_THEN(X_CHOOSE_THEN `x1:num` (X_CHOOSE_THEN `y1:num`
545 STRIP_ASSUME_TAC)) THEN
546 FIRST_X_ASSUM(MP_TAC o SPEC `y1:num`) THEN ASM_REWRITE_TAC[] THEN
547 DISCH_THEN(MP_TAC o SPEC `x1:num`) THEN ASM_REWRITE_TAC[] THEN
548 DISCH_THEN(X_CHOOSE_THEN `n:num` SUBST1_TAC) THEN
549 EXISTS_TAC `SUC n` THEN REWRITE_TAC[real_pow; REAL_MUL_AC]; ALL_TAC] THEN
550 ASM_SIMP_TAC[GSYM XY_POWER_POS] THEN MATCH_MP_TAC MONO_EXISTS THEN
551 X_GEN_TAC `n:num` THEN
552 ASM_SIMP_TAC[SQRT_LINEAR_EQ;
553 ARITH_RULE `~(a = 0) /\ ~(a = 1) ==> 2 <= a`]);;
555 (* ------------------------------------------------------------------------- *)
556 (* Addition formulas. *)
557 (* ------------------------------------------------------------------------- *)
559 let ADDITION_FORMULA_POS = prove
562 ==> ((X a (m + n) = X a m * X a n + (a EXP 2 - 1) * Y a m * Y a n) /\
563 (Y a (m + n) = X a m * Y a n + X a n * Y a m))`,
564 REPEAT GEN_TAC THEN DISCH_TAC THEN ASM_CASES_TAC `a = 1` THENL
565 [ASM_REWRITE_TAC[X_DEGENERATE; Y_DEGENERATE] THEN
566 REWRITE_TAC[ARITH; MULT_CLAUSES] THEN REWRITE_TAC[ADD_AC]; ALL_TAC] THEN
567 MP_TAC(SPECL [`a:num`; `m + n:num`] XY_POWER_POS) THEN
568 MP_TAC(SPECL [`a:num`; `m:num`] XY_POWER_POS) THEN
569 MP_TAC(SPECL [`a:num`; `n:num`] XY_POWER_POS) THEN
570 ASM_REWRITE_TAC[] THEN
571 REWRITE_TAC[REAL_POW_ADD] THEN
572 DISCH_THEN(SUBST1_TAC o SYM) THEN DISCH_THEN(SUBST1_TAC o SYM) THEN
573 REWRITE_TAC[REAL_ARITH
574 `(a + b * s) * (c + d * s) = (a * c + (s * s) * b * d) +
575 (a * d + b * c) * s`] THEN
576 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1;
577 REAL_OF_NUM_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
578 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` SUBST1_TAC THENL
579 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
580 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
581 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
582 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
583 REWRITE_TAC[REAL_OF_NUM_MUL; REAL_OF_NUM_ADD] THEN
584 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` (SUBST1_TAC o SYM) THENL
585 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
586 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
587 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
588 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
589 ASM_SIMP_TAC[SQRT_LINEAR_EQ;
590 ARITH_RULE `~(a = 0) /\ ~(a = 1) ==> 2 <= a`] THEN
591 REWRITE_TAC[MULT_AC]);;
593 let ADDITION_FORMULA_NEG = prove
596 ==> ((X a (n - m) = X a m * X a n - (a EXP 2 - 1) * Y a m * Y a n) /\
597 (Y a (n - m) = X a m * Y a n - X a n * Y a m))`,
598 REPEAT GEN_TAC THEN STRIP_TAC THEN ASM_CASES_TAC `a = 1` THENL
599 [ASM_REWRITE_TAC[X_DEGENERATE; Y_DEGENERATE] THEN
600 REWRITE_TAC[ARITH; MULT_CLAUSES]; ALL_TAC] THEN
601 MP_TAC(SPECL [`a:num`; `n - m:num`] XY_POWER_POS) THEN
602 ASM_REWRITE_TAC[] THEN
603 DISCH_THEN(MP_TAC o AP_TERM
604 `( * ) (((&a - sqrt (&a pow 2 - &1)) *
605 (&a + sqrt (&a pow 2 - &1))) pow m)`) THEN
606 GEN_REWRITE_TAC (LAND_CONV o LAND_CONV o ONCE_DEPTH_CONV)
607 [REAL_ARITH `(x - y) * (x + y) = x * x - y * y`] THEN
608 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE;
609 REAL_POW_LE_1; REAL_OF_NUM_LE;
610 ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
611 REWRITE_TAC[REAL_ARITH `x - (x - &1) = &1`] THEN
612 REWRITE_TAC[REAL_POW_MUL; REAL_POW_ONE; REAL_MUL_LID] THEN
613 REWRITE_TAC[GSYM REAL_MUL_ASSOC] THEN
614 REWRITE_TAC[GSYM REAL_POW_ADD] THEN
615 ASM_SIMP_TAC[ARITH_RULE `m <= n ==> (m + (n - m) = n:num)`] THEN
616 MP_TAC(SPECL [`a:num`; `m:num`] XY_POWER_NEG) THEN
617 MP_TAC(SPECL [`a:num`; `n:num`] XY_POWER_POS) THEN
618 ASM_REWRITE_TAC[] THEN
619 DISCH_THEN(SUBST1_TAC o SYM) THEN DISCH_THEN(SUBST1_TAC o SYM) THEN
620 REWRITE_TAC[REAL_ARITH
621 `(a - b * s) * (c + d * s) = (a * c - (s * s) * b * d) +
622 (a * d - b * c) * s`] THEN
623 ASM_SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_SUB_LE; REAL_POW_LE_1;
624 REAL_OF_NUM_LE; ARITH_RULE `~(a = 0) ==> 1 <= a`] THEN
625 ONCE_REWRITE_TAC[REAL_ARITH
626 `(a + b * s = (x1 - x2) + (y1 - y2) * s) =
627 ((a + x2) + (b + y2) * s = x1 + y1 * s)`] THEN
628 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` SUBST1_TAC THENL
629 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
630 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
631 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
632 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
633 REWRITE_TAC[REAL_OF_NUM_MUL; REAL_OF_NUM_ADD] THEN
634 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` (SUBST1_TAC o SYM) THENL
635 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
636 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
637 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
638 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
639 ASM_SIMP_TAC[SQRT_LINEAR_EQ;
640 ARITH_RULE `~(a = 0) /\ ~(a = 1) ==> 2 <= a`] THEN
641 DISCH_THEN(CONJUNCTS_THEN(SUBST1_TAC o SYM)) THEN
642 REWRITE_TAC[MULT_AC] THEN REWRITE_TAC[ADD_SUB]);;
644 (* ------------------------------------------------------------------------- *)
645 (* Some stronger monotonicity theorems for Y. *)
646 (* ------------------------------------------------------------------------- *)
648 let Y_INCREASES_SUC = prove
649 (`!a n. ~(a = 0) ==> Y a n < Y a (SUC n)`,
650 REPEAT STRIP_TAC THEN ASM_SIMP_TAC[ADD1; ADDITION_FORMULA_POS] THEN
651 REWRITE_TAC[X_CLAUSES; Y_CLAUSES] THEN
652 MATCH_MP_TAC(ARITH_RULE `1 * y <= ay /\ ~(x = 0) ==> y < x * 1 + ay`) THEN
653 ASM_SIMP_TAC[LE_MULT_RCANCEL; ARITH_RULE `1 <= a <=> ~(a = 0)`] THEN
654 MATCH_MP_TAC(ARITH_RULE
655 `!n. (n = 1) /\ n <= m ==> ~(m = 0)`) THEN
656 EXISTS_TAC `X a 0` THEN CONJ_TAC THENL
657 [REWRITE_TAC[X_CLAUSES]; ALL_TAC] THEN
658 SPEC_TAC(`n:num`,`n:num`) THEN
659 INDUCT_TAC THEN REWRITE_TAC[ADD_CLAUSES; LE_REFL] THEN
660 REWRITE_TAC[ADD1] THEN ASM_MESON_TAC[LE_TRANS; X_INCREASES]);;
662 let Y_INCREASES_LT = prove
663 (`!a m n. ~(a = 0) /\ m < n ==> Y a m < Y a n`,
664 REPEAT GEN_TAC THEN DISCH_THEN(CONJUNCTS_THEN2 ASSUME_TAC MP_TAC) THEN
665 GEN_REWRITE_TAC LAND_CONV [LT_EXISTS] THEN
666 SIMP_TAC[LEFT_IMP_EXISTS_THM] THEN X_GEN_TAC `d:num` THEN DISCH_TAC THEN
667 MATCH_MP_TAC LTE_TRANS THEN EXISTS_TAC `Y a (SUC m)` THEN
668 ASM_SIMP_TAC[Y_INCREASES_SUC] THEN
669 REWRITE_TAC[ARITH_RULE `m + SUC d = SUC m + d`] THEN
670 SPEC_TAC(`d:num`,`d:num`) THEN
671 INDUCT_TAC THEN REWRITE_TAC[ADD_CLAUSES; LE_REFL] THEN
672 RULE_ASSUM_TAC(REWRITE_RULE[ADD_CLAUSES]) THEN
673 ASM_MESON_TAC[ADD1; LE_TRANS; Y_INCREASES]);;
675 let Y_INCREASES_LE = prove
676 (`!a m n. ~(a = 0) /\ m <= n ==> Y a m <= Y a n`,
677 REWRITE_TAC[LE_LT] THEN MESON_TAC[LE_REFL; Y_INCREASES_LT]);;
680 (`!a m n. ~(a = 0) ==> ((Y a m = Y a n) <=> (m = n))`,
681 REPEAT STRIP_TAC THEN EQ_TAC THEN SIMP_TAC[] THEN
682 MP_TAC(SPEC `a:num` Y_INCREASES_LT) THEN ASM_REWRITE_TAC[] THEN
683 MESON_TAC[LT_CASES; LT_REFL]);;
685 (* ------------------------------------------------------------------------- *)
686 (* One for X (to get the same as Y, need a /= 1). *)
687 (* ------------------------------------------------------------------------- *)
689 let X_INCREASES_LE = prove
690 (`!a m n. ~(a = 0) /\ m <= n ==> X a m <= X a n`,
691 REPEAT GEN_TAC THEN DISCH_THEN(CONJUNCTS_THEN2 ASSUME_TAC MP_TAC) THEN
692 GEN_REWRITE_TAC LAND_CONV [LE_EXISTS] THEN
693 SIMP_TAC[LEFT_IMP_EXISTS_THM] THEN X_GEN_TAC `d:num` THEN
694 DISCH_THEN(K ALL_TAC) THEN SPEC_TAC(`d:num`,`d:num`) THEN
695 INDUCT_TAC THEN REWRITE_TAC[ADD_CLAUSES; LE_REFL] THEN
696 REWRITE_TAC[ADD1] THEN ASM_MESON_TAC[LE_TRANS; X_INCREASES]);;
698 let X_INCREASES_LT = prove
699 (`!a m n. ~(a = 0) /\ ~(a = 1) /\ m < n ==> X a m < X a n`,
701 GEN_REWRITE_TAC (LAND_CONV o ONCE_DEPTH_CONV) [GSYM LE_SUC_LT] THEN
703 MATCH_MP_TAC LTE_TRANS THEN EXISTS_TAC `X a (SUC m)` THEN
704 ASM_SIMP_TAC[X_INCREASES_LE] THEN
705 SPEC_TAC(`m:num`,`p:num`) THEN
706 INDUCT_TAC THEN ASM_SIMP_TAC[ARITH; X_CLAUSES; ARITH_RULE
707 `~(a = 0) /\ ~(a = 1) ==> 1 < a`] THEN
708 REWRITE_TAC[ARITH_RULE `SUC(SUC p) = p + 2`] THEN
709 REWRITE_TAC[X_CLAUSES; ADD1] THEN
710 MATCH_MP_TAC(ARITH_RULE `a <= b /\ c < b ==> a < 2 * b - c`) THEN
713 MATCH_MP_TAC LTE_TRANS THEN EXISTS_TAC `X a (SUC p)` THEN
714 ASM_REWRITE_TAC[]] THEN
715 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `a = 1 * a`] THEN
716 REWRITE_TAC[LE_MULT_RCANCEL; ADD1] THEN DISJ1_TAC THEN
717 MAP_EVERY UNDISCH_TAC [`~(a = 0)`; `~(a = 1)`] THEN ARITH_TAC);;
719 let X_INCREASES_SUC = prove
720 (`!a n. ~(a = 0) /\ ~(a = 1) ==> X a n < X a (SUC n)`,
721 SIMP_TAC[X_INCREASES_LT; LT]);;
724 (`!a m n. ~(a = 0) /\ ~(a = 1) ==> ((X a m = X a n) <=> (m = n))`,
725 REPEAT STRIP_TAC THEN EQ_TAC THEN SIMP_TAC[] THEN
726 MP_TAC(SPEC `a:num` X_INCREASES_LT) THEN ASM_REWRITE_TAC[] THEN
727 MESON_TAC[LT_CASES; LT_REFL]);;
729 (* ------------------------------------------------------------------------- *)
730 (* Coprimality of "X a n" and "Y a n". *)
731 (* ------------------------------------------------------------------------- *)
733 let XY_COPRIME = prove
734 (`!a n. ~(a = 0) ==> coprime(X a n,Y a n)`,
736 DISCH_THEN(MP_TAC o SPEC `n:num` o MATCH_MP XY_ARE_SOLUTIONS) THEN
737 ONCE_REWRITE_TAC[TAUT `a ==> b <=> ~b ==> ~a`] THEN
738 REWRITE_TAC[coprime; NOT_FORALL_THM; LEFT_IMP_EXISTS_THM] THEN
739 X_GEN_TAC `d:num` THEN REWRITE_TAC[NOT_IMP] THEN
740 REWRITE_TAC[divides] THEN STRIP_TAC THEN ASM_REWRITE_TAC[EXP_2] THEN
741 REWRITE_TAC[GSYM MULT_ASSOC] THEN
742 GEN_REWRITE_TAC (funpow 2 RAND_CONV o LAND_CONV)
743 [AC MULT_AC `a * d * x * d * x = d * d * a * x * x:num`] THEN
744 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
745 `(a = b + 1) ==> (a - b = 1)`)) THEN
746 ASM_REWRITE_TAC[GSYM LEFT_SUB_DISTRIB; MULT_EQ_1]);;
748 (* ------------------------------------------------------------------------- *)
749 (* Divisibility properties. *)
750 (* ------------------------------------------------------------------------- *)
752 let Y_DIVIDES_LEMMA = prove
753 (`!a k n. ~(a = 0) ==> (Y a n) divides (Y a (n * k))`,
754 REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN GEN_TAC THEN DISCH_TAC THEN
755 ONCE_REWRITE_TAC[SWAP_FORALL_THM] THEN GEN_TAC THEN
756 INDUCT_TAC THEN REWRITE_TAC[MULT_CLAUSES] THEN
757 REWRITE_TAC[Y_CLAUSES; DIVIDES_0] THEN
758 ASM_SIMP_TAC[ADDITION_FORMULA_POS] THEN
759 UNDISCH_TAC `Y a n divides Y a (n * k)` THEN
760 SIMP_TAC[divides; LEFT_IMP_EXISTS_THM] THEN
761 X_GEN_TAC `d:num` THEN DISCH_TAC THEN
762 EXISTS_TAC `X a n * d + X a (n * k)` THEN
763 REWRITE_TAC[LEFT_ADD_DISTRIB] THEN REWRITE_TAC[MULT_AC; ADD_AC]);;
765 let Y_DIVIDES = prove
766 (`!a m n. ~(a = 0) ==> ((Y a m) divides (Y a n) <=> m divides n)`,
767 REPEAT STRIP_TAC THEN EQ_TAC THENL
769 GEN_REWRITE_TAC LAND_CONV [divides] THEN
770 ASM_SIMP_TAC[LEFT_IMP_EXISTS_THM; Y_DIVIDES_LEMMA]] THEN
771 ONCE_REWRITE_TAC[TAUT `a ==> b <=> ~b ==> ~a`] THEN
772 ASM_CASES_TAC `n = 0` THEN ASM_REWRITE_TAC[DIVIDES_0] THEN
773 ASM_CASES_TAC `m = 0` THENL
774 [ASM_REWRITE_TAC[Y_CLAUSES; DIVIDES_ZERO] THEN
775 MATCH_MP_TAC(ARITH_RULE
776 `!n. (n = 1) /\ n <= m ==> ~(m = 0)`) THEN
777 EXISTS_TAC `Y a 1` THEN CONJ_TAC THENL
778 [REWRITE_TAC[Y_CLAUSES]; ALL_TAC] THEN
779 ASM_SIMP_TAC[Y_INCREASES_LE; ARITH_RULE `1 <= n <=> ~(n = 0)`];
781 MP_TAC(SPECL [`n:num`; `m:num`] DIVISION) THEN
782 ASM_REWRITE_TAC[] THEN
783 ABBREV_TAC `q = n DIV m` THEN ABBREV_TAC `r = n MOD m` THEN
784 STRIP_TAC THEN ASM_REWRITE_TAC[] THEN
785 ASM_CASES_TAC `r = 0` THEN
786 ASM_SIMP_TAC[ADD_CLAUSES; DIVIDES_LMUL; DIVIDES_REFL] THEN
788 ASM_SIMP_TAC[ADDITION_FORMULA_POS] THEN
789 SUBGOAL_THEN `~((Y a m) divides (X a (q * m) * Y a r))` MP_TAC THENL
791 REWRITE_TAC[TAUT `~a ==> ~b <=> b ==> a`] THEN DISCH_TAC THEN
792 MATCH_MP_TAC DIVIDES_ADD_REVL THEN
793 EXISTS_TAC `X a r * Y a (q * m)` THEN
794 ASM_REWRITE_TAC[] THEN
795 GEN_REWRITE_TAC (funpow 3 RAND_CONV) [MULT_SYM] THEN
796 ASM_SIMP_TAC[DIVIDES_LMUL; Y_DIVIDES_LEMMA]] THEN
797 DISCH_THEN(MP_TAC o MATCH_MP
798 (REWRITE_RULE[IMP_CONJ] COPRIME_DIVPROD)) THEN
799 REWRITE_TAC[NOT_IMP] THEN CONJ_TAC THENL
800 [MP_TAC(SPECL [`a:num`; `q * m:num`] XY_COPRIME) THEN ASM_REWRITE_TAC[] THEN
801 ONCE_REWRITE_TAC[TAUT `a ==> b <=> ~b ==> ~a`] THEN
802 REWRITE_TAC[coprime; NOT_FORALL_THM; NOT_IMP] THEN
803 MATCH_MP_TAC MONO_EXISTS THEN X_GEN_TAC `d:num` THEN
804 STRIP_TAC THEN ASM_REWRITE_TAC[] THEN ONCE_REWRITE_TAC[MULT_SYM] THEN
805 ASM_MESON_TAC[DIVIDES_TRANS; Y_DIVIDES_LEMMA]; ALL_TAC] THEN
806 DISCH_THEN(MP_TAC o MATCH_MP DIVIDES_LE) THEN
807 ASM_SIMP_TAC[DE_MORGAN_THM; NOT_LE; Y_INCREASES_LT] THEN
808 ONCE_REWRITE_TAC[GSYM(CONJUNCT1 Y_CLAUSES)] THEN ASM_SIMP_TAC[Y_INJ]);;
810 (* ------------------------------------------------------------------------- *)
811 (* This lemma would be trivial from binomial theorem. *)
812 (* ------------------------------------------------------------------------- *)
814 let BINOMIAL_TRIVIALITY = prove
816 (&x + &y * sqrt(&d)) pow (n + 2) =
818 &(n + 2) * &x pow (n + 1) * &y * sqrt(&d) +
819 &(((n + 1) * (n + 2)) DIV 2) * &x pow n * &y pow 2 * &d +
820 &p * &y pow 3 + &q * &y pow 3 * sqrt(&d)`,
821 GEN_TAC THEN GEN_TAC THEN GEN_TAC THEN INDUCT_TAC THENL
822 [REPEAT(EXISTS_TAC `0`) THEN CONV_TAC NUM_REDUCE_CONV THEN
823 REWRITE_TAC[REAL_POW_1; real_pow; REAL_MUL_LZERO; REAL_ADD_RID] THEN
824 REWRITE_TAC[REAL_MUL_LID] THEN REWRITE_TAC[REAL_POW_2] THEN
825 REWRITE_TAC[REAL_ARITH
826 `(x + y) * (x + y) = x * x + &2 * x * y + y * y`] THEN
827 AP_TERM_TAC THEN AP_TERM_TAC THEN
828 ONCE_REWRITE_TAC[AC REAL_MUL_AC `(a * b) * (a * b) = (a * a) * b * b`] THEN
829 SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_POS]; ALL_TAC] THEN
830 GEN_REWRITE_TAC (funpow 2 BINDER_CONV o LAND_CONV o TOP_DEPTH_CONV)
831 [ADD_CLAUSES; real_pow] THEN
832 FIRST_ASSUM(X_CHOOSE_THEN `p:num` (X_CHOOSE_THEN `q:num` SUBST1_TAC)) THEN
833 REWRITE_TAC[REAL_ARITH
834 `(x + y) * (xn + xn1 + xn2 + p + q) =
835 (x * xn) + (x * xn1 + y * xn) + (x * xn2 + y * xn1) +
836 (y * xn2 + p * x + q * y) + (p * y + q * x)`] THEN
837 ONCE_REWRITE_TAC[REAL_ARITH
838 `x * n2 * xn1 * y * d + (y * d) * xn2 = (n2 * x * xn1 + xn2) * y * d`] THEN
839 REWRITE_TAC[GSYM(CONJUNCT2 real_pow)] THEN
840 REWRITE_TAC[ARITH_RULE `SUC(n + m) = n + SUC m`] THEN
841 REWRITE_TAC[ARITH_RULE `SUC n + m = n + SUC m`] THEN
842 CONV_TAC NUM_REDUCE_CONV THEN
843 REWRITE_TAC[REAL_ARITH `&n * x + x = (&n + &1) * x`] THEN
844 REWRITE_TAC[REAL_OF_NUM_ADD; ARITH_RULE `(n + 2) + 1 = n + 3`] THEN
845 REWRITE_TAC[GSYM REAL_ADD_ASSOC; GSYM REAL_MUL_ASSOC; REAL_EQ_LADD] THEN
846 ONCE_REWRITE_TAC[REAL_ARITH
847 `x * n12 * xn * y2 * d + y * s * n2 * xn1 * y * s + a =
848 (n12 * (x * xn) * y2 * d + n2 * xn1 * (y * y) * (s * s)) + a`] THEN
849 REWRITE_TAC[GSYM REAL_POW_2; GSYM(CONJUNCT2 real_pow)] THEN
850 SIMP_TAC[SQRT_POW_2; REAL_POS] THEN
851 REWRITE_TAC[ADD1; REAL_MUL_ASSOC; GSYM REAL_ADD_RDISTRIB] THEN
852 SUBGOAL_THEN `&(((n + 1) * (n + 2)) DIV 2) + &(n + 2) =
853 &(((n + 2) * (n + 3)) DIV 2)`
855 [REWRITE_TAC[REAL_OF_NUM_ADD; REAL_OF_NUM_EQ] THEN
856 CONV_TAC SYM_CONV THEN MATCH_MP_TAC DIV_UNIQ THEN
857 EXISTS_TAC `0` THEN REWRITE_TAC[ARITH; ADD_CLAUSES] THEN
858 REWRITE_TAC[ARITH_RULE `(n + 2) * (n + 3) = n * n + 5 * n + 6`] THEN
859 REWRITE_TAC[ARITH_RULE
860 `(x + 5 * n + 6 = (y + n + 2) * 2) <=> (x + 3 * n + 2 = 2 * y)`] THEN
861 REWRITE_TAC[ARITH_RULE `n * n + 3 * n + 2 = (n + 1) * (n + 2)`] THEN
862 SUBGOAL_THEN `EVEN((n + 1) * (n + 2))` MP_TAC THENL
863 [REWRITE_TAC[EVEN_MULT; EVEN_ADD; ARITH_EVEN] THEN
864 CONV_TAC(EQT_INTRO o TAUT); ALL_TAC] THEN
865 SIMP_TAC[EVEN_EXISTS; LEFT_IMP_EXISTS_THM] THEN
866 SIMP_TAC[DIV_MULT; ARITH_EQ]; ALL_TAC] THEN
867 REWRITE_TAC[REAL_EQ_LADD] THEN REWRITE_TAC[GSYM REAL_MUL_ASSOC] THEN
868 ONCE_REWRITE_TAC[REAL_ARITH `q * y3 * s * y * s = q * y * y3 * s * s`] THEN
869 SIMP_TAC[GSYM REAL_POW_2; SQRT_POW_2; REAL_POS] THEN
870 ONCE_REWRITE_TAC[REAL_ARITH
871 `y * s * nn * xn * y2 * d = nn * d * xn * (y * y2) * s`] THEN
872 REWRITE_TAC[GSYM(CONJUNCT2 real_pow)] THEN
873 EXISTS_TAC `p * x + q * y * d:num` THEN REWRITE_TAC[ARITH_SUC] THEN
874 EXISTS_TAC `((n + 1) * (n + 2)) DIV 2 * d * x EXP n +
876 REWRITE_TAC[GSYM REAL_OF_NUM_MUL; GSYM REAL_OF_NUM_ADD;
877 GSYM REAL_OF_NUM_POW] THEN
878 REWRITE_TAC[REAL_ADD_LDISTRIB; REAL_ADD_RDISTRIB] THEN
879 REWRITE_TAC[REAL_MUL_AC] THEN REWRITE_TAC[REAL_ADD_AC]);;
881 (* ------------------------------------------------------------------------- *)
882 (* A lower bound theorem. *)
883 (* ------------------------------------------------------------------------- *)
885 let Y_LOWERBOUND = prove
886 (`!a n. (2 * a - 1) EXP n <= Y a (n + 1)`,
887 GEN_TAC THEN INDUCT_TAC THEN REWRITE_TAC[EXP; ARITH; Y_CLAUSES] THEN
888 ASM_CASES_TAC `a = 0` THEN ASM_REWRITE_TAC[ARITH; MULT_CLAUSES; LE_0] THEN
889 REWRITE_TAC[ARITH_RULE `SUC n + 1 = n + 2`; Y_CLAUSES] THEN
890 MATCH_MP_TAC LE_TRANS THEN
891 EXISTS_TAC `(2 * a - 1) * Y a (n + 1)` THEN
892 ASM_REWRITE_TAC[LE_MULT_LCANCEL] THEN
893 REWRITE_TAC[RIGHT_SUB_DISTRIB; MULT_CLAUSES; GSYM MULT_ASSOC] THEN
894 MATCH_MP_TAC(ARITH_RULE `a <= b ==> c - b <= c - a:num`) THEN
895 ASM_SIMP_TAC[Y_INCREASES]);;
897 let Y_UPPERBOUND = prove
898 (`!a n. Y a (n + 1) <= (2 * a) EXP n`,
899 GEN_TAC THEN INDUCT_TAC THEN
900 REWRITE_TAC[EXP; ADD_CLAUSES; Y_CLAUSES; LE_REFL] THEN
901 REWRITE_TAC[ARITH_RULE `SUC(n + 1) = n + 2`; Y_CLAUSES] THEN
902 MATCH_MP_TAC(ARITH_RULE `a <= b ==> a - c <= b:num`) THEN
903 ASM_REWRITE_TAC[MULT_ASSOC; LE_MULT_LCANCEL]);;
905 (* ------------------------------------------------------------------------- *)
906 (* Now a key congruence. *)
907 (* ------------------------------------------------------------------------- *)
909 let XY_Y3_CONGRUENCE = prove
911 ==> ?q. Y a (n * k) =
912 k * (X a n) EXP (k - 1) * Y a n + q * (Y a n) EXP 3`,
913 REPEAT STRIP_TAC THEN ASM_CASES_TAC `k = 0` THENL
915 ASM_REWRITE_TAC[Y_CLAUSES; MULT_CLAUSES; ADD_CLAUSES; SUB_0]; ALL_TAC] THEN
916 ASM_CASES_TAC `a = 1` THENL
917 [ASM_REWRITE_TAC[X_DEGENERATE; Y_DEGENERATE; EXP_ONE] THEN
918 EXISTS_TAC `0` THEN REWRITE_TAC[ADD_CLAUSES; MULT_CLAUSES] THEN
919 REWRITE_TAC[MULT_AC]; ALL_TAC] THEN
920 ASM_CASES_TAC `k = 1` THENL
921 [ASM_REWRITE_TAC[MULT_CLAUSES; SUB_REFL; EXP] THEN
922 EXISTS_TAC `0` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES]; ALL_TAC] THEN
923 MP_TAC(SPECL [`a:num`; `n * k:num`] XY_POWER_POS) THEN ASM_REWRITE_TAC[] THEN
924 REWRITE_TAC[GSYM REAL_POW_POW] THEN
925 MP_TAC(SPECL [`a:num`; `n:num`] XY_POWER_POS) THEN ASM_REWRITE_TAC[] THEN
926 REWRITE_TAC[GSYM REAL_POW_POW] THEN DISCH_THEN(SUBST1_TAC o SYM) THEN
927 SUBGOAL_THEN `2 <= k` MP_TAC THENL
928 [MAP_EVERY UNDISCH_TAC [`~(k = 0)`; `~(k = 1)`] THEN ARITH_TAC;
930 GEN_REWRITE_TAC LAND_CONV [LE_EXISTS] THEN
931 DISCH_THEN(X_CHOOSE_THEN `d:num`
932 (SUBST1_TAC o ONCE_REWRITE_RULE[ADD_SYM])) THEN
933 MP_TAC(SPECL [`X a n`; `Y a n`; `a EXP 2 - 1`; `d:num`]
934 BINOMIAL_TRIVIALITY) THEN
935 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` (SUBST1_TAC o SYM) THENL
936 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
937 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
938 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
939 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
940 DISCH_THEN(X_CHOOSE_THEN `p:num` (X_CHOOSE_THEN `q:num` SUBST1_TAC)) THEN
941 ONCE_REWRITE_TAC[REAL_ARITH
942 `x1 + y1 + x2 + x3 + y2 = (x1 + x2 + x3) + (y1 + y2)`] THEN
943 REWRITE_TAC[REAL_MUL_ASSOC; GSYM REAL_ADD_RDISTRIB] THEN
944 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` SUBST1_TAC THENL
945 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
946 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
947 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
948 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
949 REWRITE_TAC[REAL_OF_NUM_POW; REAL_OF_NUM_MUL; REAL_OF_NUM_ADD] THEN
950 SUBGOAL_THEN `&a pow 2 - &1 = &(a EXP 2 - 1)` (SUBST1_TAC o SYM) THENL
951 [REWRITE_TAC[REAL_OF_NUM_POW] THEN MATCH_MP_TAC REAL_OF_NUM_SUB THEN
952 REWRITE_TAC[GSYM REAL_OF_NUM_LE; GSYM REAL_OF_NUM_POW] THEN
953 ASM_SIMP_TAC[REAL_POW_LE_1; REAL_OF_NUM_LE;
954 ARITH_RULE `~(a = 0) ==> 1 <= a`]; ALL_TAC] THEN
955 ASM_SIMP_TAC[SQRT_LINEAR_EQ;
956 ARITH_RULE `~(p = 0) /\ ~(p = 1) ==> 2 <= p`] THEN
957 DISCH_THEN(K ALL_TAC) THEN
958 REWRITE_TAC[ARITH_RULE `(d + 2) - 1 = d + 1`] THEN
959 EXISTS_TAC `q:num` THEN REWRITE_TAC[GSYM MULT_ASSOC]);;
961 (* ------------------------------------------------------------------------- *)
962 (* The other key divisibility result. *)
963 (* ------------------------------------------------------------------------- *)
965 let Y2_DIVIDES = prove
967 ==> (((Y a m) EXP 2) divides (Y a n) <=> (m * Y a m) divides n)`,
968 REPEAT STRIP_TAC THEN ASM_CASES_TAC `m = 0` THENL
969 [ASM_REWRITE_TAC[Y_CLAUSES; MULT_CLAUSES; DIVIDES_ZERO; EXP_2] THEN
970 GEN_REWRITE_TAC (LAND_CONV o RAND_CONV) [GSYM(CONJUNCT1 Y_CLAUSES)] THEN
971 ASM_SIMP_TAC[Y_INJ]; ALL_TAC] THEN
972 SUBGOAL_THEN `~(Y a m = 0)` ASSUME_TAC THENL
973 [GEN_REWRITE_TAC (RAND_CONV o RAND_CONV) [GSYM(CONJUNCT1 Y_CLAUSES)] THEN
974 ASM_SIMP_TAC[Y_INJ]; ALL_TAC] THEN
976 `!c. (a ==> c) /\ (b ==> c) /\ (c ==> (a <=> b)) ==> (a <=> b)`) THEN
977 EXISTS_TAC `m divides n` THEN REPEAT CONJ_TAC THENL
979 SUBGOAL_THEN `(Y a m) divides (Y a n)` MP_TAC THENL
980 [ALL_TAC; ASM_SIMP_TAC[Y_DIVIDES]] THEN
981 UNDISCH_TAC `((Y a m) EXP 2) divides (Y a n)` THEN
982 REWRITE_TAC[divides; EXP_2; GSYM MULT_ASSOC] THEN MESON_TAC[];
983 REWRITE_TAC[divides; GSYM MULT_ASSOC] THEN MESON_TAC[];
985 GEN_REWRITE_TAC LAND_CONV [divides] THEN
986 DISCH_THEN(X_CHOOSE_THEN `k:num` SUBST1_TAC) THEN
987 MP_TAC(SPECL [`a:num`; `m:num`; `k:num`] XY_Y3_CONGRUENCE) THEN
988 ASM_REWRITE_TAC[] THEN
989 DISCH_THEN(X_CHOOSE_THEN `q:num` SUBST1_TAC) THEN
990 MATCH_MP_TAC EQ_TRANS THEN
991 EXISTS_TAC `((Y a m) EXP 2) divides (k * (X a m) EXP (k - 1) * Y a m)` THEN
993 [REWRITE_TAC[num_CONV `3`; EXP] THEN
994 MESON_TAC[DIVIDES_ADD; DIVIDES_ADD_REVL; DIVIDES_LMUL; DIVIDES_REFL];
996 REWRITE_TAC[MULT_ASSOC] THEN
997 GEN_REWRITE_TAC (LAND_CONV o RAND_CONV) [MULT_SYM] THEN
998 REWRITE_TAC[EXP_2; GSYM MULT_ASSOC] THEN
999 ASM_SIMP_TAC[DIVIDES_LMUL2_EQ] THEN
1000 EQ_TAC THEN SIMP_TAC[DIVIDES_RMUL] THEN
1001 DISCH_TAC THEN MATCH_MP_TAC COPRIME_DIVPROD THEN
1002 EXISTS_TAC `X a m EXP (k - 1)` THEN
1003 ONCE_REWRITE_TAC[MULT_SYM] THEN ASM_REWRITE_TAC[] THEN
1004 MATCH_MP_TAC COPRIME_EXP THEN
1005 ONCE_REWRITE_TAC[COPRIME_SYM] THEN ASM_SIMP_TAC[XY_COPRIME]);;
1007 (* ------------------------------------------------------------------------- *)
1008 (* Some more congruences. *)
1009 (* ------------------------------------------------------------------------- *)
1011 let Y_N_MOD2 = prove
1012 (`!a n. ~(a = 0) ==> ?q. Y a n = 2 * q + n`,
1013 GEN_TAC THEN REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN DISCH_TAC THEN
1014 MATCH_MP_TAC PELL_INDUCTION THEN REWRITE_TAC[Y_CLAUSES] THEN
1015 REPEAT CONJ_TAC THENL
1016 [EXISTS_TAC `0` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES];
1017 EXISTS_TAC `0` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES];
1019 REWRITE_TAC[RIGHT_AND_EXISTS_THM; LEFT_AND_EXISTS_THM;
1020 LEFT_IMP_EXISTS_THM] THEN
1021 MAP_EVERY X_GEN_TAC [`n:num`; `q1:num`; `q2:num`] THEN STRIP_TAC THEN
1022 FIRST_ASSUM(MP_TAC o SPEC `n:num` o MATCH_MP Y_INCREASES) THEN
1023 ASM_REWRITE_TAC[] THEN
1024 REWRITE_TAC[ARITH_RULE `2 * q1 + n <= 2 * q2 + n + 1 <=> q1 <= q2`] THEN
1026 EXISTS_TAC `(2 * a * q2 - q1) + (a - 1) * (n + 1)` THEN
1027 MATCH_MP_TAC(ARITH_RULE
1028 `v <= u /\ y <= x /\ (2 * (x + z) + w + v = 2 * y + u)
1029 ==> (u - v = 2 * ((x - y) + z) + w)`) THEN
1030 REPEAT CONJ_TAC THENL
1031 [REWRITE_TAC[LEFT_ADD_DISTRIB] THEN
1032 MATCH_MP_TAC(ARITH_RULE
1033 `x <= u /\ y <= v ==> 2 * x + y <= 2 * u + v + w`) THEN
1034 REWRITE_TAC[MULT_ASSOC] THEN CONJ_TAC THEN
1035 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `n = 1 * n`] THENL
1036 [MATCH_MP_TAC LE_MULT2 THEN ASM_REWRITE_TAC[];
1037 REWRITE_TAC[LE_MULT_RCANCEL] THEN DISJ1_TAC] THEN
1038 UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC;
1039 REWRITE_TAC[MULT_ASSOC] THEN
1040 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `n = 1 * n`] THEN
1041 MATCH_MP_TAC LE_MULT2 THEN ASM_REWRITE_TAC[] THEN
1042 UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC;
1043 UNDISCH_TAC `~(a = 0)` THEN SPEC_TAC(`a:num`,`a:num`) THEN
1044 INDUCT_TAC THEN REWRITE_TAC[NOT_SUC] THEN
1045 REWRITE_TAC[ARITH_RULE `SUC a - 1 = a`] THEN
1046 REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES] THEN
1049 let Y_N_MODA1 = prove
1050 (`!a n. ~(a = 0) ==> ?q. Y a n = q * (a - 1) + n`,
1051 GEN_TAC THEN REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN DISCH_TAC THEN
1052 ASM_CASES_TAC `a = 1` THENL
1053 [ASM_REWRITE_TAC[SUB_REFL; Y_DEGENERATE; MULT_CLAUSES; ADD_CLAUSES];
1055 MATCH_MP_TAC PELL_INDUCTION THEN REWRITE_TAC[Y_CLAUSES] THEN
1056 REPEAT CONJ_TAC THENL
1057 [EXISTS_TAC `0` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES];
1058 EXISTS_TAC `0` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES];
1060 REWRITE_TAC[RIGHT_AND_EXISTS_THM; LEFT_AND_EXISTS_THM;
1061 LEFT_IMP_EXISTS_THM] THEN
1062 MAP_EVERY X_GEN_TAC [`n:num`; `q1:num`; `q2:num`] THEN
1064 FIRST_ASSUM(MP_TAC o SPEC `n:num` o MATCH_MP Y_INCREASES) THEN
1065 ASM_REWRITE_TAC[] THEN
1066 REWRITE_TAC[ARITH_RULE `q1 + n <= q2 + n + 1 <=> q1 <= q2 + 1`] THEN
1067 ASM_CASES_TAC `q2 = 0` THENL
1068 [ASM_REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES] THEN
1069 REWRITE_TAC[ARITH_RULE `a <= 1 <=> (a = 0) \/ (a = 1)`] THEN
1070 ASM_REWRITE_TAC[MULT_EQ_0; MULT_EQ_1] THEN
1071 ASM_REWRITE_TAC[ARITH_RULE `(a - 1 = 0) <=> (a = 0) \/ (a = 1)`] THEN
1072 SIMP_TAC[ARITH_RULE `(a - 1 = 1) <=> (a = 2)`] THEN
1073 STRIP_TAC THEN ASM_REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES] THENL
1074 [EXISTS_TAC `2 * (n + 1)` THEN
1075 UNDISCH_TAC `~(a = 0)` THEN SPEC_TAC(`a:num`,`b:num`) THEN
1076 INDUCT_TAC THEN REWRITE_TAC[NOT_SUC] THEN
1077 REWRITE_TAC[ARITH_RULE `SUC n - 1 = n`] THEN
1078 REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES] THEN
1079 MATCH_MP_TAC(ARITH_RULE `(a + c = b) ==> (b - a = c:num)`) THEN
1081 REWRITE_TAC[MULT_ASSOC; ARITH] THEN
1082 REWRITE_TAC[ARITH_RULE `4 * (n + 1) - (1 + n) = 3 * (n + 1)`] THEN
1083 EXISTS_TAC `2 * n + 1` THEN ARITH_TAC];
1085 DISCH_THEN(fun th ->
1086 EXISTS_TAC `2 * (n + 1) + 2 * a * q2 - q1` THEN MP_TAC th) THEN
1087 UNDISCH_TAC `~(a = 1)` THEN
1088 UNDISCH_TAC `~(a = 0)` THEN SPEC_TAC(`a:num`,`b:num`) THEN
1089 INDUCT_TAC THEN REWRITE_TAC[NOT_SUC] THEN
1090 REWRITE_TAC[ARITH_RULE `(SUC n = 1) <=> (n = 0)`] THEN DISCH_TAC THEN
1091 REWRITE_TAC[ARITH_RULE `SUC n - 1 = n`] THEN DISCH_TAC THEN
1092 REWRITE_TAC[RIGHT_ADD_DISTRIB; RIGHT_SUB_DISTRIB] THEN
1093 MATCH_MP_TAC(ARITH_RULE
1094 `v <= u /\ y <= x /\ (u + y = z + x + w + v)
1095 ==> (u - v = (z + (x - y)) + w:num)`) THEN
1096 REPEAT CONJ_TAC THENL
1097 [GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `a = 1 * a`] THEN
1098 REWRITE_TAC[MULT_ASSOC] THEN MATCH_MP_TAC LE_MULT2 THEN
1099 ASM_REWRITE_TAC[ARITH_RULE `q1 + n <= q2 + n + 1 <=> q1 <= q2 + 1`] THEN
1100 REWRITE_TAC[MULT_CLAUSES] THEN ARITH_TAC;
1101 MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `q2 * b + 1` THEN
1102 ASM_REWRITE_TAC[] THEN
1103 REWRITE_TAC[ARITH_RULE `a + 1 <= b <=> a < b`] THEN
1104 ASM_SIMP_TAC[LT_MULT_RCANCEL] THEN
1105 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `a = 1 * a`] THEN
1106 REWRITE_TAC[MULT_ASSOC] THEN
1107 ASM_SIMP_TAC[LT_MULT_RCANCEL] THEN
1108 REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES] THEN ARITH_TAC;
1109 REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES] THEN ARITH_TAC]);;
1111 let X_CONGRUENT = prove
1112 (`!a b c n. ~(a = 0) ==> ?q. X (a + b * c) n = X a n + q * c`,
1113 GEN_TAC THEN GEN_TAC THEN GEN_TAC THEN
1114 REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN DISCH_TAC THEN
1115 ASM_CASES_TAC `b * c = 0` THENL
1116 [GEN_TAC THEN EXISTS_TAC `0` THEN
1117 ASM_REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES]; ALL_TAC] THEN
1118 UNDISCH_TAC `~(b * c = 0)` THEN
1119 REWRITE_TAC[MULT_EQ_0; DE_MORGAN_THM] THEN STRIP_TAC THEN
1120 MATCH_MP_TAC PELL_INDUCTION THEN REWRITE_TAC[X_CLAUSES] THEN
1121 REPEAT CONJ_TAC THENL
1122 [EXISTS_TAC `0` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES];
1123 EXISTS_TAC `b:num` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES];
1125 REWRITE_TAC[RIGHT_AND_EXISTS_THM; LEFT_AND_EXISTS_THM;
1126 LEFT_IMP_EXISTS_THM] THEN
1127 MAP_EVERY X_GEN_TAC [`n:num`; `q1:num`; `q2:num`] THEN
1128 STRIP_TAC THEN ASM_REWRITE_TAC[] THEN
1129 REWRITE_TAC[ARITH_RULE
1130 `2 * (x + y) * (u + v) = 2 * x * u + 2 * u * y + 2 * (x + y) * v`] THEN
1131 EXISTS_TAC `(2 * X a (n + 1) * b + 2 * (a + b * c) * q2) - q1` THEN
1132 MATCH_MP_TAC(ARITH_RULE
1133 `a <= x /\ b <= y + z:num /\ ((x - a) + ((y + z) - b) = u)
1134 ==> ((x + y + z) - (a + b) = u)`) THEN
1135 REWRITE_TAC[RIGHT_SUB_DISTRIB; RIGHT_ADD_DISTRIB; GSYM MULT_ASSOC] THEN
1137 [MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `1 * X a (n + 1)` THEN CONJ_TAC THENL
1138 [ASM_SIMP_TAC[MULT_CLAUSES; X_INCREASES]; ALL_TAC] THEN
1139 REWRITE_TAC[MULT_ASSOC; LE_MULT_RCANCEL] THEN DISJ1_TAC THEN
1140 UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC; ALL_TAC] THEN
1141 MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `X (a + b * c) n` THEN CONJ_TAC THENL
1142 [ASM_REWRITE_TAC[ONCE_REWRITE_RULE[ADD_SYM] LE_ADD]; ALL_TAC] THEN
1143 MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `X (a + b * c) (n + 1)` THEN
1144 CONJ_TAC THENL [ASM_SIMP_TAC[X_INCREASES; ADD_EQ_0]; ALL_TAC] THEN
1145 ASM_REWRITE_TAC[] THEN MATCH_MP_TAC LE_ADD2 THEN CONJ_TAC THENL
1146 [GEN_REWRITE_TAC RAND_CONV [MULT_SYM] THEN
1147 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `a = a * 1`] THEN
1148 REWRITE_TAC[GSYM MULT_ASSOC; LE_MULT_LCANCEL] THEN
1149 ASM_REWRITE_TAC[ARITH_RULE `1 <= x <=> ~(x = 0)`; MULT_EQ_0; ARITH_EQ];
1150 MATCH_MP_TAC(ARITH_RULE `a <= y ==> a <= 2 * (x + y)`) THEN
1151 ONCE_REWRITE_TAC[AC MULT_AC `a * b * c * d = (a * b) * (c * d:num)`] THEN
1152 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `a = 1 * a`] THEN
1153 REWRITE_TAC[LE_MULT_RCANCEL] THEN
1154 ASM_REWRITE_TAC[ARITH_RULE `1 <= x <=> ~(x = 0)`; MULT_EQ_0; ARITH_EQ]]);;
1156 let Y_CONGRUENT = prove
1157 (`!a b c n. ~(a = 0) ==> ?q. Y (a + b * c) n = Y a n + q * c`,
1158 GEN_TAC THEN GEN_TAC THEN GEN_TAC THEN
1159 REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN DISCH_TAC THEN
1160 ASM_CASES_TAC `b * c = 0` THENL
1161 [GEN_TAC THEN EXISTS_TAC `0` THEN
1162 ASM_REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES]; ALL_TAC] THEN
1163 UNDISCH_TAC `~(b * c = 0)` THEN
1164 REWRITE_TAC[MULT_EQ_0; DE_MORGAN_THM] THEN STRIP_TAC THEN
1165 MATCH_MP_TAC PELL_INDUCTION THEN REWRITE_TAC[Y_CLAUSES] THEN
1166 REPEAT CONJ_TAC THENL
1167 [EXISTS_TAC `0` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES];
1168 EXISTS_TAC `0` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES];
1170 REWRITE_TAC[RIGHT_AND_EXISTS_THM; LEFT_AND_EXISTS_THM;
1171 LEFT_IMP_EXISTS_THM] THEN
1172 MAP_EVERY X_GEN_TAC [`n:num`; `q1:num`; `q2:num`] THEN
1173 STRIP_TAC THEN ASM_REWRITE_TAC[] THEN
1174 REWRITE_TAC[ARITH_RULE
1175 `2 * (x + y) * (u + v) = 2 * x * u + 2 * u * y + 2 * (x + y) * v`] THEN
1176 EXISTS_TAC `(2 * Y a (n + 1) * b + 2 * (a + b * c) * q2) - q1` THEN
1177 MATCH_MP_TAC(ARITH_RULE
1178 `a <= x /\ b <= y + z:num /\ ((x - a) + ((y + z) - b) = u)
1179 ==> ((x + y + z) - (a + b) = u)`) THEN
1180 REWRITE_TAC[RIGHT_SUB_DISTRIB; RIGHT_ADD_DISTRIB; GSYM MULT_ASSOC] THEN
1182 [MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `1 * Y a (n + 1)` THEN CONJ_TAC THENL
1183 [ASM_SIMP_TAC[MULT_CLAUSES; Y_INCREASES]; ALL_TAC] THEN
1184 REWRITE_TAC[MULT_ASSOC; LE_MULT_RCANCEL] THEN DISJ1_TAC THEN
1185 UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC; ALL_TAC] THEN
1186 MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `Y (a + b * c) n` THEN CONJ_TAC THENL
1187 [ASM_REWRITE_TAC[ONCE_REWRITE_RULE[ADD_SYM] LE_ADD]; ALL_TAC] THEN
1188 MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `Y (a + b * c) (n + 1)` THEN
1189 CONJ_TAC THENL [ASM_SIMP_TAC[Y_INCREASES; ADD_EQ_0]; ALL_TAC] THEN
1190 ASM_REWRITE_TAC[] THEN MATCH_MP_TAC LE_ADD2 THEN CONJ_TAC THENL
1191 [GEN_REWRITE_TAC RAND_CONV [MULT_SYM] THEN
1192 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `a = a * 1`] THEN
1193 REWRITE_TAC[GSYM MULT_ASSOC; LE_MULT_LCANCEL] THEN
1194 ASM_REWRITE_TAC[ARITH_RULE `1 <= x <=> ~(x = 0)`; MULT_EQ_0; ARITH_EQ];
1195 MATCH_MP_TAC(ARITH_RULE `a <= y ==> a <= 2 * (x + y)`) THEN
1196 ONCE_REWRITE_TAC[AC MULT_AC `a * b * c * d = (a * b) * (c * d:num)`] THEN
1197 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `a = 1 * a`] THEN
1198 REWRITE_TAC[LE_MULT_RCANCEL] THEN
1199 ASM_REWRITE_TAC[ARITH_RULE `1 <= x <=> ~(x = 0)`; MULT_EQ_0; ARITH_EQ]]);;
1201 (* ------------------------------------------------------------------------- *)
1202 (* A more important congruence. *)
1203 (* ------------------------------------------------------------------------- *)
1205 let X_CONGRUENT_2NJ_POS = prove
1206 (`!a n j. ~(a = 0) ==> ?q. X a (2 * n + j) + X a j = q * X a n`,
1207 REPEAT STRIP_TAC THEN
1208 MP_TAC(SPECL [`a:num`; `n:num`; `n + j:num`] ADDITION_FORMULA_POS) THEN
1209 ASM_REWRITE_TAC[ARITH_RULE `n + n + j = 2 * n + j`] THEN
1210 DISCH_THEN(SUBST1_TAC o CONJUNCT1) THEN
1211 MP_TAC(SPECL [`a:num`; `n:num`; `j:num`] ADDITION_FORMULA_POS) THEN
1212 ASM_REWRITE_TAC[] THEN DISCH_THEN(SUBST1_TAC o CONJUNCT2) THEN
1213 ONCE_REWRITE_TAC[ARITH_RULE
1214 `(xn * a + d * yn * (xn * yj + xj * yn)) + xj =
1215 xn * (a + d * yn * yj) + xj * (d * yn * yn + 1)`] THEN
1216 ASM_SIMP_TAC[GSYM XY_ARE_SOLUTIONS; GSYM EXP_2] THEN
1217 REWRITE_TAC[EXP_2; ARITH_RULE
1218 `xn * a + xj * xn * xn = (a + xj * xn) * xn:num`] THEN
1221 let X_CONGRUENT_4NJ_POS = prove
1222 (`!a n j. ~(a = 0) ==> ?q. X a (4 * n + j) = q * X a n + X a j`,
1223 REPEAT STRIP_TAC THEN
1224 MP_TAC(SPECL [`a:num`; `n:num`; `2 * n + j`] X_CONGRUENT_2NJ_POS) THEN
1225 ASM_REWRITE_TAC[ARITH_RULE `2 * n + 2 * n + j = 4 * n + j`] THEN
1226 DISCH_THEN(X_CHOOSE_THEN `q1:num` MP_TAC) THEN
1227 DISCH_THEN(MP_TAC o C AP_THM `X a j` o AP_TERM `(+):num->num->num`) THEN
1228 REWRITE_TAC[GSYM ADD_ASSOC] THEN
1229 MP_TAC(SPECL [`a:num`; `n:num`; `j:num`] X_CONGRUENT_2NJ_POS) THEN
1230 ASM_REWRITE_TAC[] THEN DISCH_THEN(X_CHOOSE_THEN `q2:num` MP_TAC) THEN
1231 DISCH_THEN SUBST1_TAC THEN
1232 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1233 `(y + q2 = q1 + x) ==> x <= y ==> (y = (q1 - q2) + x:num)`)) THEN
1234 ASM_SIMP_TAC[X_INCREASES_LE; ARITH_RULE `j <= 4 * n + j`] THEN
1235 DISCH_THEN(K ALL_TAC) THEN REWRITE_TAC[GSYM RIGHT_SUB_DISTRIB] THEN
1238 let X_CONGRUENT_4MNJ_POS = prove
1239 (`!a m n j. ~(a = 0) ==> ?q. X a (4 * m * n + j) = q * X a n + X a j`,
1240 GEN_TAC THEN REWRITE_TAC[RIGHT_FORALL_IMP_THM] THEN
1241 DISCH_TAC THEN INDUCT_TAC THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES] THENL
1242 [REPEAT GEN_TAC THEN EXISTS_TAC `0` THEN
1243 REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES]; ALL_TAC] THEN
1244 UNDISCH_TAC `!n j. ?q. X a (4 * m * n + j) = q * X a n + X a j` THEN
1245 REPEAT(MATCH_MP_TAC MONO_FORALL THEN GEN_TAC) THEN
1246 DISCH_THEN(X_CHOOSE_THEN `q1:num` ASSUME_TAC) THEN
1247 MP_TAC(SPECL [`a:num`; `n:num`; `4 * m * n + j`] X_CONGRUENT_4NJ_POS) THEN
1248 ASM_REWRITE_TAC[ARITH_RULE
1249 `4 * (m * n + n) + j = 4 * n + 4 * m * n + j`] THEN
1250 DISCH_THEN(X_CHOOSE_THEN `q2:num` SUBST1_TAC) THEN
1251 EXISTS_TAC `q2 + q1:num` THEN ARITH_TAC);;
1253 let X_CONGRUENT_2NJ_NEG_LEMMA = prove
1254 (`!a n j. ~(a = 0) /\ j <= n ==> ?q. X a (2 * n - j) + X a j = q * X a n`,
1255 REPEAT STRIP_TAC THEN ASM_CASES_TAC `j = n:num` THENL
1256 [EXISTS_TAC `2` THEN ASM_REWRITE_TAC[MULT_2; ADD_SUB]; ALL_TAC] THEN
1257 MP_TAC(SPECL [`a:num`; `n:num`; `n - j:num`] ADDITION_FORMULA_POS) THEN
1258 ASM_SIMP_TAC[ARITH_RULE `j <= n ==> (n + n - j = 2 * n - j)`] THEN
1260 MP_TAC(SPECL [`a:num`; `j:num`; `n:num`] ADDITION_FORMULA_NEG) THEN
1261 ASM_REWRITE_TAC[] THEN STRIP_TAC THEN ASM_REWRITE_TAC[] THEN
1262 EXISTS_TAC `(X a j * X a n - (a EXP 2 - 1) * Y a j * Y a n) +
1263 (X a j * X a n - (a EXP 2 - 1) * Y a j * Y a n)` THEN
1264 REWRITE_TAC[ARITH_RULE
1265 `((xn * a + b) + c = (a + d) * xn) <=> (b + c = xn * d:num)`] THEN
1266 REWRITE_TAC[LEFT_SUB_DISTRIB] THEN
1267 MATCH_MP_TAC(ARITH_RULE
1268 `b <= a /\ e <= d /\ (e + a + c = d + b)
1269 ==> ((a - b) + c = d - e:num)`) THEN
1270 REPEAT CONJ_TAC THENL
1271 [REWRITE_TAC[LE_MULT_LCANCEL] THEN REPEAT DISJ2_TAC THEN
1272 FIRST_ASSUM(MATCH_MP_TAC o MATCH_MP (ARITH_RULE
1273 `(c = a - b) ==> 1 <= c ==> b <= a`)) THEN
1274 SUBST1_TAC(SYM(SPEC `a:num` (el 1 (CONJUNCTS Y_CLAUSES)))) THEN
1275 MATCH_MP_TAC Y_INCREASES_LE THEN
1276 ASM_SIMP_TAC[ARITH_RULE `j <= n ==> (1 <= n - j <=> ~(j = n))`];
1277 REWRITE_TAC[LE_MULT_LCANCEL] THEN DISJ2_TAC THEN
1278 FIRST_ASSUM(MATCH_MP_TAC o MATCH_MP (ARITH_RULE
1279 `(c = a - b) ==> 1 <= c ==> b <= a`)) THEN
1280 SUBST1_TAC(SYM(SPEC `a:num` (CONJUNCT1 X_CLAUSES))) THEN
1281 MATCH_MP_TAC X_INCREASES_LE THEN ASM_REWRITE_TAC[LE_0];
1282 REWRITE_TAC[ARITH_RULE
1283 `xn * a * yj * yn + a * yn * xj * yn + xj =
1284 xj * (a * yn * yn + 1) + a * yn * xn * yj`] THEN
1285 ASM_SIMP_TAC[GSYM XY_ARE_SOLUTIONS; GSYM EXP_2] THEN
1286 REWRITE_TAC[EXP_2; MULT_AC]]);;
1288 let X_CONGRUENT_2NJ_NEG = prove
1289 (`!a n j. ~(a = 0) /\ j <= 2 * n ==> ?q. X a (2 * n - j) + X a j = q * X a n`,
1290 REPEAT STRIP_TAC THEN
1291 ASM_CASES_TAC `j <= n:num` THEN ASM_SIMP_TAC[X_CONGRUENT_2NJ_NEG_LEMMA] THEN
1292 MP_TAC(SPECL [`a:num`; `n:num`; `2 * n - j`] X_CONGRUENT_2NJ_NEG_LEMMA) THEN
1293 ASM_SIMP_TAC[ARITH_RULE `~(j <= n) ==> 2 * n - j <= n`] THEN
1294 ASM_SIMP_TAC[ARITH_RULE `y <= x ==> (x - (x - y) = y:num)`] THEN
1297 (* ------------------------------------------------------------------------- *)
1298 (* The cute GCD fact given by Smorynski. *)
1299 (* ------------------------------------------------------------------------- *)
1301 let XY_GCD_LEMMA = prove
1302 (`!a m n. ~(a = 0) /\ m < n
1303 ==> (gcd(Y a m,Y a n) = Y a (gcd(m,n)))`,
1304 GEN_TAC THEN ASM_CASES_TAC `a = 0` THEN ASM_REWRITE_TAC[] THEN
1305 ASM_CASES_TAC `a = 1` THEN ASM_REWRITE_TAC[Y_DEGENERATE] THEN
1306 MATCH_MP_TAC num_WF THEN X_GEN_TAC `m:num` THEN DISCH_TAC THEN
1307 X_GEN_TAC `n:num` THEN DISCH_TAC THEN
1308 MP_TAC(SPECL [`n:num`; `m:num`] DIVISION) THEN
1309 ASM_CASES_TAC `m = 0` THEN ASM_REWRITE_TAC[Y_CLAUSES; GCD_0] THEN
1310 ABBREV_TAC `q = n DIV m` THEN ABBREV_TAC `r = n MOD m` THEN
1311 DISCH_THEN(STRIP_ASSUME_TAC o GSYM) THEN
1312 FIRST_X_ASSUM(MP_TAC o SPEC `r:num`) THEN ASM_REWRITE_TAC[] THEN
1313 DISCH_THEN(MP_TAC o SPEC `m:num`) THEN ASM_REWRITE_TAC[] THEN
1314 MATCH_MP_TAC EQ_IMP THEN BINOP_TAC THENL
1315 [EXPAND_TAC "n" THEN ASM_SIMP_TAC[ADDITION_FORMULA_POS] THEN
1316 GEN_REWRITE_TAC LAND_CONV [GCD_SYM] THEN MATCH_MP_TAC GCD_EQ THEN
1317 X_GEN_TAC `d:num` THEN CONV_TAC SYM_CONV THEN MATCH_MP_TAC(TAUT
1318 `(a ==> (b <=> c)) ==> (a /\ b <=> a /\ c)`) THEN
1319 DISCH_TAC THEN MATCH_MP_TAC EQ_TRANS THEN
1320 EXISTS_TAC `d divides (X a (q * m) * Y a r)` THEN CONJ_TAC THENL
1321 [SUBGOAL_THEN `d divides (Y a (q * m))` MP_TAC THENL
1322 [ASM_MESON_TAC[Y_DIVIDES; DIVIDES_TRANS; DIVIDES_LMUL; DIVIDES_REFL];
1324 MESON_TAC[DIVIDES_ADD; DIVIDES_LMUL; DIVIDES_RMUL; DIVIDES_REFL;
1327 EQ_TAC THEN SIMP_TAC[DIVIDES_LMUL] THEN
1328 SUBGOAL_THEN `coprime(d,X a (q * m))`
1329 (fun th -> MESON_TAC[COPRIME_DIVPROD; th]) THEN
1330 SUBGOAL_THEN `d divides (Y a (q * m))` MP_TAC THENL
1331 [ASM_MESON_TAC[Y_DIVIDES; DIVIDES_TRANS; DIVIDES_LMUL; DIVIDES_REFL];
1333 MP_TAC(SPECL [`a:num`; `q * m:num`] XY_COPRIME) THEN ASM_REWRITE_TAC[] THEN
1334 DISCH_TAC THEN DISCH_TAC THEN REWRITE_TAC[coprime] THEN
1335 X_GEN_TAC `e:num` THEN STRIP_TAC THEN
1336 UNDISCH_TAC `coprime (X a (q * m),Y a (q * m))` THEN
1337 REWRITE_TAC[coprime] THEN DISCH_THEN(MP_TAC o SPEC `e:num`) THEN
1338 DISCH_THEN MATCH_MP_TAC THEN ASM_MESON_TAC[DIVIDES_TRANS];
1339 AP_TERM_TAC THEN EXPAND_TAC "n" THEN
1340 GEN_REWRITE_TAC I [GSYM DIVIDES_ANTISYM] THEN
1341 POP_ASSUM_LIST(K ALL_TAC) THEN NUMBER_TAC]);;
1344 (`!a m n. ~(a = 0) ==> (gcd(Y a m,Y a n) = Y a (gcd(m,n)))`,
1345 REPEAT STRIP_TAC THEN
1346 REPEAT_TCL DISJ_CASES_THEN ASSUME_TAC
1347 (SPECL [`m:num`; `n:num`] LT_CASES)
1349 [ASM_SIMP_TAC[XY_GCD_LEMMA];
1350 ONCE_REWRITE_TAC[GCD_SYM] THEN ASM_SIMP_TAC[XY_GCD_LEMMA];
1351 ASM_REWRITE_TAC[GCD_REFL]]);;
1353 (* ------------------------------------------------------------------------- *)
1354 (* The "step-down" lemma. *)
1355 (* ------------------------------------------------------------------------- *)
1357 let STEP_DOWN_LEMMA = prove
1359 ~(a = 0) /\ ~(a = 1) /\
1360 i <= j /\ j <= 2 * n /\
1361 (X a j = q * X a n + X a i)
1362 ==> (i = j) \/ ((a = 2) /\ (n = 1) /\ (i = 0) /\ (j = 2))`,
1363 REPEAT STRIP_TAC THEN ASM_CASES_TAC `j <= n:num` THENL
1364 [ASM_CASES_TAC `i = j:num` THEN ASM_REWRITE_TAC[] THEN
1365 SUBGOAL_THEN `i < n:num` ASSUME_TAC THENL
1366 [ASM_MESON_TAC[LTE_TRANS; LT_LE]; ALL_TAC] THEN
1367 UNDISCH_TAC `X a j = q * X a n + X a i` THEN
1368 ASM_CASES_TAC `q = 0` THEN
1369 ASM_SIMP_TAC[ADD_CLAUSES; MULT_CLAUSES; X_INJ] THEN
1371 MP_TAC(SPECL [`a:num`; `j:num`; `n:num`] X_INCREASES_LE) THEN
1372 ASM_REWRITE_TAC[] THEN
1373 MATCH_MP_TAC(TAUT `~a ==> a ==> b`) THEN
1374 MATCH_MP_TAC(ARITH_RULE `1 <= b /\ 1 * x <= qx ==> ~(qx + b <= x)`) THEN
1375 SIMP_TAC[LE_MULT_RCANCEL] THEN
1376 ASM_SIMP_TAC[ARITH_RULE `~(x = 0) ==> 1 <= x`] THEN
1377 ONCE_REWRITE_TAC[GSYM(CONJUNCT1 X_CLAUSES)] THEN
1378 ASM_SIMP_TAC[X_INCREASES_LE; LE_0]; ALL_TAC] THEN
1379 ASM_CASES_TAC `n = 0` THENL
1380 [UNDISCH_TAC `i <= j:num` THEN UNDISCH_TAC `j <= 2 * n` THEN
1381 ASM_SIMP_TAC[LE; MULT_CLAUSES]; ALL_TAC] THEN
1382 ASM_CASES_TAC `i <= n:num` THENL
1383 [MP_TAC(SPECL [`a:num`; `n:num`; `j:num`] X_CONGRUENT_2NJ_NEG) THEN
1384 ASM_REWRITE_TAC[] THEN
1385 DISCH_THEN(X_CHOOSE_THEN `q1:num` MP_TAC) THEN
1386 UNDISCH_TAC `X a j = q * X a n + X a i` THEN
1387 ASM_CASES_TAC `q = 0` THEN
1388 ASM_SIMP_TAC[ADD_CLAUSES; MULT_CLAUSES; X_INJ] THEN DISCH_TAC THEN
1389 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1390 `(a + b + c = d:num) ==> (a + c = d - b)`)) THEN
1391 REWRITE_TAC[GSYM RIGHT_SUB_DISTRIB] THEN
1392 ASM_CASES_TAC `i = n:num` THENL
1393 [ASM_REWRITE_TAC[] THEN
1394 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1395 `(x + n = q * n) ==> (x = q * n - 1 * n)`)) THEN
1396 MATCH_MP_TAC(TAUT `~a ==> a ==> b`) THEN
1397 REWRITE_TAC[GSYM RIGHT_SUB_DISTRIB] THEN
1398 ASM_CASES_TAC `q1 - q - 1 = 0` THENL
1399 [ASM_REWRITE_TAC[MULT_CLAUSES; ARITH_RULE `~(n = 0) <=> 1 <= n`] THEN
1400 ONCE_REWRITE_TAC[GSYM(CONJUNCT1 X_CLAUSES)] THEN
1401 ASM_SIMP_TAC[X_INCREASES_LE; LE_0]; ALL_TAC] THEN
1402 MATCH_MP_TAC(ARITH_RULE
1403 `j < n /\ 1 * n <= a * n ==> ~(j = a * n)`) THEN
1404 ASM_SIMP_TAC[LE_MULT_RCANCEL; ARITH_RULE `~(x = 0) ==> 1 <= x`] THEN
1405 MATCH_MP_TAC X_INCREASES_LT THEN ASM_REWRITE_TAC[] THEN
1406 UNDISCH_TAC `~(j <= n:num)` THEN
1407 UNDISCH_TAC `~(n = 0)` THEN ARITH_TAC; ALL_TAC] THEN
1408 ASM_CASES_TAC `q1 - q = 0` THENL
1409 [ASM_REWRITE_TAC[MULT_CLAUSES; ADD_EQ_0] THEN
1410 MATCH_MP_TAC(TAUT `~c ==> a /\ c ==> b`) THEN
1411 REWRITE_TAC[ARITH_RULE `~(n = 0) <=> 1 <= n`] THEN
1412 ONCE_REWRITE_TAC[GSYM(CONJUNCT1 X_CLAUSES)] THEN
1413 ASM_SIMP_TAC[X_INCREASES_LE; LE_0]; ALL_TAC] THEN
1414 MATCH_MP_TAC(TAUT `(~b ==> a ==> c) ==> a ==> b \/ c`) THEN
1415 DISCH_TAC THEN DISCH_TAC THEN
1416 ASM_CASES_TAC `n = 1` THENL
1417 [UNDISCH_TAC `j <= 2 * n` THEN ASM_REWRITE_TAC[MULT_CLAUSES] THEN
1418 UNDISCH_TAC `~(j <= n:num)` THEN ASM_REWRITE_TAC[] THEN
1419 REWRITE_TAC[IMP_IMP] THEN
1420 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1421 `~(j <= 1) /\ j <= 2 ==> (j = 2)`)) THEN
1422 DISCH_THEN SUBST_ALL_TAC THEN REWRITE_TAC[] THEN
1423 UNDISCH_THEN `n = 1` SUBST_ALL_TAC THEN
1424 SUBGOAL_THEN `i = 0` SUBST_ALL_TAC THENL
1425 [MAP_EVERY UNDISCH_TAC [`i <= 1`; `~(i = 1)`] THEN ARITH_TAC;
1427 UNDISCH_TAC `X a (2 * 1 - 2) + X a 0 = (q1 - q) * X a 1` THEN
1428 REWRITE_TAC[ARITH; X_CLAUSES] THEN DISCH_THEN(ASSUME_TAC o SYM) THEN
1429 MATCH_MP_TAC(ARITH_RULE
1430 `~(a = 0) /\ ~(a = 1) /\ a <= 2 ==> (a = 2)`) THEN
1431 ASM_REWRITE_TAC[] THEN
1432 UNDISCH_THEN `(q1 - q) * a = 2` (SUBST1_TAC o SYM) THEN
1433 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `a = 1 * a`] THEN
1434 REWRITE_TAC[LE_MULT_RCANCEL] THEN
1435 ASM_SIMP_TAC[ARITH_RULE `~(q = 0) ==> 1 <= q`]; ALL_TAC] THEN
1436 UNDISCH_TAC `X a (2 * n - j) + X a i = (q1 - q) * X a n` THEN
1437 MATCH_MP_TAC(TAUT `~b ==> b ==> a`) THEN
1438 MATCH_MP_TAC(ARITH_RULE
1439 `s < x /\ x <= q * x ==> ~(s = q * x:num)`) THEN
1442 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `a = 1 * a`] THEN
1443 REWRITE_TAC[LE_MULT_RCANCEL] THEN
1444 ASM_SIMP_TAC[ARITH_RULE `~(q = 0) ==> 1 <= q`]] THEN
1445 MATCH_MP_TAC LET_TRANS THEN
1446 EXISTS_TAC `2 * X a (n - 1)` THEN CONJ_TAC THENL
1447 [MATCH_MP_TAC(ARITH_RULE `a <= c /\ b <= c ==> a + b <= 2 * c`) THEN
1448 CONJ_TAC THEN MATCH_MP_TAC X_INCREASES_LE THEN ASM_REWRITE_TAC[] THENL
1449 [UNDISCH_TAC `~(n = 0)` THEN UNDISCH_TAC `~(j <= n:num)` THEN ARITH_TAC;
1450 UNDISCH_TAC `~(i = n:num)` THEN UNDISCH_TAC `i <= n:num` THEN
1453 SUBGOAL_THEN `n - 1 = (n - 2) + 1` SUBST1_TAC THENL
1454 [UNDISCH_TAC `~(n = 0)` THEN UNDISCH_TAC `~(n = 1)` THEN ARITH_TAC;
1456 SUBGOAL_THEN `n = (n - 2) + 2`
1457 (fun th -> GEN_REWRITE_TAC (RAND_CONV o ONCE_DEPTH_CONV) [th])
1459 [UNDISCH_TAC `~(n = 0)` THEN UNDISCH_TAC `~(n = 1)` THEN ARITH_TAC;
1461 REWRITE_TAC[X_CLAUSES] THEN
1462 MATCH_MP_TAC(ARITH_RULE `z < x /\ 3 * x <= y ==> 2 * x < y - z`) THEN
1463 ASM_SIMP_TAC[X_INCREASES_LT; ARITH_RULE `n < n + 1`] THEN
1464 REWRITE_TAC[MULT_ASSOC; LE_MULT_RCANCEL] THEN DISJ1_TAC THEN
1465 UNDISCH_TAC `~(a = 1)` THEN UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC;
1467 MP_TAC(SPECL [`a:num`; `n:num`; `j:num`] X_CONGRUENT_2NJ_NEG) THEN
1468 ASM_REWRITE_TAC[] THEN
1469 DISCH_THEN(X_CHOOSE_THEN `q1:num` MP_TAC) THEN
1470 MP_TAC(SPECL [`a:num`; `n:num`; `i:num`] X_CONGRUENT_2NJ_NEG) THEN
1472 [ASM_REWRITE_TAC[] THEN ASM_MESON_TAC[LE_TRANS]; ALL_TAC] THEN
1473 DISCH_THEN(X_CHOOSE_THEN `q2:num` MP_TAC) THEN
1474 ASM_REWRITE_TAC[] THEN
1475 REWRITE_TAC[IMP_IMP] THEN
1476 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1477 `(a = b) /\ (c = d) ==> (a + d = b + c:num)`)) THEN
1478 REWRITE_TAC[ARITH_RULE
1479 `((x + i) + q1 = q2 + y + q3 + i) <=> (x + q1 = y + q2 + q3:num)`] THEN
1480 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1481 `(x + q1 = y + q2) ==> y <= x ==> (x = y + (q2 - q1:num))`)) THEN
1483 [MATCH_MP_TAC X_INCREASES_LE THEN ASM_REWRITE_TAC[] THEN
1484 UNDISCH_TAC `i <= j:num` THEN ARITH_TAC; ALL_TAC] THEN
1485 REWRITE_TAC[GSYM RIGHT_ADD_DISTRIB; GSYM RIGHT_SUB_DISTRIB] THEN
1486 ASM_CASES_TAC `(q2 + q) - q1 = 0` THENL
1487 [ASM_SIMP_TAC[ADD_CLAUSES; MULT_CLAUSES; X_INJ] THEN
1488 MATCH_MP_TAC(TAUT `(a ==> b) ==> (a ==> b \/ c)`) THEN
1489 UNDISCH_TAC `j <= 2 * n` THEN UNDISCH_TAC `i <= j:num` THEN ARITH_TAC;
1491 MATCH_MP_TAC(TAUT `~a ==> a ==> b`) THEN
1492 MATCH_MP_TAC(ARITH_RULE
1493 `1 * xi <= qxn /\ 1 <= xj ==> ~(xi = xj + qxn)`) THEN
1495 [MATCH_MP_TAC LE_MULT2 THEN
1496 ASM_REWRITE_TAC[ARITH_RULE `1 <= a <=> ~(a = 0)`] THEN
1497 MATCH_MP_TAC X_INCREASES_LE THEN ASM_REWRITE_TAC[] THEN
1498 UNDISCH_TAC `~(i <= n:num)` THEN ARITH_TAC; ALL_TAC] THEN
1499 REWRITE_TAC[GSYM(CONJUNCT1 X_CLAUSES)] THEN
1500 MATCH_MP_TAC X_INCREASES_LE THEN ASM_REWRITE_TAC[LE_0]);;
1502 let STEP_DOWN_LEMMA_4_ASYM = prove
1504 ~(a = 0) /\ ~(a = 1) /\
1505 0 < i /\ i <= n /\ j < 4 * n /\
1506 (X a i + q * X a n = X a j)
1507 ==> (j = i) \/ (j = 4 * n - i)`,
1508 REPEAT STRIP_TAC THEN ASM_CASES_TAC `j <= 2 * n` THENL
1509 [MP_TAC(SPECL [`a:num`; `i:num`; `j:num`; `n:num`; `q:num`]
1510 STEP_DOWN_LEMMA) THEN
1512 [ASM_REWRITE_TAC[] THEN
1513 UNDISCH_TAC `X a i + q * X a n = X a j` THEN
1514 SIMP_TAC[ADD_AC; MULT_AC] THEN DISCH_THEN(ASSUME_TAC o SYM) THEN
1515 SUBGOAL_THEN `X a i <= X a j` MP_TAC THENL
1516 [ASM_REWRITE_TAC[ONCE_REWRITE_RULE[ADD_SYM] LE_ADD]; ALL_TAC] THEN
1517 ONCE_REWRITE_TAC[TAUT `a ==> b <=> ~b ==> ~a`] THEN
1518 ASM_SIMP_TAC[X_INCREASES_LT; NOT_LE]; ALL_TAC] THEN
1519 ASM_SIMP_TAC[ARITH_RULE `0 < i ==> ~(i = 0)`]; ALL_TAC] THEN
1520 DISJ_CASES_TAC(SPECL [`i:num`; `4 * n - j`] LE_CASES) THEN
1521 (MP_TAC(SPECL [`a:num`; `n:num`; `2 * n - (4 * n - j)`]
1522 X_CONGRUENT_2NJ_POS) THEN
1523 MP_TAC(SPECL [`a:num`; `n:num`; `4 * n - j`] X_CONGRUENT_2NJ_NEG) THEN
1524 ASM_SIMP_TAC[ARITH_RULE `~(j <= 2 * n) ==> 4 * n - j <= 2 * n`] THEN
1525 ASM_SIMP_TAC[ARITH_RULE
1526 `j < 4 * n /\ ~(j <= 2 * n)
1527 ==> (2 * n + 2 * n - (4 * n - j) = j)`] THEN
1528 DISCH_THEN(X_CHOOSE_THEN `q1:num` ASSUME_TAC) THEN
1529 DISCH_THEN(X_CHOOSE_THEN `q2:num` MP_TAC) THEN
1530 SUBST1_TAC(SYM(ASSUME `X a i + q * X a n = X a j`)) THEN
1532 `X a (2 * n - (4 * n - j)) + X a (4 * n - j) = q1 * X a n` THEN
1533 REWRITE_TAC[IMP_IMP] THEN
1534 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1535 `(a + b = c) /\ (d + a = e) ==> (b + e = c + d:num)`)))
1537 [DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1538 `(x + q1 = q2 + y + q3)
1539 ==> y <= x ==> (x = ((q2 + q3) - q1) + y:num)`));
1540 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1541 `(x + q1 = q2 + y + q3)
1542 ==> x <= y ==> (y = (q1 - (q2 + q3)) + x:num)`))] THEN
1543 REWRITE_TAC[GSYM RIGHT_SUB_DISTRIB; GSYM RIGHT_ADD_DISTRIB] THEN
1544 ASM_SIMP_TAC[X_INCREASES_LE] THEN DISCH_TAC THENL
1545 [MP_TAC(SPECL [`a:num`; `i:num`; `4 * n - j`; `n:num`; `(q1 + q) - q2:num`]
1546 STEP_DOWN_LEMMA) THEN
1548 [ASM_REWRITE_TAC[] THEN UNDISCH_TAC `~(j <= 2 * n)` THEN ARITH_TAC;
1550 ASM_SIMP_TAC[ARITH_RULE `0 < i ==> ~(i = 0)`] THEN
1551 DISCH_TAC THEN DISJ2_TAC THEN UNDISCH_TAC `j < 4 * n` THEN ARITH_TAC;
1552 MP_TAC(SPECL [`a:num`; `4 * n - j`; `i:num`; `n:num`; `q2:num - (q1 + q)`]
1553 STEP_DOWN_LEMMA) THEN
1555 [ASM_REWRITE_TAC[] THEN UNDISCH_TAC `i <= n:num` THEN ARITH_TAC;
1557 ASM_REWRITE_TAC[SUB_EQ_0; GSYM NOT_LT] THEN
1558 DISCH_THEN(SUBST1_TAC o SYM) THEN
1559 DISJ2_TAC THEN UNDISCH_TAC `j < 4 * n` THEN ARITH_TAC]);;
1561 let STEP_DOWN_LEMMA_4 = prove
1563 ~(a = 0) /\ ~(a = 1) /\
1564 0 < i /\ i <= n /\ j < 4 * n /\
1565 (X a i + q1 * X a n = X a j + q2 * X a n)
1566 ==> (j = i) \/ (j = 4 * n - i)`,
1567 REPEAT STRIP_TAC THEN ASM_CASES_TAC `j < i:num` THENL
1568 [UNDISCH_TAC `X a i + q1 * X a n = X a j + q2 * X a n` THEN
1569 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1570 `(x + q1 = y + q2) ==> y < x ==> (x = y + (q2 - q1:num))`)) THEN
1571 ASM_SIMP_TAC[X_INCREASES_LT; GSYM RIGHT_SUB_DISTRIB] THEN
1572 ASM_CASES_TAC `q2 - q1 = 0` THENL
1573 [ASM_SIMP_TAC[MULT_CLAUSES; ADD_CLAUSES; X_INJ]; ALL_TAC] THEN
1574 MATCH_MP_TAC(TAUT `~a ==> a ==> b`) THEN
1575 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1576 `(i = j + q * n) ==> 1 <= j /\ 1 * n <= q * n ==> ~(i <= n)`)) THEN
1577 ASM_SIMP_TAC[X_INCREASES_LE] THEN
1578 ASM_SIMP_TAC[LE_MULT_RCANCEL;
1579 ARITH_RULE `~(q2 - q1 = 0) ==> 1 <= q2 - q1`] THEN
1580 ONCE_REWRITE_TAC[GSYM(CONJUNCT1 X_CLAUSES)] THEN
1581 ASM_SIMP_TAC[X_INCREASES_LE; LE_0]; ALL_TAC] THEN
1582 MP_TAC(SPECL [`a:num`; `i:num`; `j:num`; `n:num`; `q1 - q2:num`]
1583 STEP_DOWN_LEMMA_4_ASYM) THEN
1584 DISCH_THEN MATCH_MP_TAC THEN ASM_REWRITE_TAC[] THEN
1585 REWRITE_TAC[RIGHT_SUB_DISTRIB] THEN
1586 MATCH_MP_TAC(ARITH_RULE
1587 `(i + q1 = j + q2) /\ ~(j < i) ==> (i + q1 - q2 = j:num)`) THEN
1588 RULE_ASSUM_TAC(REWRITE_RULE[NOT_LT]) THEN
1589 ASM_SIMP_TAC[NOT_LT; X_INCREASES_LE]);;
1591 let STEP_DOWN_LEMMA_STRONG_ASYM = prove
1593 ~(a = 0) /\ ~(a = 1) /\
1595 (X a i + c * X a n = X a j)
1596 ==> (?q. j = i + 4 * n * q) \/
1597 (?q. j + i = 4 * n * q)`,
1598 REPEAT STRIP_TAC THEN
1599 MP_TAC(SPECL [`j:num`; `4 * n`] DIVISION) THEN
1600 ABBREV_TAC `q = j DIV (4 * n)` THEN ABBREV_TAC `k = j MOD (4 * n)` THEN
1602 [UNDISCH_TAC `0 < i` THEN UNDISCH_TAC `i <= n:num` THEN ARITH_TAC;
1604 DISCH_THEN(STRIP_ASSUME_TAC o GSYM) THEN
1605 MP_TAC(SPECL [`a:num`; `q:num`; `n:num`; `k:num`] X_CONGRUENT_4MNJ_POS) THEN
1606 ASM_REWRITE_TAC[] THEN
1607 DISCH_THEN(X_CHOOSE_THEN `q1:num` MP_TAC) THEN
1608 SUBST1_TAC(ARITH_RULE `4 * q * n + k = q * 4 * n + k`) THEN
1609 ASM_REWRITE_TAC[] THEN DISCH_THEN SUBST_ALL_TAC THEN
1610 ASM_CASES_TAC `k < i:num` THENL
1611 [UNDISCH_TAC `X a i + c * X a n = q1 * X a n + X a k` THEN
1612 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1613 `(a + q1 = q2 + b) ==> b < a ==> (a = (q2 - q1) + b:num)`)) THEN
1614 ASM_SIMP_TAC[X_INCREASES_LT] THEN REWRITE_TAC[GSYM RIGHT_SUB_DISTRIB] THEN
1615 ASM_CASES_TAC `q1 - c = 0` THENL
1616 [ASM_SIMP_TAC[MULT_CLAUSES; ADD_CLAUSES; X_INJ] THEN
1617 DISCH_TAC THEN DISJ1_TAC THEN EXISTS_TAC `q:num` THEN
1618 FIRST_ASSUM(fun th -> GEN_REWRITE_TAC LAND_CONV [SYM th]) THEN
1619 REWRITE_TAC[ADD_AC; MULT_AC];
1620 MATCH_MP_TAC(TAUT `~a ==> a ==> b`) THEN
1621 MATCH_MP_TAC(ARITH_RULE
1622 `a <= b /\ 1 <= c ==> ~(a = b + c)`) THEN
1624 [GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `n = 1 * n`] THEN
1625 MATCH_MP_TAC LE_MULT2 THEN
1626 ASM_REWRITE_TAC[ARITH_RULE `1 <= n <=> ~(n = 0)`] THEN
1627 ASM_SIMP_TAC[X_INCREASES_LE; LT_IMP_LE];
1628 SUBST1_TAC(SYM(SPEC `a:num` (CONJUNCT1 X_CLAUSES))) THEN
1629 ASM_SIMP_TAC[X_INCREASES_LE; LE_0]]];
1630 MP_TAC(SPECL [`a:num`; `i:num`; `k:num`; `n:num`; `c - q1:num`]
1631 STEP_DOWN_LEMMA_4_ASYM) THEN
1633 [ASM_REWRITE_TAC[] THEN
1634 UNDISCH_TAC `X a i + c * X a n = q1 * X a n + X a k` THEN
1635 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1636 `(a + q1 = q2 + b) ==> ~(b < a) ==> (a + (q1 - q2)= b:num)`)) THEN
1637 REWRITE_TAC[GSYM RIGHT_SUB_DISTRIB] THEN
1638 DISCH_THEN MATCH_MP_TAC THEN REWRITE_TAC[NOT_LT] THEN
1639 MATCH_MP_TAC X_INCREASES_LE THEN ASM_REWRITE_TAC[GSYM NOT_LT];
1641 DISCH_THEN DISJ_CASES_TAC THENL
1642 [DISJ1_TAC THEN EXISTS_TAC `q:num` THEN
1643 UNDISCH_THEN `q * 4 * n + k = j` (SUBST1_TAC o SYM) THEN
1644 ASM_REWRITE_TAC[MULT_AC; ADD_AC];
1645 DISJ2_TAC THEN EXISTS_TAC `q + 1` THEN
1646 UNDISCH_THEN `q * 4 * n + k = j` (SUBST1_TAC o SYM) THEN
1647 REWRITE_TAC[GSYM ADD_ASSOC; LEFT_ADD_DISTRIB; MULT_CLAUSES] THEN
1648 ASM_REWRITE_TAC[] THEN
1649 MATCH_MP_TAC(ARITH_RULE
1650 `(a' = a) /\ i <= b ==> (a + (b - i) + i = a' + b:num)`) THEN
1651 REWRITE_TAC[MULT_AC] THEN
1652 UNDISCH_TAC `i <= n:num` THEN ARITH_TAC]]);;
1654 let STEP_DOWN_LEMMA_STRONG = prove
1656 ~(a = 0) /\ ~(a = 1) /\ 0 < i /\ i <= n /\
1657 (X a i + c1 * X a n = X a j + c2 * X a n)
1658 ==> (?q. j = i + 4 * n * q) \/
1659 (?q. j + i = 4 * n * q)`,
1660 REPEAT STRIP_TAC THEN ASM_CASES_TAC `j < i:num` THENL
1661 [UNDISCH_TAC `X a i + c1 * X a n = X a j + c2 * X a n` THEN
1662 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1663 `(x + q1 = y + q2) ==> y < x ==> (x = y + (q2 - q1:num))`)) THEN
1664 ASM_SIMP_TAC[X_INCREASES_LT; GSYM RIGHT_SUB_DISTRIB] THEN
1665 ASM_CASES_TAC `c2 - c1 = 0` THENL
1666 [ASM_SIMP_TAC[MULT_CLAUSES; ADD_CLAUSES; X_INJ] THEN
1667 DISCH_THEN(K ALL_TAC) THEN DISJ1_TAC THEN
1668 EXISTS_TAC `0` THEN REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES];
1670 MATCH_MP_TAC(TAUT `~a ==> a ==> b`) THEN
1671 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1672 `(i = j + q * n) ==> 1 <= j /\ 1 * n <= q * n ==> ~(i <= n)`)) THEN
1673 ASM_SIMP_TAC[X_INCREASES_LE] THEN
1674 ASM_SIMP_TAC[LE_MULT_RCANCEL;
1675 ARITH_RULE `~(q2 - q1 = 0) ==> 1 <= q2 - q1`] THEN
1676 ONCE_REWRITE_TAC[GSYM(CONJUNCT1 X_CLAUSES)] THEN
1677 ASM_SIMP_TAC[X_INCREASES_LE; LE_0]; ALL_TAC] THEN
1678 MP_TAC(SPECL [`a:num`; `i:num`; `j:num`; `n:num`; `c1 - c2:num`]
1679 STEP_DOWN_LEMMA_STRONG_ASYM) THEN
1680 DISCH_THEN MATCH_MP_TAC THEN ASM_REWRITE_TAC[] THEN
1681 REWRITE_TAC[RIGHT_SUB_DISTRIB] THEN
1682 MATCH_MP_TAC(ARITH_RULE
1683 `(i + q1 = j + q2) /\ ~(j < i) ==> (i + q1 - q2 = j:num)`) THEN
1684 RULE_ASSUM_TAC(REWRITE_RULE[NOT_LT]) THEN
1685 ASM_SIMP_TAC[NOT_LT; X_INCREASES_LE]);;
1687 (* ------------------------------------------------------------------------- *)
1688 (* Diophantine nature of the Y sequence. *)
1689 (* ------------------------------------------------------------------------- *)
1692 (`~(a = 0) /\ ~(a = 1) /\ ~(y = 0)
1693 ==> ((y = Y a k) <=>
1694 ?x u v r b p q s t c d.
1696 (x EXP 2 = (a EXP 2 - 1) * y EXP 2 + 1) /\
1697 (u EXP 2 = (a EXP 2 - 1) * v EXP 2 + 1) /\
1698 (s EXP 2 = (b EXP 2 - 1) * t EXP 2 + 1) /\
1699 (v = r * y EXP 2) /\
1700 (b = 1 + 4 * p * y) /\
1703 (t = k + 4 * d * y) /\
1705 REPEAT STRIP_TAC THEN EQ_TAC THENL
1707 DISCH_THEN(STRIP_ASSUME_TAC o GSYM) THEN
1708 MP_TAC(SPECL [`a:num`; `x:num`; `y:num`] SOLUTIONS_ARE_XY) THEN
1709 ASM_REWRITE_TAC[] THEN
1710 DISCH_THEN(X_CHOOSE_THEN `i:num` (STRIP_ASSUME_TAC o GSYM)) THEN
1711 MP_TAC(SPECL [`a:num`; `u:num`; `v:num`] SOLUTIONS_ARE_XY) THEN
1712 ASM_REWRITE_TAC[] THEN
1713 DISCH_THEN(X_CHOOSE_THEN `n:num` (STRIP_ASSUME_TAC o GSYM)) THEN
1714 SUBGOAL_THEN `~(b = 0)` ASSUME_TAC THENL
1715 [SUBST1_TAC(SYM(ASSUME `1 + 4 * p * y = b`)) THEN
1716 REWRITE_TAC[ADD_EQ_0; ARITH_EQ]; ALL_TAC] THEN
1717 MP_TAC(SPECL [`b:num`; `s:num`; `t:num`] SOLUTIONS_ARE_XY) THEN
1718 ASM_REWRITE_TAC[] THEN
1719 DISCH_THEN(X_CHOOSE_THEN `j:num` (STRIP_ASSUME_TAC o GSYM)) THEN
1720 SUBGOAL_THEN `y <= v:num` ASSUME_TAC THENL
1721 [SUBST1_TAC(SYM(ASSUME `r * y EXP 2 = v`)) THEN REWRITE_TAC[EXP_2] THEN
1722 GEN_REWRITE_TAC LAND_CONV [ARITH_RULE `y = 1 * y`] THEN
1723 REWRITE_TAC[MULT_ASSOC; LE_MULT_RCANCEL] THEN DISJ1_TAC THEN
1724 ASM_REWRITE_TAC[ARITH_RULE `1 <= a <=> ~(a = 0)`; MULT_EQ_0] THEN
1725 ASM_SIMP_TAC[ARITH_RULE `0 < r ==> ~(r = 0)`]; ALL_TAC] THEN
1726 SUBGOAL_THEN `i <= n:num` ASSUME_TAC THENL
1727 [UNDISCH_TAC `y <= v:num` THEN
1728 SUBST1_TAC(SYM(ASSUME `Y a i = y`)) THEN
1729 SUBST1_TAC(SYM(ASSUME `Y a n = v`)) THEN
1730 ONCE_REWRITE_TAC[TAUT `a ==> b <=> ~b ==> ~a`] THEN
1731 ASM_SIMP_TAC[NOT_LE; Y_INCREASES_LT]; ALL_TAC] THEN
1732 MP_TAC(SPECL [`a:num`; `q:num`; `u:num`; `j:num`] X_CONGRUENT) THEN
1733 REWRITE_TAC[ASSUME `~(a = 0)`; ASSUME `a + q * u = b:num`] THEN
1734 DISCH_THEN(X_CHOOSE_THEN `q1:num` MP_TAC) THEN
1735 SUBST1_TAC(ASSUME `X b j = s`) THEN
1736 SUBST1_TAC(SYM(ASSUME `x + c * u = s:num`)) THEN
1737 SUBST1_TAC(SYM(ASSUME `X a i = x`)) THEN
1738 SUBST1_TAC(SYM(ASSUME `X a n = u`)) THEN DISCH_TAC THEN
1739 SUBGOAL_THEN `~(i = 0)` ASSUME_TAC THENL
1740 [UNDISCH_TAC `~(y = 0)` THEN
1741 REWRITE_TAC[TAUT `~a ==> ~b <=> b ==> a`] THEN
1742 EXPAND_TAC "y" THEN SIMP_TAC[Y_CLAUSES; ASSUME `~(a = 0)`];
1744 SUBGOAL_THEN `(?q. j = i + 4 * n * q) \/ (?q. j + i = 4 * n * q)`
1746 [MATCH_MP_TAC STEP_DOWN_LEMMA_STRONG THEN
1747 MAP_EVERY EXISTS_TAC [`a:num`; `c:num`; `q1:num`] THEN
1748 ASM_SIMP_TAC[ARITH_RULE `~(i = 0) ==> 0 < i`]; ALL_TAC] THEN
1749 MP_TAC(SPECL [`a:num`; `i:num`; `n:num`] Y2_DIVIDES) THEN
1750 ASM_REWRITE_TAC[] THEN
1751 DISCH_THEN(MP_TAC o fst o EQ_IMP_RULE) THEN
1752 REWRITE_TAC[divides; LEFT_IMP_EXISTS_THM] THEN
1753 DISCH_THEN(MP_TAC o SPEC `r:num`) THEN
1754 SUBST1_TAC(SYM(ASSUME `r * y EXP 2 = v`)) THEN
1755 REWRITE_TAC[EQT_INTRO(SPEC_ALL MULT_SYM)] THEN
1756 DISCH_THEN(X_CHOOSE_THEN `d1:num` (ASSUME_TAC o SYM)) THEN
1757 UNDISCH_TAC `(?q. j = i + 4 * n * q) \/ (?q. j + i = 4 * n * q:num)` THEN
1758 UNDISCH_THEN `(i * y) * d1 = n:num` (SUBST1_TAC o SYM) THEN DISCH_TAC THEN
1759 SUBGOAL_THEN `(?q. j = i + q * 4 * Y a i) \/
1760 (?q. j + i = q * 4 * Y a i)`
1762 [FIRST_ASSUM(UNDISCH_TAC o check is_disj o concl) THEN
1763 REWRITE_TAC[OR_EXISTS_THM] THEN
1764 DISCH_THEN(X_CHOOSE_THEN `d2:num`
1765 (fun th -> EXISTS_TAC `i * d1 * d2:num` THEN MP_TAC th)) THEN
1766 SUBST1_TAC(ASSUME `Y a i = y`) THEN REWRITE_TAC[MULT_AC];
1767 FIRST_X_ASSUM(K ALL_TAC o check (is_disj o concl)) THEN
1769 MP_TAC(SPECL [`b:num`; `j:num`] Y_N_MODA1) THEN
1770 ASM_REWRITE_TAC[] THEN
1771 DISCH_THEN(X_CHOOSE_THEN `d3:num` MP_TAC) THEN
1772 SUBST1_TAC(SYM(ASSUME `1 + 4 * p * y = b`)) THEN REWRITE_TAC[ADD_SUB2] THEN
1773 SUBST1_TAC(SYM(ASSUME `k + 4 * d * y = t`)) THEN DISCH_TAC THEN
1774 SUBST1_TAC(SYM(ASSUME `Y a i = y`)) THEN AP_TERM_TAC THEN
1775 SUBGOAL_THEN `(?q1 q2. k + q1 * 4 * Y a i = i + q2 * 4 * Y a i) \/
1776 (?q. i + k = q * 4 * Y a i)`
1778 [UNDISCH_TAC `(?q. j = i + q * 4 * Y a i) \/
1779 (?q. j + i = q * 4 * Y a i)` THEN
1781 `(a1 ==> b1) /\ (a2 ==> b2) ==> a1 \/ a2 ==> b1 \/ b2`) THEN
1782 CONJ_TAC THEN DISCH_TAC THEN
1783 UNDISCH_TAC `k + 4 * d * y = d3 * 4 * p * y + j` THENL
1784 [FIRST_X_ASSUM(X_CHOOSE_THEN `d4:num` SUBST1_TAC) THEN
1785 DISCH_THEN(fun th ->
1786 EXISTS_TAC `d:num` THEN
1787 EXISTS_TAC `d3 * p + d4:num` THEN MP_TAC th) THEN
1788 SUBST1_TAC(SYM(ASSUME `Y a i = y`)) THEN
1789 REWRITE_TAC[RIGHT_ADD_DISTRIB] THEN
1790 REWRITE_TAC[MULT_AC] THEN REWRITE_TAC[ADD_AC];
1791 DISCH_THEN(MP_TAC o C AP_THM `i:num` o
1792 AP_TERM `(+):num->num->num`) THEN
1793 REWRITE_TAC[GSYM ADD_ASSOC] THEN
1794 FIRST_X_ASSUM(X_CHOOSE_THEN `d4:num` SUBST1_TAC) THEN
1795 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1796 `(k + q1 + i = q2) ==> (i + k = q2 - q1:num)`)) THEN
1797 DISCH_THEN SUBST1_TAC THEN
1798 SUBST1_TAC(SYM(ASSUME `Y a i = y`)) THEN
1799 REWRITE_TAC[GSYM RIGHT_ADD_DISTRIB; MULT_ASSOC;
1800 GSYM RIGHT_SUB_DISTRIB] THEN
1801 REWRITE_TAC[GSYM MULT_ASSOC] THEN
1802 REWRITE_TAC[ARITH_RULE
1803 `(d3 * 4 * p + d4 * 4) - 4 * x =
1804 ((d3 * p + d4) - x) * 4`] THEN REWRITE_TAC[GSYM MULT_ASSOC] THEN
1805 EXISTS_TAC `(d3 * p + d4) - d:num` THEN REFL_TAC];
1807 SUBGOAL_THEN `k <= Y a i` ASSUME_TAC THENL
1808 [ASM_REWRITE_TAC[]; ALL_TAC] THEN
1809 SUBGOAL_THEN `i <= Y a i` ASSUME_TAC THENL
1810 [MP_TAC(SPECL [`a:num`; `i:num`] Y_N_MODA1) THEN
1811 ASM_SIMP_TAC[LEFT_IMP_EXISTS_THM] THEN
1812 REWRITE_TAC[ONCE_REWRITE_RULE[ADD_SYM] LE_ADD]; ALL_TAC] THEN
1813 DISCH_THEN(DISJ_CASES_THEN MP_TAC) THENL
1814 [DISCH_THEN(X_CHOOSE_THEN `q4:num` (X_CHOOSE_THEN `q5:num` MP_TAC)) THEN
1815 REPEAT_TCL DISJ_CASES_THEN ASSUME_TAC
1816 (SPECL [`q4:num`; `q5:num`] LT_CASES)
1818 [DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1819 `(k + q4 = i + q5) ==> q4 < q5:num ==> (k = i + (q5 - q4))`)) THEN
1820 REWRITE_TAC[MULT_ASSOC; LT_MULT_RCANCEL; GSYM RIGHT_SUB_DISTRIB] THEN
1821 ASM_REWRITE_TAC[MULT_EQ_0; ARITH_EQ] THEN
1822 UNDISCH_TAC `k <= y:num` THEN
1823 MATCH_MP_TAC(TAUT `(a ==> ~b) ==> b ==> a ==> c`) THEN
1824 DISCH_THEN SUBST1_TAC THEN
1825 MATCH_MP_TAC(ARITH_RULE `1 * y < k * y ==> ~(i + k * y <= y)`) THEN
1826 ASM_REWRITE_TAC[LT_MULT_RCANCEL] THEN
1827 UNDISCH_TAC `q4 < q5:num` THEN ARITH_TAC;
1828 DISCH_THEN(MP_TAC o MATCH_MP (ARITH_RULE
1829 `(k + q4 = i + q5) ==> q5 < q4:num ==> (i = k + (q4 - q5))`)) THEN
1830 REWRITE_TAC[MULT_ASSOC; LT_MULT_RCANCEL; GSYM RIGHT_SUB_DISTRIB] THEN
1831 ASM_REWRITE_TAC[MULT_EQ_0; ARITH_EQ] THEN
1832 UNDISCH_TAC `i <= Y a i` THEN
1833 MATCH_MP_TAC(TAUT `(a ==> ~b) ==> b ==> a ==> c`) THEN
1834 ASM_REWRITE_TAC[] THEN
1835 DISCH_THEN SUBST1_TAC THEN
1836 MATCH_MP_TAC(ARITH_RULE `1 * y < k * y ==> ~(i + k * y <= y)`) THEN
1837 ASM_REWRITE_TAC[LT_MULT_RCANCEL] THEN
1838 UNDISCH_TAC `q5 < q4:num` THEN ARITH_TAC;
1839 ASM_SIMP_TAC[EQ_ADD_RCANCEL]];
1840 DISCH_THEN(X_CHOOSE_THEN `q6:num` MP_TAC) THEN
1841 ASM_CASES_TAC `q6 = 0` THEN ASM_REWRITE_TAC[MULT_CLAUSES; ADD_EQ_0] THEN
1842 UNDISCH_TAC `k <= Y a i` THEN UNDISCH_TAC `i <= Y a i` THEN
1843 SUBST1_TAC(ASSUME `Y a i = y`) THEN
1844 MATCH_MP_TAC(ARITH_RULE
1845 `2 * y < ay ==> i <= y ==> k <= y ==> (i + k = ay) ==> (i = k)`) THEN
1846 REWRITE_TAC[MULT_ASSOC; LT_MULT_RCANCEL] THEN ASM_REWRITE_TAC[] THEN
1847 UNDISCH_TAC `~(q6 = 0)` THEN ARITH_TAC]] THEN
1848 DISCH_THEN(ASSUME_TAC o SYM) THEN ABBREV_TAC `x = X a k` THEN
1849 SUBGOAL_THEN `x EXP 2 = (a EXP 2 - 1) * y EXP 2 + 1` (ASSUME_TAC o SYM) THENL
1850 [MAP_EVERY EXPAND_TAC ["x"; "y"] THEN
1851 SIMP_TAC[XY_ARE_SOLUTIONS; ASSUME `~(a = 0)`]; ALL_TAC] THEN
1852 EXISTS_TAC `x:num` THEN ASM_REWRITE_TAC[] THEN
1853 ABBREV_TAC `m = 2 * k * Y a k` THEN
1854 ABBREV_TAC `u = X a m` THEN ABBREV_TAC `v = Y a m` THEN
1855 SUBGOAL_THEN `u EXP 2 = (a EXP 2 - 1) * v EXP 2 + 1` (ASSUME_TAC o SYM) THENL
1856 [MAP_EVERY EXPAND_TAC ["u"; "v"] THEN
1857 SIMP_TAC[XY_ARE_SOLUTIONS; ASSUME `~(a = 0)`]; ALL_TAC] THEN
1858 EXISTS_TAC `u:num` THEN EXISTS_TAC `v:num` THEN ASM_REWRITE_TAC[] THEN
1859 SUBGOAL_THEN `(y EXP 2) divides v` MP_TAC THENL
1860 [SUBST1_TAC(SYM(ASSUME `Y a m = v`)) THEN
1861 SUBST1_TAC(SYM(ASSUME `Y a k = y`)) THEN
1862 SIMP_TAC[Y2_DIVIDES; ASSUME `~(a = 0)`] THEN
1863 SUBST1_TAC(SYM(ASSUME `2 * k * Y a k = m`)) THEN
1864 REWRITE_TAC[divides] THEN EXISTS_TAC `2` THEN
1865 REWRITE_TAC[MULT_AC]; ALL_TAC] THEN
1866 REWRITE_TAC[divides] THEN
1867 DISCH_THEN(X_CHOOSE_THEN `r:num` (ASSUME_TAC o SYM)) THEN
1868 EXISTS_TAC `r:num` THEN ASM_REWRITE_TAC[] THEN
1869 ASM_CASES_TAC `r = 0` THENL
1870 [UNDISCH_TAC `y EXP 2 * r = v` THEN ASM_REWRITE_TAC[MULT_CLAUSES] THEN
1871 DISCH_THEN(ASSUME_TAC o SYM) THEN REWRITE_TAC[LT_REFL] THEN
1872 UNDISCH_TAC `Y a m = v` THEN ASM_REWRITE_TAC[] THEN DISCH_TAC THEN
1873 SUBGOAL_THEN `m = 0` ASSUME_TAC THENL
1874 [UNDISCH_TAC `Y a m = 0` THEN
1875 ONCE_REWRITE_TAC[GSYM(CONJUNCT1 Y_CLAUSES)] THEN
1876 SIMP_TAC[Y_INJ; ASSUME `~(a = 0)`] THEN
1877 REWRITE_TAC[Y_CLAUSES]; ALL_TAC] THEN
1878 SUBGOAL_THEN `k = 0` ASSUME_TAC THENL
1879 [UNDISCH_TAC `2 * k * Y a k = m` THEN
1880 REWRITE_TAC[ASSUME `m = 0`; MULT_EQ_0; ARITH_EQ] THEN
1881 ONCE_REWRITE_TAC[GSYM(CONJUNCT1 Y_CLAUSES)] THEN
1882 SIMP_TAC[Y_INJ; ASSUME `~(a = 0)`] THEN
1883 REWRITE_TAC[Y_CLAUSES; EQ_SYM]; ALL_TAC] THEN
1884 UNDISCH_TAC `Y a k = y` THEN ASM_REWRITE_TAC[Y_CLAUSES];
1886 ASM_SIMP_TAC[ARITH_RULE `~(r = 0) ==> 0 < r`] THEN
1887 SUBGOAL_THEN `ODD(u)` ASSUME_TAC THENL
1888 [UNDISCH_TAC `(a EXP 2 - 1) * v EXP 2 + 1 = u EXP 2` THEN
1889 DISCH_THEN(MP_TAC o AP_TERM `EVEN`) THEN
1890 REWRITE_TAC[EXP_2; EVEN_ADD; EVEN_MULT; ARITH_EVEN] THEN
1891 SUBGOAL_THEN `EVEN v` (fun th -> REWRITE_TAC[GSYM NOT_EVEN; th]) THEN
1892 SUBST1_TAC(SYM(ASSUME `Y a m = v`)) THEN
1893 MP_TAC(SPECL [`a:num`; `m:num`] Y_N_MOD2) THEN
1894 SIMP_TAC[ASSUME `~(a = 0)`; LEFT_IMP_EXISTS_THM] THEN
1895 SUBST1_TAC(SYM(ASSUME `2 * k * Y a k = m`)) THEN
1896 REWRITE_TAC[EVEN_ADD; EVEN_MULT; ARITH_EVEN]; ALL_TAC] THEN
1897 SUBGOAL_THEN `?b0 q6 q7. (b0 = 1 + q6 * 4 * y) /\ (b0 = a + q7 * u)`
1899 [MATCH_MP_TAC CHINESE_REMAINDER THEN
1900 UNDISCH_TAC `ODD u` THEN
1901 ASM_CASES_TAC `u = 0` THEN ASM_REWRITE_TAC[ARITH_ODD] THEN
1902 DISCH_TAC THEN ASM_REWRITE_TAC[MULT_EQ_0; ARITH_EQ] THEN
1903 ONCE_REWRITE_TAC[COPRIME_SYM] THEN MATCH_MP_TAC COPRIME_MUL THEN
1905 [SUBST1_TAC(SYM(NUM_REDUCE_CONV `2 * 2`)) THEN
1906 MATCH_MP_TAC COPRIME_MUL THEN REWRITE_TAC[] THEN
1907 MP_TAC(SPECL [`u:num`; `2`] PRIME_COPRIME) THEN REWRITE_TAC[PRIME_2] THEN
1908 MATCH_MP_TAC(TAUT `~b /\ (a ==> d) /\ (c ==> d)
1909 ==> a \/ b \/ c ==> d`) THEN
1910 REPEAT CONJ_TAC THENL
1911 [UNDISCH_TAC `ODD u` THEN
1912 ONCE_REWRITE_TAC[TAUT `a ==> b <=> ~b ==> ~a`] THEN
1913 SIMP_TAC[divides; LEFT_IMP_EXISTS_THM; ODD_MULT; ARITH_ODD];
1914 ONCE_REWRITE_TAC[COPRIME_SYM] THEN SIMP_TAC[COPRIME_1];
1915 REWRITE_TAC[COPRIME_SYM]];
1916 MP_TAC(SPECL [`a:num`; `m:num`] XY_COPRIME) THEN ASM_REWRITE_TAC[] THEN
1917 SUBST1_TAC(SYM(ASSUME `y EXP 2 * r = v`)) THEN
1918 REWRITE_TAC[coprime; EXP_2] THEN
1919 MESON_TAC[DIVIDES_RMUL; DIVIDES_LMUL]]; ALL_TAC] THEN
1920 DISCH_THEN(X_CHOOSE_THEN `b:num` (X_CHOOSE_THEN `p:num`
1921 (X_CHOOSE_THEN `q:num` (STRIP_ASSUME_TAC o GSYM)))) THEN
1922 MAP_EVERY EXISTS_TAC [`b:num`; `p:num`; `q:num`] THEN
1923 ONCE_REWRITE_TAC[ARITH_RULE `1 + 4 * p * y = 1 + p * 4 * y`] THEN
1924 ASM_REWRITE_TAC[] THEN
1925 ABBREV_TAC `s = X b k` THEN ABBREV_TAC `t = Y b k` THEN
1926 EXISTS_TAC `s:num` THEN EXISTS_TAC `t:num` THEN
1927 SUBST1_TAC(ARITH_RULE `r * y EXP 2 = y EXP 2 * r`) THEN
1928 ASM_REWRITE_TAC[] THEN
1929 SUBST1_TAC(SYM(ASSUME `X b k = s`)) THEN
1930 SUBST1_TAC(SYM(ASSUME `Y b k = t`)) THEN
1931 SUBGOAL_THEN `~(b = 0)` ASSUME_TAC THENL
1932 [UNDISCH_THEN `1 + p * 4 * y = b` (SUBST1_TAC o SYM) THEN
1933 ONCE_REWRITE_TAC[TAUT `~b ==> a ==> b ==> ~a`] THEN
1934 REWRITE_TAC[ADD_EQ_0; ARITH_EQ]; ALL_TAC] THEN
1935 SIMP_TAC[XY_ARE_SOLUTIONS; ASSUME `~(b = 0)`] THEN
1936 MP_TAC(SPECL [`a:num`; `q:num`; `u:num`; `k:num`] X_CONGRUENT) THEN
1937 ASM_REWRITE_TAC[] THEN
1938 DISCH_THEN(X_CHOOSE_THEN `c:num` (ASSUME_TAC o SYM)) THEN
1939 EXISTS_TAC `c:num` THEN ASM_REWRITE_TAC[] THEN
1940 MP_TAC(SPECL [`b:num`; `k:num`] Y_N_MODA1) THEN
1941 SUBST1_TAC(SYM(ASSUME `1 + p * 4 * y = b`)) THEN
1942 REWRITE_TAC[ADD_EQ_0; ADD_SUB2; ARITH_EQ] THEN ASM_REWRITE_TAC[] THEN
1943 DISCH_THEN(X_CHOOSE_THEN `q8:num` SUBST1_TAC) THEN
1944 EXISTS_TAC `q8 * p:num` THEN REWRITE_TAC[MULT_AC; ADD_AC] THEN
1945 MP_TAC(SPECL [`a:num`; `k:num`] Y_N_MODA1) THEN
1946 ASM_SIMP_TAC[LEFT_IMP_EXISTS_THM] THEN
1947 REWRITE_TAC[ONCE_REWRITE_RULE[ADD_SYM] LE_ADD]);;
1949 (* ------------------------------------------------------------------------- *)
1950 (* A ratio approaches a^n for large enough k. *)
1951 (* ------------------------------------------------------------------------- *)
1953 let BINOMIALISH_LEMMA = prove
1954 (`!m n. m EXP n * (m - n) <= m * (m - 1) EXP n`,
1955 GEN_TAC THEN INDUCT_TAC THEN
1956 REWRITE_TAC[EXP; SUB_0; MULT_CLAUSES; LE_REFL] THEN
1957 MATCH_MP_TAC LE_TRANS THEN
1958 EXISTS_TAC `(m - 1) * m EXP n * (m - n)` THEN CONJ_TAC THENL
1959 [REWRITE_TAC[GSYM MULT_ASSOC] THEN
1960 ONCE_REWRITE_TAC[AC MULT_AC `a * b * c = b * a * c:num`] THEN
1961 REWRITE_TAC[LE_MULT_LCANCEL] THEN DISJ2_TAC THEN
1962 REWRITE_TAC[LEFT_SUB_DISTRIB; RIGHT_SUB_DISTRIB; MULT_CLAUSES] THEN
1963 ONCE_REWRITE_TAC[ARITH_RULE `a - (b + c) = a - c - b:num`] THEN
1964 MATCH_MP_TAC(ARITH_RULE `c <= b ==> a - b <= a - c:num`) THEN ARITH_TAC;
1965 GEN_REWRITE_TAC RAND_CONV
1966 [AC MULT_AC `m * (m - 1) * n = (m - 1) * m * n`] THEN
1967 ASM_REWRITE_TAC[LE_MULT_LCANCEL]]);;
1969 let XY_EXP_LEMMA = prove
1973 ==> abs(&(Y (a * k) (n + 1)) / &(Y k (n + 1)) - &a pow n) < &1 / &2`,
1974 REPEAT STRIP_TAC THEN
1975 SUBGOAL_THEN `~(k = 0)` ASSUME_TAC THENL
1976 [FIRST_ASSUM(ACCEPT_TAC o MATCH_MP (ARITH_RULE
1977 `a < k ==> ~(k = 0)`)); ALL_TAC] THEN
1978 SUBGOAL_THEN `0 < Y k (n + 1)` ASSUME_TAC THENL
1979 [SUBST1_TAC(SYM(SPEC `k:num` (CONJUNCT1 Y_CLAUSES))) THEN
1980 ASM_SIMP_TAC[Y_INCREASES_LT; ARITH_RULE `0 < n + 1`];
1982 MATCH_MP_TAC REAL_LT_LCANCEL_IMP THEN
1983 EXISTS_TAC `abs(&(Y k (n + 1)))` THEN
1984 REWRITE_TAC[GSYM REAL_ABS_MUL; REAL_SUB_LDISTRIB] THEN
1985 ASM_SIMP_TAC[REAL_ABS_NUM; REAL_LT_IMP_NZ;
1986 REAL_OF_NUM_LT; REAL_DIV_LMUL] THEN
1987 REWRITE_TAC[real_div; REAL_MUL_LID; REAL_MUL_ASSOC] THEN
1988 SIMP_TAC[GSYM real_div; REAL_OF_NUM_LT; ARITH; REAL_LT_RDIV_EQ] THEN
1989 MATCH_MP_TAC(REAL_ARITH
1991 lx <= x /\ x <= ux /\ ly <= y /\ y <= uy /\
1992 &2 * uy < &2 * lx + d /\ &2 * ux < &2 * ly + d
1993 ==> abs(x - y) * &2 < d`) THEN
1994 MAP_EVERY EXISTS_TAC
1995 [`&((2 * a * k - 1) EXP n)`; `&((2 * k - 1) EXP n) * &a pow n`;
1996 `&((2 * a * k) EXP n)`; `&((2 * k) EXP n) * &a pow n`] THEN
1997 ASM_SIMP_TAC[REAL_OF_NUM_LE; Y_LOWERBOUND; Y_UPPERBOUND;
1998 REAL_LE_RMUL_EQ; REAL_POW_LT; REAL_OF_NUM_LT;
1999 ARITH_RULE `~(a = 0) ==> 0 < a`] THEN
2000 REWRITE_TAC[REAL_OF_NUM_ADD; REAL_OF_NUM_POW; REAL_OF_NUM_MUL] THEN
2001 REWRITE_TAC[REAL_OF_NUM_LT] THEN
2002 MATCH_MP_TAC(ARITH_RULE
2003 `!x:num. x <= c /\ a < b + x /\ d < e + x ==> a < b + c /\ d < e + c`) THEN
2004 EXISTS_TAC `(2 * k - 1) EXP n` THEN REWRITE_TAC[Y_LOWERBOUND] THEN
2005 REWRITE_TAC[GSYM MULT_EXP; GSYM MULT_ASSOC] THEN
2006 REWRITE_TAC[RIGHT_SUB_DISTRIB; GSYM MULT_ASSOC] THEN
2007 SUBST1_TAC(AC MULT_AC `2 * k * a = 2 * a * k`) THEN
2008 REWRITE_TAC[MULT_CLAUSES] THEN
2009 MATCH_MP_TAC(ARITH_RULE
2010 `b' <= b /\ a < b' + c ==> a < b + c /\ a < b' + c:num`) THEN
2012 [REWRITE_TAC[LE_MULT_LCANCEL] THEN DISJ2_TAC THEN
2013 SPEC_TAC(`n:num`,`m:num`) THEN
2014 INDUCT_TAC THEN REWRITE_TAC[CONJUNCT1 EXP; LE_REFL] THEN
2015 REWRITE_TAC[EXP_MONO_LE_SUC] THEN UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC;
2017 SUBST1_TAC(AC MULT_AC `2 * a * k = 2 * k * a`) THEN
2018 GEN_REWRITE_TAC (RAND_CONV o LAND_CONV o RAND_CONV o LAND_CONV o RAND_CONV)
2019 [ARITH_RULE `a = 1 * a`] THEN
2020 REWRITE_TAC[MULT_ASSOC; GSYM RIGHT_SUB_DISTRIB] THEN
2021 REWRITE_TAC[MULT_EXP] THEN
2022 REWRITE_TAC[ARITH_RULE `2 * e * a + e = (2 * a + 1) * e`] THEN
2023 REWRITE_TAC[GSYM MULT_EXP; GSYM MULT_ASSOC] THEN
2024 SUBST1_TAC(AC MULT_AC `2 * k * a = a * 2 * k`) THEN
2025 ONCE_REWRITE_TAC[MULT_EXP] THEN REWRITE_TAC[MULT_ASSOC] THEN
2026 SUBGOAL_THEN `(2 * k) * (2 * a EXP n) * (2 * k) EXP n <
2027 (2 * k) * (2 * a EXP n + 1) * (2 * k - 1) EXP n`
2029 [ALL_TAC; ASM_SIMP_TAC[LT_MULT_LCANCEL; MULT_EQ_0; ARITH_EQ]] THEN
2030 GEN_REWRITE_TAC RAND_CONV
2031 [AC MULT_AC `(2 * k) * l * m = l * (2 * k) * m`] THEN
2032 MATCH_MP_TAC LTE_TRANS THEN
2033 EXISTS_TAC `(2 * a EXP n + 1) * (2 * k) EXP n * (2 * k - n)` THEN
2035 [ALL_TAC; REWRITE_TAC[LE_MULT_LCANCEL; BINOMIALISH_LEMMA]] THEN
2036 REWRITE_TAC[ARITH_RULE
2037 `(2 * k) * (2 * an) * 2kn < a2na * 2kn * kmn <=>
2038 2kn * 4 * k * an < 2kn * a2na * kmn`] THEN
2039 ASM_SIMP_TAC[LT_MULT_LCANCEL; EXP_EQ_0; MULT_EQ_0; ARITH_EQ] THEN
2040 REWRITE_TAC[LEFT_SUB_DISTRIB] THEN
2041 MATCH_MP_TAC(ARITH_RULE `a + b < c ==> a < c - b:num`) THEN
2042 REWRITE_TAC[LEFT_ADD_DISTRIB; RIGHT_ADD_DISTRIB; MULT_CLAUSES] THEN
2043 REWRITE_TAC[GSYM MULT_ASSOC] THEN
2044 REWRITE_TAC[ARITH_RULE `4 * k * an + x < 2 * an * 2 * k + y <=> x < y`] THEN
2045 ONCE_REWRITE_TAC[AC MULT_AC `2 * a * n = 2 * n * a`] THEN
2046 UNDISCH_TAC `2 * n * a EXP n < k` THEN
2047 MATCH_MP_TAC(ARITH_RULE
2048 `n * 1 <= x ==> 2 * x < k ==> 2 * x + n < 2 * k`) THEN
2049 ASM_REWRITE_TAC[LE_MULT_LCANCEL; ARITH_RULE `1 <= n <=> ~(n = 0)`] THEN
2050 ASM_REWRITE_TAC[EXP_EQ_0]);;
2052 let ABS_LT_REPRESENTATION = prove
2055 ==> (abs(&x / &y - &z) < &1 / &2 <=>
2056 4 * x EXP 2 + 4 * (y * z) EXP 2 < 8 * x * y * z + y EXP 2)`,
2057 REPEAT STRIP_TAC THEN MATCH_MP_TAC EQ_TRANS THEN
2058 EXISTS_TAC `&4 * (&x / &y - &z) pow 2 < &1` THEN CONJ_TAC THENL
2059 [SIMP_TAC[REAL_LT_RDIV_EQ; REAL_OF_NUM_LT; ARITH] THEN
2060 SUBST1_TAC(SYM(REAL_RAT_REDUCE_CONV `&2 * &2`)) THEN
2061 REWRITE_TAC[GSYM REAL_POW_2; GSYM REAL_POW_MUL] THEN
2062 ONCE_REWRITE_TAC[GSYM REAL_POW2_ABS] THEN
2063 REWRITE_TAC[REAL_ABS_MUL; REAL_ABS_NUM] THEN EQ_TAC THENL
2064 [GEN_REWRITE_TAC (RAND_CONV o RAND_CONV)
2065 [SYM(REAL_RAT_REDUCE_CONV `&1 pow 2`)] THEN
2066 GEN_REWRITE_TAC (LAND_CONV o LAND_CONV) [REAL_MUL_SYM] THEN
2067 SIMP_TAC[ARITH_EQ; REAL_POW_LT2; REAL_LE_MUL; REAL_POS; REAL_ABS_POS];
2068 ONCE_REWRITE_TAC[TAUT `a ==> b <=> ~b ==> ~a`] THEN
2069 REWRITE_TAC[REAL_NOT_LT] THEN
2070 GEN_REWRITE_TAC (RAND_CONV o LAND_CONV)
2071 [SYM(REAL_RAT_REDUCE_CONV `&1 pow 2`)] THEN
2072 GEN_REWRITE_TAC (LAND_CONV o RAND_CONV) [REAL_MUL_SYM] THEN
2073 SIMP_TAC[ARITH_EQ; REAL_POW_LE2; REAL_LE_MUL; REAL_POS; REAL_ABS_POS]];
2075 MATCH_MP_TAC EQ_TRANS THEN
2076 EXISTS_TAC `&4 * (&x - &y * &z) pow 2 < &y pow 2` THEN CONJ_TAC THENL
2077 [GEN_REWRITE_TAC (RAND_CONV o RAND_CONV) [GSYM REAL_POW2_ABS] THEN
2078 REWRITE_TAC[GSYM REAL_ABS_POW] THEN
2079 GEN_REWRITE_TAC (RAND_CONV o RAND_CONV) [GSYM REAL_MUL_LID] THEN
2080 ASM_SIMP_TAC[GSYM REAL_LT_LDIV_EQ; GSYM REAL_ABS_NZ; REAL_POW_EQ_0;
2081 ARITH_EQ; REAL_OF_NUM_EQ] THEN
2082 REWRITE_TAC[REAL_ABS_POW; REAL_POW2_ABS] THEN
2083 REWRITE_TAC[real_div; GSYM REAL_MUL_ASSOC] THEN
2084 REWRITE_TAC[GSYM real_div; GSYM REAL_POW_DIV] THEN
2085 AP_THM_TAC THEN AP_TERM_TAC THEN AP_TERM_TAC THEN
2086 AP_THM_TAC THEN AP_TERM_TAC THEN
2087 REWRITE_TAC[real_div; REAL_SUB_RDISTRIB; GSYM REAL_MUL_ASSOC] THEN
2089 ASM_SIMP_TAC[GSYM real_div; REAL_DIV_LMUL; REAL_OF_NUM_EQ]; ALL_TAC] THEN
2090 REWRITE_TAC[GSYM REAL_OF_NUM_LT; GSYM REAL_OF_NUM_ADD;
2091 GSYM REAL_OF_NUM_MUL; GSYM REAL_OF_NUM_POW] THEN
2092 REWRITE_TAC[REAL_POW_2] THEN REAL_ARITH_TAC);;
2095 (`!a n. ~(a = 0) ==> ((Y a n = 0) <=> (n = 0))`,
2096 REPEAT STRIP_TAC THEN
2097 SUBST1_TAC(SYM(SPEC `a:num` (CONJUNCT1 Y_CLAUSES))) THEN
2098 ASM_SIMP_TAC[Y_INJ] THEN REWRITE_TAC[Y_CLAUSES]);;
2102 ==> ((a EXP n = p) <=>
2103 ?k x y z. (Y (a * k) (n + 1) = x) /\
2104 (Y k (n + 1) = y) /\
2105 (Y a (n + 1) = z) /\
2107 4 * x EXP 2 + 4 * (y * p) EXP 2 < 8 * x * y * p + y EXP 2)`,
2109 (`(?x y z. (a = x) /\ (b = y) /\ (c = z) /\ P x y z) <=> P a b c`,
2112 CONV_RULE(RAND_CONV(ONCE_DEPTH_CONV SYM_CONV))
2113 (SPEC_ALL ABS_LT_REPRESENTATION) in
2114 REPEAT STRIP_TAC THEN REWRITE_TAC[lemma1] THEN
2115 GEN_REWRITE_TAC (RAND_CONV o BINDER_CONV o LAND_CONV)
2116 [ARITH_RULE `n < k <=> n < k /\ ~(k = 0)`] THEN
2117 ONCE_REWRITE_TAC[TAUT `a /\ b <=> ~(a ==> ~b)`] THEN
2118 ASM_SIMP_TAC[lemma2; Y_EQ_0; ADD_EQ_0; ARITH_EQ] THEN
2119 REWRITE_TAC[NOT_IMP] THEN
2120 REWRITE_TAC[ARITH_RULE `n < k /\ ~(k = 0) <=> n < k`] THEN
2122 [DISCH_THEN(SUBST1_TAC o SYM) THEN
2123 EXISTS_TAC `2 * n * Y a (n + 1) + 1` THEN
2124 REWRITE_TAC[ARITH_RULE `c < c + 1`; GSYM REAL_OF_NUM_POW] THEN
2125 MATCH_MP_TAC XY_EXP_LEMMA THEN ASM_REWRITE_TAC[] THEN
2126 MATCH_MP_TAC(ARITH_RULE `a <= b ==> 2 * a < 2 * b + 1`) THEN
2127 REWRITE_TAC[LE_MULT_LCANCEL] THEN DISJ2_TAC THEN
2128 MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `(2 * a - 1) EXP n` THEN
2129 REWRITE_TAC[Y_LOWERBOUND] THEN
2130 SPEC_TAC(`n:num`,`n:num`) THEN INDUCT_TAC THEN
2131 REWRITE_TAC[CONJUNCT1 EXP; LE_REFL; EXP_MONO_LE_SUC] THEN
2132 UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC; ALL_TAC] THEN
2133 DISCH_THEN(X_CHOOSE_THEN `k:num` (CONJUNCTS_THEN2 ASSUME_TAC MP_TAC)) THEN
2134 MP_TAC(SPECL [`a:num`; `k:num`; `n:num`] XY_EXP_LEMMA) THEN
2136 [ASM_REWRITE_TAC[] THEN
2137 FIRST_X_ASSUM(MATCH_MP_TAC o MATCH_MP (ARITH_RULE
2138 `2 * a < k ==> b <= a ==> 2 * b < k`)) THEN
2139 REWRITE_TAC[LE_MULT_LCANCEL] THEN DISJ2_TAC THEN
2140 MATCH_MP_TAC LE_TRANS THEN EXISTS_TAC `(2 * a - 1) EXP n` THEN
2141 REWRITE_TAC[Y_LOWERBOUND] THEN
2142 SPEC_TAC(`n:num`,`n:num`) THEN INDUCT_TAC THEN
2143 REWRITE_TAC[CONJUNCT1 EXP; LE_REFL; EXP_MONO_LE_SUC] THEN
2144 UNDISCH_TAC `~(a = 0)` THEN ARITH_TAC; ALL_TAC] THEN
2145 REWRITE_TAC[IMP_IMP] THEN
2146 DISCH_THEN(MP_TAC o MATCH_MP (REAL_ARITH
2147 `abs(x - a) < e1 /\ abs(x - b) < e2 ==> abs(a - b) < e1 + e2`)) THEN
2148 CONV_TAC REAL_RAT_REDUCE_CONV THEN
2149 DISCH_THEN(MP_TAC o MATCH_MP (REAL_ARITH
2151 ==> a + &1 <= b \/ (a = b) \/ b + &1 <= a ==> (a = b)`)) THEN
2152 REWRITE_TAC[REAL_OF_NUM_POW; REAL_OF_NUM_ADD;
2153 REAL_OF_NUM_EQ; REAL_OF_NUM_LE] THEN
2154 DISCH_THEN MATCH_MP_TAC THEN ARITH_TAC);;
2156 (* ------------------------------------------------------------------------- *)
2158 (* ------------------------------------------------------------------------- *)
2160 let REAL_SUM_OF_SQUARES = prove
2161 (`(x pow 2 + y pow 2 = &0) <=> (x = &0) /\ (y = &0)`,
2162 REWRITE_TAC[REAL_POW_2] THEN EQ_TAC THEN
2163 SIMP_TAC[REAL_MUL_LZERO; REAL_ADD_LID] THEN
2164 DISCH_THEN(MP_TAC o MATCH_MP (REAL_ARITH
2165 `(a + b = &0) ==> &0 <= a /\ &0 <= b ==> (a = &0) /\ (b = &0)`)) THEN
2166 REWRITE_TAC[REAL_LE_SQUARE; REAL_ENTIRE]);;
2168 (* ------------------------------------------------------------------------- *)
2169 (* Combining theorems for conjunction and disjunction. *)
2170 (* ------------------------------------------------------------------------- *)
2172 let DIOPH_CONJ = prove
2173 (`(x1 = x2) /\ (y1 = y2) <=>
2174 (x1 * x1 + x2 * x2 + y1 * y1 + y2 * y2 = 2 * x1 * x2 + 2 * y1 * y2)`,
2175 REWRITE_TAC[GSYM REAL_OF_NUM_EQ;
2176 GSYM REAL_OF_NUM_ADD; GSYM REAL_OF_NUM_MUL] THEN
2177 ONCE_REWRITE_TAC[GSYM REAL_SUB_0] THEN
2178 REWRITE_TAC[GSYM REAL_SUM_OF_SQUARES] THEN
2179 REWRITE_TAC[REAL_POW_2] THEN REAL_ARITH_TAC);;
2181 let DIOPH_DISJ = prove
2182 (`(x1 = x2) \/ (y1 = y2) <=>
2183 (x1 * y1 + x2 * y2 = x1 * y2 + x2 * y1)`,
2184 REWRITE_TAC[GSYM REAL_OF_NUM_EQ;
2185 GSYM REAL_OF_NUM_ADD; GSYM REAL_OF_NUM_MUL] THEN
2186 ONCE_REWRITE_TAC[GSYM REAL_SUB_0] THEN
2187 REWRITE_TAC[GSYM REAL_ENTIRE] THEN REAL_ARITH_TAC);;
2189 (* ------------------------------------------------------------------------- *)
2191 (* ------------------------------------------------------------------------- *)
2193 let DIOPH_LE = prove
2194 (`x <= y <=> ?d:num. x + d = y`,
2195 REWRITE_TAC[LE_EXISTS] THEN
2196 AP_TERM_TAC THEN ABS_TAC THEN
2197 REWRITE_TAC[ADD_AC; EQ_SYM_EQ]);;
2199 let DIOPH_LT = prove
2200 (`x < y <=> ?d. x + d + 1 = y`,
2201 REWRITE_TAC[LT_EXISTS] THEN
2202 REWRITE_TAC[ADD1] THEN
2203 AP_TERM_TAC THEN ABS_TAC THEN
2204 REWRITE_TAC[ADD_AC; EQ_SYM_EQ]);;
2206 let DIOPH_NE = prove
2207 (`~(x = y) <=> x < y \/ y < x:num`,
2210 (* ------------------------------------------------------------------------- *)
2211 (* Exponentiation (from the Pell stuff). *)
2212 (* ------------------------------------------------------------------------- *)
2215 (`!k. Y 0 k = if k = 1 then 1 else 0`,
2216 INDUCT_TAC THEN REWRITE_TAC[Y_CLAUSES; ARITH_EQ] THEN
2217 SPEC_TAC(`k:num`,`k:num`) THEN
2218 INDUCT_TAC THEN REWRITE_TAC[Y_CLAUSES; ARITH] THEN
2219 REWRITE_TAC[ARITH_RULE `SUC(SUC n) = n + 2`; Y_CLAUSES; ARITH] THEN
2220 REWRITE_TAC[MULT_CLAUSES; SUB_0; ARITH_RULE `~(k + 2 = 1)`]);;
2222 let Y_0_TRIV = prove
2223 (`!k. (Y 0 k = 0) <=> ~(k = 1)`,
2224 GEN_TAC THEN REWRITE_TAC[Y_0] THEN
2225 COND_CASES_TAC THEN ASM_REWRITE_TAC[ARITH_EQ]);;
2229 (a = 0) /\ (k = 1) /\ (y = 1) \/
2230 (a = 0) /\ ~(k = 1) /\ (y = 0) \/
2231 (k = 0) /\ (y = 0) \/
2232 (a = 1) /\ (y = k) \/
2233 ~(a = 0) /\ ~(k = 0) /\ ~(a = 1) /\ ~(y = 0) /\
2234 ?x u v r b p q s t c d.
2236 (x EXP 2 = (a EXP 2 - 1) * y EXP 2 + 1) /\
2237 (u EXP 2 = (a EXP 2 - 1) * v EXP 2 + 1) /\
2238 (s EXP 2 = (b EXP 2 - 1) * t EXP 2 + 1) /\
2239 (v = r * y EXP 2) /\
2240 (b = 1 + 4 * p * y) /\
2243 (t = k + 4 * d * y) /\
2245 ASM_CASES_TAC `a = 0` THENL
2246 [ASM_CASES_TAC `y = 0` THENL
2247 [ASM_REWRITE_TAC[Y_0_TRIV; ARITH_EQ] THEN ARITH_TAC; ALL_TAC] THEN
2248 ASM_CASES_TAC `k = 0` THEN ASM_REWRITE_TAC[Y_CLAUSES; ARITH_EQ] THEN
2249 ASM_REWRITE_TAC[ARITH_EQ] THEN CONV_TAC NUM_REDUCE_CONV THEN
2250 REWRITE_TAC[MULT_CLAUSES; ADD_CLAUSES] THEN
2251 REWRITE_TAC[EXP_2; MULT_EQ_1] THEN
2252 REWRITE_TAC[Y_0] THEN COND_CASES_TAC THEN ASM_REWRITE_TAC[] THEN
2253 REWRITE_TAC[EQ_SYM_EQ]; ALL_TAC] THEN
2254 ASM_REWRITE_TAC[ARITH_EQ] THEN
2255 ASM_CASES_TAC `k = 0` THEN ASM_REWRITE_TAC[Y_CLAUSES] THENL
2256 [REWRITE_TAC[EQ_SYM_EQ] THEN CONV_TAC(EQT_INTRO o TAUT); ALL_TAC] THEN
2257 ASM_CASES_TAC `a = 1` THEN ASM_REWRITE_TAC[Y_DEGENERATE] THENL
2258 [REWRITE_TAC[EQ_SYM_EQ]; ALL_TAC] THEN
2259 ASM_CASES_TAC `y = 0` THEN ASM_SIMP_TAC[Y_EQ_0] THEN
2260 GEN_REWRITE_TAC LAND_CONV [EQ_SYM_EQ] THEN ASM_SIMP_TAC[Y_DIOPH]);;
2262 let DIOPH_EXP_LEMMA = prove
2264 (m = 0) /\ (n = 0) /\ (p = 1) \/
2265 (m = 0) /\ ~(n = 0) /\ (p = 0) \/
2267 ?k x y z. (Y (m * k) (n + 1) = x) /\
2268 (Y k (n + 1) = y) /\
2269 (Y m (n + 1) = z) /\
2271 4 * x EXP 2 + 4 * (y * p) EXP 2 < 8 * x * y * p + y EXP 2`,
2272 ASM_CASES_TAC `m = 0` THEN ASM_REWRITE_TAC[ARITH_EQ] THENL
2273 [SPEC_TAC(`n:num`,`n:num`) THEN INDUCT_TAC THEN
2274 REWRITE_TAC[EXP; MULT_CLAUSES; ADD_CLAUSES; NOT_SUC] THEN
2275 REWRITE_TAC[EQ_SYM_EQ]; ALL_TAC] THEN
2276 ASM_SIMP_TAC[XY_EXP]);;
2279 let th1 = REWRITE_RULE[DIOPH_Y] DIOPH_EXP_LEMMA in
2280 let th2 = REWRITE_RULE[EXP_2] th1 in
2281 let th3 = REWRITE_RULE[DIOPH_NE; DIOPH_LT; DIOPH_LE] th2 in
2282 let th4 = REWRITE_RULE[ADD_CLAUSES; ARITH_EQ; ADD_EQ_0;
2283 ARITH_RULE `(n + 1 = 1) = (n = 0)`; ADD_ASSOC;
2284 EQ_ADD_RCANCEL] th3 in
2285 let th5 = REWRITE_RULE[GSYM ADD_ASSOC] th4 in
2287 [OR_EXISTS_THM; LEFT_OR_EXISTS_THM; RIGHT_OR_EXISTS_THM;
2288 LEFT_AND_EXISTS_THM; RIGHT_AND_EXISTS_THM] th5;;
2290 (****** This takes about an hour to compute, and longer to print out!
2292 let DIOPH_EXP_ONE_EQUATION =
2293 REWRITE_RULE[DIOPH_CONJ; DIOPH_DISJ] DIOPH_EXP;;