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: Plus.v 9750 2007-04-06 00:58:14Z letouzey $ i*)
11
(** Properties of addition. [add] is defined in [Init/Peano.v] as:
13
Fixpoint plus (n m:nat) {struct n} : nat :=
18
where "n + m" := (plus n m) : nat_scope.
25
Open Local Scope nat_scope.
27
Implicit Types m n p q : nat.
29
(** * Zero is neutral *)
31
Lemma plus_0_l : forall n, 0 + n = n.
36
Lemma plus_0_r : forall n, n + 0 = n.
38
intro; symmetry in |- *; apply plus_n_O.
41
(** * Commutativity *)
43
Lemma plus_comm : forall n m, n + m = m + n.
45
intros n m; elim n; simpl in |- *; auto with arith.
46
intros y H; elim (plus_n_Sm m y); auto with arith.
48
Hint Immediate plus_comm: arith v62.
50
(** * Associativity *)
52
Lemma plus_Snm_nSm : forall n m, S n + m = n + S m.
56
rewrite (plus_comm n m).
57
rewrite (plus_comm n (S m)).
61
Lemma plus_assoc : forall n m p, n + (m + p) = n + m + p.
63
intros n m p; elim n; simpl in |- *; auto with arith.
65
Hint Resolve plus_assoc: arith v62.
67
Lemma plus_permute : forall n m p, n + (m + p) = m + (n + p).
69
intros; rewrite (plus_assoc m n p); rewrite (plus_comm m n); auto with arith.
72
Lemma plus_assoc_reverse : forall n m p, n + m + p = n + (m + p).
76
Hint Resolve plus_assoc_reverse: arith v62.
78
(** * Simplification *)
80
Lemma plus_reg_l : forall n m p, p + n = p + m -> n = m.
82
intros m p n; induction n; simpl in |- *; auto with arith.
85
Lemma plus_le_reg_l : forall n m p, p + n <= p + m -> n <= m.
87
induction p; simpl in |- *; auto with arith.
90
Lemma plus_lt_reg_l : forall n m p, p + n < p + m -> n < m.
92
induction p; simpl in |- *; auto with arith.
95
(** * Compatibility with order *)
97
Lemma plus_le_compat_l : forall n m p, n <= m -> p + n <= p + m.
99
induction p; simpl in |- *; auto with arith.
101
Hint Resolve plus_le_compat_l: arith v62.
103
Lemma plus_le_compat_r : forall n m p, n <= m -> n + p <= m + p.
105
induction 1; simpl in |- *; auto with arith.
107
Hint Resolve plus_le_compat_r: arith v62.
109
Lemma le_plus_l : forall n m, n <= n + m.
111
induction n; simpl in |- *; auto with arith.
113
Hint Resolve le_plus_l: arith v62.
115
Lemma le_plus_r : forall n m, m <= n + m.
117
intros n m; elim n; simpl in |- *; auto with arith.
119
Hint Resolve le_plus_r: arith v62.
121
Theorem le_plus_trans : forall n m p, n <= m -> n <= m + p.
123
intros; apply le_trans with (m := m); auto with arith.
125
Hint Resolve le_plus_trans: arith v62.
127
Theorem lt_plus_trans : forall n m p, n < m -> n < m + p.
129
intros; apply lt_le_trans with (m := m); auto with arith.
131
Hint Immediate lt_plus_trans: arith v62.
133
Lemma plus_lt_compat_l : forall n m p, n < m -> p + n < p + m.
135
induction p; simpl in |- *; auto with arith.
137
Hint Resolve plus_lt_compat_l: arith v62.
139
Lemma plus_lt_compat_r : forall n m p, n < m -> n + p < m + p.
141
intros n m p H; rewrite (plus_comm n p); rewrite (plus_comm m p).
142
elim p; auto with arith.
144
Hint Resolve plus_lt_compat_r: arith v62.
146
Lemma plus_le_compat : forall n m p q, n <= m -> p <= q -> n + p <= m + q.
149
elim H; simpl in |- *; auto with arith.
152
Lemma plus_le_lt_compat : forall n m p q, n <= m -> p < q -> n + p < m + q.
154
unfold lt in |- *. intros. change (S n + p <= m + q) in |- *. rewrite plus_Snm_nSm.
155
apply plus_le_compat; assumption.
158
Lemma plus_lt_le_compat : forall n m p q, n < m -> p <= q -> n + p < m + q.
160
unfold lt in |- *. intros. change (S n + p <= m + q) in |- *. apply plus_le_compat; assumption.
163
Lemma plus_lt_compat : forall n m p q, n < m -> p < q -> n + p < m + q.
165
intros. apply plus_lt_le_compat. assumption.
166
apply lt_le_weak. assumption.
169
(** * Inversion lemmas *)
171
Lemma plus_is_O : forall n m, n + m = 0 -> n = 0 /\ m = 0.
173
intro m; destruct m as [| n]; auto.
174
intros. discriminate H.
177
Definition plus_is_one :
178
forall m n, m + n = 1 -> {m = 0 /\ n = 1} + {m = 1 /\ n = 0}.
180
intro m; destruct m as [| n]; auto.
183
simpl in H. discriminate H.
186
(** * Derived properties *)
188
Lemma plus_permute_2_in_4 : forall n m p q, n + m + (p + q) = n + p + (m + q).
191
rewrite <- (plus_assoc m n (p + q)). rewrite (plus_assoc n p q).
192
rewrite (plus_comm n p). rewrite <- (plus_assoc p n q). apply plus_assoc.
195
(** * Tail-recursive plus *)
197
(** [tail_plus] is an alternative definition for [plus] which is
198
tail-recursive, whereas [plus] is not. This can be useful
199
when extracting programs. *)
201
Fixpoint tail_plus n m {struct n} : nat :=
204
| S n => tail_plus n (S m)
207
Lemma plus_tail_plus : forall n m, n + m = tail_plus n m.
208
induction n as [| n IHn]; simpl in |- *; auto.
209
intro m; rewrite <- IHn; simpl in |- *; auto.
212
(** * Discrimination *)
214
Lemma succ_plus_discr : forall n m, n <> S (plus m n).
216
intros n m; induction n as [|n IHn].
218
intro H; apply IHn; apply eq_add_S; rewrite H; rewrite <- plus_n_Sm;
222
Lemma n_SSn : forall n, n <> S (S n).
224
intro n; exact (succ_plus_discr n 1).
227
Lemma n_SSSn : forall n, n <> S (S (S n)).
229
intro n; exact (succ_plus_discr n 2).
232
Lemma n_SSSSn : forall n, n <> S (S (S (S n))).
234
intro n; exact (succ_plus_discr n 3).