(** * Properties of [Qmult] *)
(** Multiplication is associative: *)

(* Specifications: *)
Theorem Qmult_assoc : forall n m p, n*(m*p)==(n*m)*p.
(** multiplication and zero *)
Lemma Qmult_0_l : forall x , 0*x == 0.
Lemma Qmult_0_r : forall x , x*0 == 0.
(** [1] is a neutral element for multiplication: *)
Lemma Qmult_1_l : forall n, 1*n == n.
Theorem Qmult_1_r : forall n, n*1==n.
(** Commutativity of multiplication *)
Theorem Qmult_comm : forall x y, x*y==y*x.
(** Distributivity over [Qadd] *)
Theorem Qmult_plus_distr_r : forall x y z, x*(y+z)==(x*y)+(x*z).
Theorem Qmult_plus_distr_l : forall x y z, (x+y)*z==(x*z)+(y*z).
(** Integrality *)
Theorem Qmult_integral : forall x y, x*y==0 -> x==0 \/ y==0.
Theorem Qmult_integral_l : forall x y, ~ x == 0 -> x*y == 0 -> y == 0.
(** * inject_Z is a ring homomorphism: *)
Lemma inject_Z_plus (x y: Z): inject_Z (x + y) = inject_Z x + inject_Z y.
Lemma inject_Z_mult (x y: Z): inject_Z (x * y) = inject_Z x * inject_Z y.
Theorem Qmult_inv_r : forall x, ~ x == 0 -> x*(/x) == 1.
Lemma Qinv_mult_distr : forall p q, / (p * q) == /p * /q.
Lemma Qinv_pos: forall (a b : positive),
/ (Z.pos b # a) == Z.pos a # b.
Lemma Qinv_neg: forall (a b : positive),
/ (Z.neg b # a) == Z.neg a # b.
Theorem Qdiv_mult_l : forall x y, ~ y == 0 -> (x*y)/y == x.
Theorem Qmult_div_r : forall x y, ~ y == 0 -> y*(x/y) == x.
Lemma Qinv_plus_distr : forall a b c, ((a # c) + (b # c) == (a+b) # c)%Q.
Lemma Qinv_minus_distr : forall a b c, (a # c) + - (b # c) == (a-b) # c.
(** Injectivity of Qmult (requires theory about Qinv above): *)
Lemma Qmult_inj_r (x y z: Q): ~ z == 0 -> (x * z == y * z <-> x == y).
Lemma Qmult_inj_l (x y z: Q): ~ z == 0 -> (z * x == z * y <-> x == y).
(** * Reduction and construction of Q *)
(** ** Removal/introduction of common factor in both numerator and denominator. *)
Lemma Qreduce_l : forall (a : Z) (b z : positive),
(Zpos z)*a # z*b == a#b.
Lemma Qreduce_r : forall (a : Z) (b z : positive),
a*(Zpos z) # b*z == a#b.
Lemma Qreduce_num_l : forall (a b : positive),
Z.pos a # a * b == (1 # b).
Lemma Qreduce_num_r : forall (a b : positive),
Z.pos b # a * b == (1 # a).
Lemma Qreduce_den_l : forall (a : positive) (b : Z),
Z.pos a * b # a == (b # 1).
Lemma Qreduce_den_r : forall (a : Z) (b : positive),
a * Z.pos b # b == (a # 1).
Lemma Qreduce_den_inject_Z_l : forall (a : positive) (b : Z),
(Z.pos a * b # a == inject_Z b)%Q.
Lemma Qreduce_den_inject_Z_r : forall (a : Z) (b : positive),
a * Z.pos b # b == inject_Z a.
Lemma Qreduce_zero: forall (d : positive),
(0#d == 0)%Q.