forked from coq-community/math-classes
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathseries.v
316 lines (265 loc) · 10 KB
/
series.v
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
Require Import
Coq.setoid_ring.Ring Coq.Arith.Factorial MathClasses.misc.workaround_tactics
MathClasses.interfaces.abstract_algebra MathClasses.interfaces.additional_operations MathClasses.interfaces.orders
MathClasses.interfaces.naturals MathClasses.interfaces.integers
MathClasses.theory.nat_pow MathClasses.theory.int_pow MathClasses.theory.streams.
Local Existing Instance srorder_semiring.
Section series.
Context `{SemiRingOrder A}.
Add Ring A : (rings.stdlib_semiring_theory A).
Add Ring nat : (rings.stdlib_semiring_theory nat).
Class DecreasingNonNegative (s : ∞A) : Prop :=
decreasing_nonneg : ForAll (λ t, 0 ≤ hd (tl t) ≤ hd t) s.
(* An equivalent definition is to say that given a point [s] in the stream,
then every further point in that stream is in [[0,s]]. *)
Lemma dnn_alt (s : ∞A) :
DecreasingNonNegative s ↔ ForAll (λ s, ForAll (λ t, 0 ≤ hd t ≤ hd s) s) s.
Proof.
split; revert s; cofix FIX; intros s E.
constructor.
cut (hd s ≤ hd s); [|reflexivity].
set (x:=hd s). unfold x at 1.
generalize s E x. clear s E x.
cofix FIX2. intros s E.
constructor.
split; trivial. destruct E.
now transitivity (hd (tl s)).
destruct E.
apply FIX2; trivial.
now transitivity (hd s).
destruct E. now apply FIX.
constructor.
now destruct E as [[? [? ?]] ?].
apply FIX. now destruct E.
Qed.
Definition dnn_Str_nth (s : ∞A) :
DecreasingNonNegative s ↔ ∀ n, 0 ≤ Str_nth (S n) s ≤ Str_nth n s.
Proof.
split.
intros dnn n. revert s dnn.
induction n; intros s E; unfold Str_nth in *; simpl.
apply E.
apply IHn. now destruct E.
revert s. cofix FIX. intros s E.
constructor; unfold Str_nth in *; simpl in *.
apply (E O).
apply FIX. intros n.
apply (E (S n)).
Qed.
Global Instance dnn_tl `(dnn : DecreasingNonNegative s) : DecreasingNonNegative (tl s).
Proof. now destruct dnn. Qed.
Global Instance dnn_Str_nth_tl `(dnn : DecreasingNonNegative s) : ∀ n, DecreasingNonNegative (Str_nth_tl n s).
Proof.
intros n. revert s dnn.
induction n; [easy|]. intros s E.
now apply IHn, _.
Qed.
Lemma dnn_hd_nonneg `(dnn : DecreasingNonNegative s) : 0 ≤ hd s.
Proof. destruct dnn. now transitivity (hd (tl s)). Qed.
Lemma dnn_Str_nth_nonneg `(dnn : DecreasingNonNegative s) n : 0 ≤ Str_nth n s.
Proof. destruct n; apply (dnn_hd_nonneg _). Qed.
Class IncreasingNonNegative (s : ∞A) : Prop :=
increasing_nonneg : ForAll (λ s, 0 ≤ hd s ≤ hd (tl s)) s.
Lemma inn_Str_nth (s : ∞A) :
IncreasingNonNegative s ↔ ∀ n, 0 ≤ Str_nth n s ≤ Str_nth (S n) s.
Proof.
split.
intros E n. revert s E.
induction n; intros s E; unfold Str_nth in *; simpl.
apply E.
apply IHn. now destruct E.
revert s. cofix FIX. intros s E.
constructor; unfold Str_nth in *; simpl in *.
apply (E O).
apply FIX. intros n.
apply (E (S n)).
Qed.
Global Instance inn_tl `(inn : IncreasingNonNegative s) : IncreasingNonNegative (tl s).
Proof. now destruct inn. Qed.
Global Instance inn_Str_nth_tl `(inn : IncreasingNonNegative s) : ∀ n, IncreasingNonNegative (Str_nth_tl n s).
Proof.
intros n. revert s inn.
induction n; trivial. intros s E.
now apply IHn, _.
Qed.
Section every_other.
CoFixpoint everyOther (s : ∞A) : ∞A := Cons (hd s) (everyOther (tl (tl s))).
Lemma Str_nth_tl_everyOther (n : nat) (s : ∞A) : Str_nth_tl n (everyOther s) ≡ everyOther (Str_nth_tl (2 * n) s).
Proof.
revert s.
induction n; intros s; simpl; trivial.
rewrite IHn.
replace (n + S (n + 0))%nat with (S (2*n))%nat.
easy.
change (1 + (1 + 1) * n = n + (1 + (n + 0))). ring.
Qed.
Lemma Str_nth_everyOther (n : nat) (s : ∞A) : Str_nth n (everyOther s) = Str_nth (2 * n) s.
Proof.
unfold Str_nth.
rewrite Str_nth_tl_everyOther.
now destruct (Str_nth_tl (2 * n) s).
Qed.
Global Instance everyOther_dnn `(dnn : !DecreasingNonNegative s) : DecreasingNonNegative (everyOther s).
Proof.
revert s dnn.
cofix FIX. intros s dnn.
constructor; simpl.
destruct dnn as [? [? ?]]. split. easy. now transitivity (hd (tl s)).
now apply FIX, _.
Qed.
Global Instance everyOther_inc `(inn : !IncreasingNonNegative s) : IncreasingNonNegative (everyOther s).
Proof.
revert s inn.
cofix FIX. intros s [? [? ?]].
constructor; simpl.
split. easy. now transitivity (hd (tl s)).
now apply FIX.
Qed.
End every_other.
Section mult.
Definition mult_Streams := zipWith (.*.).
Global Instance mult_Streams_dnn `(dnn1 : !DecreasingNonNegative s1) `(dnn2 : !DecreasingNonNegative s2) :
DecreasingNonNegative (mult_Streams s1 s2).
Proof.
revert s1 s2 dnn1 dnn2.
cofix FIX. intros s1 s2 [[? ?] ?] [[? ?] ?].
constructor; simpl.
split.
now apply nonneg_mult_compat.
now apply semirings.mult_le_compat.
now apply FIX.
Qed.
Global Instance mult_Streams_inc `(inn1 : !IncreasingNonNegative s1) `(inn2 : !IncreasingNonNegative s2) :
IncreasingNonNegative (mult_Streams s1 s2).
Proof .
revert s1 s2 inn1 inn2.
cofix FIX. intros s1 s2 [? ?] [? ?].
constructor; simpl.
split.
now apply nonneg_mult_compat.
now apply semirings.mult_le_compat.
now apply FIX.
Qed.
Global Instance: Proper ((=) ==> (=) ==> (=)) mult_Streams.
Proof. apply _. Qed.
End mult.
Section powers.
Context (a : A).
Definition powers_help : A → ∞A := iterate (.*a).
Definition powers : ∞A := powers_help 1.
Section with_nat_pow.
Context `{Naturals N} `{!NatPowSpec A N pw} (f : nat → N) `{!SemiRing_Morphism f}.
Lemma Str_nth_powers_help (n : nat) (c : A) : Str_nth n (powers_help c) = c * a ^ (f n).
Proof.
revert c.
induction n using peano_naturals.nat_induction; intros c; unfold Str_nth in *; simpl.
rewrite rings.preserves_0, nat_pow_0. ring.
rewrite rings.preserves_plus, rings.preserves_1.
rewrite nat_pow_S, IHn. ring.
Qed.
Lemma Str_nth_powers (n : nat) : Str_nth n powers = a ^ (f n).
Proof. unfold powers. rewrite Str_nth_powers_help. ring. Qed.
End with_nat_pow.
Section with_int_pow.
Context `{!Negate A} `{!DecRecip A} `{!DecField A} `{∀ x y : A, Decision (x = y)}
`{Integers Z} `{!IntPowSpec A Z pw} (f : nat → Z) `{!SemiRing_Morphism f}.
Lemma Str_nth_powers_help_int_pow (n : nat) (c : A) : Str_nth n (powers_help c) = c * a ^ (f n).
Proof. rewrite (Str_nth_powers_help id). unfold id. now rewrite int_pow_nat_pow. Qed.
Lemma Str_nth_powers_int_pow (n : nat) : Str_nth n powers = a ^ (f n).
Proof. unfold powers. rewrite Str_nth_powers_help_int_pow. ring. Qed.
End with_int_pow.
End powers.
Global Instance powers_help_proper: Proper ((=) ==> (=) ==> (=)) powers_help.
Proof.
intros ? ? E1 ? ? E2. apply stream_eq_Str_nth. intros n.
now rewrite 2!(Str_nth_powers_help _ id), E1, E2.
Qed.
Global Instance powers_proper: Proper ((=) ==> (=)) powers.
Proof.
intros ? ? E. apply stream_eq_Str_nth. intros n.
now rewrite 2!(Str_nth_powers _ id), E.
Qed.
Section increments.
Context (d:A).
Definition increments (x : A) : ∞A := iterate (+d) x.
Lemma Str_nth_increments (n : nat) (x : A) :
Str_nth n (increments x) = x + d * naturals_to_semiring nat A n.
Proof.
unfold increments. revert x.
induction n using peano_naturals.nat_induction; intros c; unfold Str_nth in *; simpl.
rewrite rings.preserves_0. now ring.
rewrite IHn, rings.preserves_plus, rings.preserves_1. now ring.
Qed.
End increments.
Section positives.
Definition positives_help : A → ∞A := increments 1.
Lemma Str_nth_positives_help (n : nat) (x : A) :
Str_nth n (positives_help x) = x + naturals_to_semiring nat A n.
Proof. unfold positives_help. rewrite Str_nth_increments. ring. Qed.
Definition positives : ∞A := positives_help 1.
Lemma Str_nth_positives (n : nat) :
Str_nth n positives = 1 + naturals_to_semiring nat A n.
Proof. unfold positives. now rewrite Str_nth_positives_help. Qed.
End positives.
Section factorials.
CoFixpoint factorials_help (n c : A) : ∞A := c ::: factorials_help (1 + n) (n * c).
Fixpoint fac_help (n : nat) (m c : A) : A :=
match n with
| O => c
| S n => (m + naturals_to_semiring nat A n) * fac_help n m c
end.
Lemma Str_nth_factorials_help (n : nat) (m c : A) :
Str_nth n (factorials_help m c) = fac_help n m c.
Proof.
revert m c.
induction n using peano_naturals.nat_induction; intros m c; unfold Str_nth in *; simpl.
ring.
rewrite IHn. clear IHn.
induction n using peano_naturals.nat_induction; simpl.
rewrite rings.preserves_0. now ring.
rewrite IHn, rings.preserves_plus, rings.preserves_1. now ring.
Qed.
Definition factorials := factorials_help 1 1.
Lemma Str_nth_factorials (n : nat) :
Str_nth n factorials = naturals_to_semiring nat A (fact n).
Proof.
unfold factorials.
rewrite Str_nth_factorials_help.
induction n using peano_naturals.nat_induction; simpl.
change (1 = naturals_to_semiring nat A 1).
now rewrite rings.preserves_1.
rewrite IHn.
setoid_rewrite rings.preserves_plus.
setoid_rewrite rings.preserves_mult. now ring.
Qed.
End factorials.
End series.
Section preservation.
Context `{SemiRingOrder A} `{SemiRingOrder B} `{!SemiRing_Morphism (f : A → B)}.
Lemma preserves_powers_help (a c : A) (n : nat) :
f (Str_nth n (powers_help a c)) = Str_nth n (powers_help (f a) (f c)).
Proof.
rewrite 2!(Str_nth_powers_help _ id).
rewrite rings.preserves_mult.
now rewrite preserves_nat_pow.
Qed.
Lemma preserves_powers (a : A) (n : nat) :
f (Str_nth n (powers a)) = Str_nth n (powers (f a)).
Proof.
rewrite 2!(Str_nth_powers _ id).
apply preserves_nat_pow.
Qed.
Lemma preserves_positives (n : nat) :
f (Str_nth n positives) = Str_nth n positives.
Proof.
rewrite 2!Str_nth_positives.
rewrite rings.preserves_plus, rings.preserves_1.
now rewrite <-(naturals.to_semiring_unique (f ∘ naturals_to_semiring nat A)).
Qed.
Lemma preserves_factorials (n : nat) :
f (Str_nth n factorials) = Str_nth n factorials.
Proof.
rewrite 2!Str_nth_factorials.
now rewrite <-(naturals.to_semiring_unique (f ∘ naturals_to_semiring nat A)).
Qed.
End preservation.