1
(************************************************************************)
2
(* v * The Coq Proof Assistant / The Coq Development Team *)
3
(* <O___,, * CNRS-Ecole Polytechnique-INRIA Futurs-Universite Paris Sud *)
4
(* \VV/ **************************************************************)
5
(* // * This file is distributed under the terms of the *)
6
(* * GNU Lesser General Public License Version 2.1 *)
7
(************************************************************************)
9
(*i $Id: R_sqrt.v 10710 2008-03-23 09:24:09Z herbelin $ i*)
12
Require Import Rfunctions.
13
Require Import Rsqrt_def.
14
Open Local Scope R_scope.
16
(** * Continuous extension of Rsqrt on R *)
17
Definition sqrt (x:R) : R :=
18
match Rcase_abs x with
20
| right a => Rsqrt (mknonnegreal x (Rge_le _ _ a))
23
Lemma sqrt_positivity : forall x:R, 0 <= x -> 0 <= sqrt x.
27
case (Rcase_abs x); intro.
28
elim (Rlt_irrefl _ (Rlt_le_trans _ _ _ r H)).
29
apply Rsqrt_positivity.
32
Lemma sqrt_sqrt : forall x:R, 0 <= x -> sqrt x * sqrt x = x.
36
case (Rcase_abs x); intro.
37
elim (Rlt_irrefl _ (Rlt_le_trans _ _ _ r H)).
38
rewrite Rsqrt_Rsqrt; reflexivity.
41
Lemma sqrt_0 : sqrt 0 = 0.
43
apply Rsqr_eq_0; unfold Rsqr in |- *; apply sqrt_sqrt; right; reflexivity.
46
Lemma sqrt_1 : sqrt 1 = 1.
48
apply (Rsqr_inj (sqrt 1) 1);
49
[ apply sqrt_positivity; left
51
| unfold Rsqr in |- *; rewrite sqrt_sqrt; [ ring | left ] ];
55
Lemma sqrt_eq_0 : forall x:R, 0 <= x -> sqrt x = 0 -> x = 0.
57
intros; cut (Rsqr (sqrt x) = 0).
58
intro; unfold Rsqr in H1; rewrite sqrt_sqrt in H1; assumption.
59
rewrite H0; apply Rsqr_0.
62
Lemma sqrt_lem_0 : forall x y:R, 0 <= x -> 0 <= y -> sqrt x = y -> y * y = x.
64
intros; rewrite <- H1; apply (sqrt_sqrt x H).
67
Lemma sqrt_lem_1 : forall x y:R, 0 <= x -> 0 <= y -> y * y = x -> sqrt x = y.
69
intros; apply Rsqr_inj;
70
[ apply (sqrt_positivity x H)
72
| unfold Rsqr in |- *; rewrite H1; apply (sqrt_sqrt x H) ].
75
Lemma sqrt_def : forall x:R, 0 <= x -> sqrt x * sqrt x = x.
77
intros; apply (sqrt_sqrt x H).
80
Lemma sqrt_square : forall x:R, 0 <= x -> sqrt (x * x) = x.
84
(Rsqr_inj (sqrt (Rsqr x)) x (sqrt_positivity (Rsqr x) (Rle_0_sqr x)) H);
85
unfold Rsqr in |- *; apply (sqrt_sqrt (Rsqr x) (Rle_0_sqr x)).
88
Lemma sqrt_Rsqr : forall x:R, 0 <= x -> sqrt (Rsqr x) = x.
90
intros; unfold Rsqr in |- *; apply sqrt_square; assumption.
93
Lemma sqrt_Rsqr_abs : forall x:R, sqrt (Rsqr x) = Rabs x.
95
intro x; rewrite Rsqr_abs; apply sqrt_Rsqr; apply Rabs_pos.
98
Lemma Rsqr_sqrt : forall x:R, 0 <= x -> Rsqr (sqrt x) = x.
100
intros x H1; unfold Rsqr in |- *; apply (sqrt_sqrt x H1).
104
forall x y:R, 0 <= x -> 0 <= y -> sqrt (x * y) = sqrt x * sqrt y.
108
(Rsqr_inj (sqrt (x * y)) (sqrt x * sqrt y)
109
(sqrt_positivity (x * y) (Rmult_le_pos x y H1 H2))
110
(Rmult_le_pos (sqrt x) (sqrt y) (sqrt_positivity x H1)
111
(sqrt_positivity y H2))); rewrite Rsqr_mult;
112
repeat rewrite Rsqr_sqrt;
113
[ ring | assumption | assumption | apply (Rmult_le_pos x y H1 H2) ].
116
Lemma sqrt_lt_R0 : forall x:R, 0 < x -> 0 < sqrt x.
118
intros x H1; apply Rsqr_incrst_0;
119
[ rewrite Rsqr_0; rewrite Rsqr_sqrt; [ assumption | left; assumption ]
121
| apply (sqrt_positivity x (Rlt_le 0 x H1)) ].
125
forall x y:R, 0 <= x -> 0 < y -> sqrt (x / y) = sqrt x / sqrt y.
127
intros x y H1 H2; apply Rsqr_inj;
128
[ apply sqrt_positivity; apply (Rmult_le_pos x (/ y));
130
| generalize (Rinv_0_lt_compat y H2); clear H2; intro H2; left;
132
| apply (Rmult_le_pos (sqrt x) (/ sqrt y));
133
[ apply (sqrt_positivity x H1)
134
| generalize (sqrt_lt_R0 y H2); clear H2; intro H2;
135
generalize (Rinv_0_lt_compat (sqrt y) H2); clear H2;
136
intro H2; left; assumption ]
137
| rewrite Rsqr_div; repeat rewrite Rsqr_sqrt;
141
| generalize (Rinv_0_lt_compat y H2); intro H3;
142
generalize (Rlt_le 0 (/ y) H3); intro H4;
143
apply (Rmult_le_pos x (/ y) H1 H4)
144
| red in |- *; intro H3; generalize (Rlt_le 0 y H2); intro H4;
145
generalize (sqrt_eq_0 y H4 H3); intro H5; rewrite H5 in H2;
146
elim (Rlt_irrefl 0 H2) ] ].
149
Lemma sqrt_lt_0 : forall x y:R, 0 <= x -> 0 <= y -> sqrt x < sqrt y -> x < y.
153
(Rsqr_incrst_1 (sqrt x) (sqrt y) H3 (sqrt_positivity x H1)
154
(sqrt_positivity y H2)); intro H4; rewrite (Rsqr_sqrt x H1) in H4;
155
rewrite (Rsqr_sqrt y H2) in H4; assumption.
158
Lemma sqrt_lt_1 : forall x y:R, 0 <= x -> 0 <= y -> x < y -> sqrt x < sqrt y.
160
intros x y H1 H2 H3; apply Rsqr_incrst_0;
161
[ rewrite (Rsqr_sqrt x H1); rewrite (Rsqr_sqrt y H2); assumption
162
| apply (sqrt_positivity x H1)
163
| apply (sqrt_positivity y H2) ].
167
forall x y:R, 0 <= x -> 0 <= y -> sqrt x <= sqrt y -> x <= y.
171
(Rsqr_incr_1 (sqrt x) (sqrt y) H3 (sqrt_positivity x H1)
172
(sqrt_positivity y H2)); intro H4; rewrite (Rsqr_sqrt x H1) in H4;
173
rewrite (Rsqr_sqrt y H2) in H4; assumption.
177
forall x y:R, 0 <= x -> 0 <= y -> x <= y -> sqrt x <= sqrt y.
179
intros x y H1 H2 H3; apply Rsqr_incr_0;
180
[ rewrite (Rsqr_sqrt x H1); rewrite (Rsqr_sqrt y H2); assumption
181
| apply (sqrt_positivity x H1)
182
| apply (sqrt_positivity y H2) ].
185
Lemma sqrt_inj : forall x y:R, 0 <= x -> 0 <= y -> sqrt x = sqrt y -> x = y.
187
intros; cut (Rsqr (sqrt x) = Rsqr (sqrt y)).
188
intro; rewrite (Rsqr_sqrt x H) in H2; rewrite (Rsqr_sqrt y H0) in H2;
190
rewrite H1; reflexivity.
193
Lemma sqrt_less : forall x:R, 0 <= x -> 1 < x -> sqrt x < x.
195
intros x H1 H2; generalize (sqrt_lt_1 1 x (Rlt_le 0 1 Rlt_0_1) H1 H2);
196
intro H3; rewrite sqrt_1 in H3; generalize (Rmult_ne (sqrt x));
197
intro H4; elim H4; intros H5 H6; rewrite <- H5; pattern x at 2 in |- *;
198
rewrite <- (sqrt_def x H1);
200
(Rmult_lt_compat_l (sqrt x) 1 (sqrt x)
201
(sqrt_lt_R0 x (Rlt_trans 0 1 x Rlt_0_1 H2)) H3).
204
Lemma sqrt_more : forall x:R, 0 < x -> x < 1 -> x < sqrt x.
207
generalize (sqrt_lt_1 x 1 (Rlt_le 0 x H1) (Rlt_le 0 1 Rlt_0_1) H2);
208
intro H3; rewrite sqrt_1 in H3; generalize (Rmult_ne (sqrt x));
209
intro H4; elim H4; intros H5 H6; rewrite <- H5; pattern x at 1 in |- *;
210
rewrite <- (sqrt_def x (Rlt_le 0 x H1));
211
apply (Rmult_lt_compat_l (sqrt x) (sqrt x) 1 (sqrt_lt_R0 x H1) H3).
216
a * c + b * d <= sqrt (Rsqr a + Rsqr b) * sqrt (Rsqr c + Rsqr d).
218
intros a b c d; apply Rsqr_incr_0_var;
219
[ rewrite Rsqr_mult; repeat rewrite Rsqr_sqrt; unfold Rsqr in |- *;
220
[ replace ((a * c + b * d) * (a * c + b * d)) with
221
(a * a * c * c + b * b * d * d + 2 * a * b * c * d);
222
[ replace ((a * a + b * b) * (c * c + d * d)) with
223
(a * a * c * c + b * b * d * d + (a * a * d * d + b * b * c * c));
224
[ apply Rplus_le_compat_l;
225
replace (a * a * d * d + b * b * c * c) with
227
(a * a * d * d + b * b * c * c - 2 * a * b * c * d));
228
[ pattern (2 * a * b * c * d) at 1 in |- *; rewrite <- Rplus_0_r;
229
apply Rplus_le_compat_l;
230
replace (a * a * d * d + b * b * c * c - 2 * a * b * c * d)
231
with (Rsqr (a * d - b * c));
232
[ apply Rle_0_sqr | unfold Rsqr in |- *; ring ]
237
(Rplus_le_le_0_compat (Rsqr c) (Rsqr d) (Rle_0_sqr c) (Rle_0_sqr d))
239
(Rplus_le_le_0_compat (Rsqr a) (Rsqr b) (Rle_0_sqr a) (Rle_0_sqr b)) ]
240
| apply Rmult_le_pos; apply sqrt_positivity; apply Rplus_le_le_0_compat;
244
(************************************************************)
245
(** * Resolution of [a*X^2+b*X+c=0] *)
246
(************************************************************)
248
Definition Delta (a:nonzeroreal) (b c:R) : R := Rsqr b - 4 * a * c.
250
Definition Delta_is_pos (a:nonzeroreal) (b c:R) : Prop := 0 <= Delta a b c.
252
Definition sol_x1 (a:nonzeroreal) (b c:R) : R :=
253
(- b + sqrt (Delta a b c)) / (2 * a).
255
Definition sol_x2 (a:nonzeroreal) (b c:R) : R :=
256
(- b - sqrt (Delta a b c)) / (2 * a).
258
Lemma Rsqr_sol_eq_0_1 :
259
forall (a:nonzeroreal) (b c x:R),
260
Delta_is_pos a b c ->
261
x = sol_x1 a b c \/ x = sol_x2 a b c -> a * Rsqr x + b * x + c = 0.
263
intros; elim H0; intro.
264
unfold sol_x1 in H1; unfold Delta in H1; rewrite H1; unfold Rdiv in |- *;
265
repeat rewrite Rsqr_mult; rewrite Rsqr_plus; rewrite <- Rsqr_neg;
268
unfold Rsqr in |- *; repeat rewrite Rinv_mult_distr.
269
repeat rewrite Rmult_assoc; rewrite (Rmult_comm a).
270
repeat rewrite Rmult_assoc; rewrite <- Rinv_l_sym.
271
rewrite Rmult_1_r; rewrite Rmult_plus_distr_r.
272
repeat rewrite Rmult_assoc.
273
pattern 2 at 2 in |- *; rewrite (Rmult_comm 2).
274
repeat rewrite Rmult_assoc; rewrite <- Rinv_l_sym.
277
(Rmult_plus_distr_r (- b) (sqrt (b * b - 2 * (2 * (a * c)))) (/ 2 * / a))
279
rewrite Rmult_plus_distr_l; repeat rewrite Rplus_assoc.
281
(- b * (sqrt (b * b - 2 * (2 * (a * c))) * (/ 2 * / a)) +
282
(b * (- b * (/ 2 * / a)) +
283
(b * (sqrt (b * b - 2 * (2 * (a * c))) * (/ 2 * / a)) + c))) with
284
(b * (- b * (/ 2 * / a)) + c).
285
unfold Rminus in |- *; repeat rewrite <- Rplus_assoc.
286
replace (b * b + b * b) with (2 * (b * b)).
287
rewrite Rmult_plus_distr_r; repeat rewrite Rmult_assoc.
288
rewrite (Rmult_comm 2); repeat rewrite Rmult_assoc.
289
rewrite <- Rinv_l_sym.
291
rewrite Ropp_mult_distr_l_reverse; repeat rewrite Rmult_assoc;
292
rewrite (Rmult_comm 2).
293
repeat rewrite Rmult_assoc; rewrite <- Rinv_l_sym.
294
rewrite Rmult_1_r; rewrite (Rmult_comm (/ 2)); repeat rewrite Rmult_assoc;
295
rewrite (Rmult_comm 2).
296
repeat rewrite Rmult_assoc; rewrite <- Rinv_l_sym.
297
rewrite Rmult_1_r; repeat rewrite Rmult_assoc.
298
rewrite (Rmult_comm a); rewrite Rmult_assoc.
299
rewrite <- Rinv_l_sym.
300
rewrite Rmult_1_r; rewrite <- Rmult_opp_opp.
302
apply (cond_nonzero a).
309
apply (cond_nonzero a).
311
apply (cond_nonzero a).
312
apply prod_neq_R0; [ discrR | apply (cond_nonzero a) ].
313
apply prod_neq_R0; [ discrR | apply (cond_nonzero a) ].
314
apply prod_neq_R0; [ discrR | apply (cond_nonzero a) ].
316
unfold sol_x2 in H1; unfold Delta in H1; rewrite H1; unfold Rdiv in |- *;
317
repeat rewrite Rsqr_mult; rewrite Rsqr_minus; rewrite <- Rsqr_neg;
320
unfold Rsqr in |- *; repeat rewrite Rinv_mult_distr;
321
repeat rewrite Rmult_assoc.
322
rewrite (Rmult_comm a); repeat rewrite Rmult_assoc.
323
rewrite <- Rinv_l_sym.
324
rewrite Rmult_1_r; unfold Rminus in |- *; rewrite Rmult_plus_distr_r.
325
rewrite Ropp_mult_distr_l_reverse; repeat rewrite Rmult_assoc;
326
pattern 2 at 2 in |- *; rewrite (Rmult_comm 2).
327
repeat rewrite Rmult_assoc; rewrite <- Rinv_l_sym.
330
(Rmult_plus_distr_r (- b) (- sqrt (b * b + - (2 * (2 * (a * c)))))
332
rewrite Rmult_plus_distr_l; repeat rewrite Rplus_assoc.
333
rewrite Ropp_mult_distr_l_reverse; rewrite Ropp_involutive.
335
(b * (sqrt (b * b + - (2 * (2 * (a * c)))) * (/ 2 * / a)) +
336
(b * (- b * (/ 2 * / a)) +
337
(b * (- sqrt (b * b + - (2 * (2 * (a * c)))) * (/ 2 * / a)) + c))) with
338
(b * (- b * (/ 2 * / a)) + c).
339
repeat rewrite <- Rplus_assoc; replace (b * b + b * b) with (2 * (b * b)).
340
rewrite Rmult_plus_distr_r; repeat rewrite Rmult_assoc;
341
rewrite (Rmult_comm 2); repeat rewrite Rmult_assoc;
342
rewrite <- Rinv_l_sym.
343
rewrite Ropp_mult_distr_l_reverse; repeat rewrite Rmult_assoc.
344
rewrite (Rmult_comm 2); repeat rewrite Rmult_assoc; rewrite <- Rinv_l_sym.
345
rewrite Rmult_1_r; rewrite (Rmult_comm (/ 2)); repeat rewrite Rmult_assoc.
346
rewrite (Rmult_comm 2); repeat rewrite Rmult_assoc; rewrite <- Rinv_l_sym.
347
rewrite Rmult_1_r; repeat rewrite Rmult_assoc; rewrite (Rmult_comm a);
348
rewrite Rmult_assoc; rewrite <- Rinv_l_sym.
349
rewrite Rmult_1_r; rewrite <- Rmult_opp_opp; ring.
350
apply (cond_nonzero a).
357
apply (cond_nonzero a).
360
apply (cond_nonzero a).
361
apply prod_neq_R0; discrR || apply (cond_nonzero a).
362
apply prod_neq_R0; discrR || apply (cond_nonzero a).
363
apply prod_neq_R0; discrR || apply (cond_nonzero a).
367
Lemma Rsqr_sol_eq_0_0 :
368
forall (a:nonzeroreal) (b c x:R),
369
Delta_is_pos a b c ->
370
a * Rsqr x + b * x + c = 0 -> x = sol_x1 a b c \/ x = sol_x2 a b c.
372
intros; rewrite (canonical_Rsqr a b c x) in H0; rewrite Rplus_comm in H0;
374
(Rplus_opp_r_uniq ((4 * a * c - Rsqr b) / (4 * a))
375
(a * Rsqr (x + b / (2 * a))) H0); cut (Rsqr b - 4 * a * c = Delta a b c).
377
replace (- ((4 * a * c - Rsqr b) / (4 * a))) with
378
((Rsqr b - 4 * a * c) / (4 * a)).
381
(Rmult_eq_compat_l (/ a) (a * Rsqr (x + b / (2 * a)))
382
(Delta a b c / (4 * a)) H2);
383
replace (/ a * (a * Rsqr (x + b / (2 * a)))) with (Rsqr (x + b / (2 * a))).
384
replace (/ a * (Delta a b c / (4 * a))) with
385
(Rsqr (sqrt (Delta a b c) / (2 * a))).
387
generalize (Rsqr_eq (x + b / (2 * a)) (sqrt (Delta a b c) / (2 * a)) H3);
388
intro; elim H4; intro.
389
left; unfold sol_x1 in |- *;
391
(Rplus_eq_compat_l (- (b / (2 * a))) (x + b / (2 * a))
392
(sqrt (Delta a b c) / (2 * a)) H5);
393
replace (- (b / (2 * a)) + (x + b / (2 * a))) with x.
394
intro; rewrite H6; unfold Rdiv in |- *; ring.
396
right; unfold sol_x2 in |- *;
398
(Rplus_eq_compat_l (- (b / (2 * a))) (x + b / (2 * a))
399
(- (sqrt (Delta a b c) / (2 * a))) H5);
400
replace (- (b / (2 * a)) + (x + b / (2 * a))) with x.
401
intro; rewrite H6; unfold Rdiv in |- *; ring.
406
repeat rewrite Rmult_assoc.
407
rewrite (Rmult_comm (/ a)).
409
rewrite <- Rinv_mult_distr.
410
replace (2 * (2 * a) * a) with (Rsqr (2 * a)).
413
rewrite <- Rmult_assoc; apply prod_neq_R0;
414
[ discrR | apply (cond_nonzero a) ].
415
apply (cond_nonzero a).
417
apply prod_neq_R0; [ discrR | apply (cond_nonzero a) ].
418
rewrite <- Rmult_assoc; rewrite <- Rinv_l_sym.
419
symmetry in |- *; apply Rmult_1_l.
420
apply (cond_nonzero a).
421
unfold Rdiv in |- *; rewrite <- Ropp_mult_distr_l_reverse.
422
rewrite Ropp_minus_distr.