Theory Interval_Division_Real
chapter‹A Naive Interval Division for Real Intervals›
theory
Interval_Division_Real
imports
Interval_Division_Non_Zero
begin
text ‹
The theory @{theory "HOL-Library.Interval"} does not define a division operation on intervals.
Actually,
In the following we define division in a straight forward way. This is possible, as in HOL, the
property @{thm "division_ring_divide_zero"} holds. Therefore, we do not need to use, in the first
instance, extended interval analysis (e.g., based on the type @{type "ereal"}. As a consequence,
results obtained using this definition might differ from results obtained using definitions of
divisions using extended reals (e.g., \<^cite>‹"moore.ea:introduction:2009"›). ›
instantiation "interval" :: ("{linordered_field, real_normed_algebra,linear_continuum_topology}") inverse
begin
definition inverse_interval :: "'a interval ⇒ 'a interval"
where "inverse_interval a = mk_interval ( 1 / (upper a), 1 / (lower a))"
definition divide_interval :: "'a interval ⇒ 'a interval ⇒ 'a interval"
where "divide_interval a b = inverse b * a"
instance ..
end
interpretation interval_division_inverse divide inverse
apply (unfold_locales)
subgoal by (simp add: inverse_interval_def)
subgoal by(simp add: divide_interval_def)
done
lemma width_of_reciprocal_interval_bound_real:
fixes Y :: "real interval"
assumes ‹¬ 0 ∈⇩i Y›
shows ‹interval_of(width ((interval_of 1) / Y)) ≤
(abs_interval((interval_of 1) / Y) * abs_interval((interval_of 1) / Y)) * interval_of(width Y)›
proof(cases "Y" rule:interval_linorder_case_split[of _ 0 "λ Y. interval_of(width ((interval_of 1) / Y)) ≤
(abs_interval((interval_of 1) / Y)) * (abs_interval((interval_of 1) / Y)) * interval_of(width Y)" ])
case LeftOf
have a0: ‹lower Y ≤ upper Y› using lower_le_upper by simp
have a1: ‹interval_of(width ((interval_of 1) / Y)) = Interval( 1 / lower Y - 1 / upper Y, 1 / lower Y - 1 / upper Y) ›
using assms interval_of_width by blast
have a2: ‹(abs_interval((interval_of 1) / Y) * abs_interval((interval_of 1) / Y)) * interval_of(width Y) = Interval((upper Y - lower Y) * 1 / ¦lower Y¦ * 1 / ¦lower Y¦, (upper Y - lower Y) * 1 / ¦upper Y¦ * 1 / ¦upper Y¦)›
proof -
have b0: ‹1 / ¦lower Y¦ ≤ 1 / ¦upper Y¦› using assms a0 LeftOf
by (smt (verit, best) frac_le)
have b1: ‹0 ≤ upper Y - lower Y›
using assms LeftOf by simp
moreover have b2: ‹(abs_interval((interval_of 1) / Y) * abs_interval((interval_of 1) / Y)) * interval_of(width Y) = Interval(1/¦lower Y¦, 1/¦upper Y¦) * Interval(1/¦lower Y¦, 1/¦upper Y¦) * Interval(upper Y - lower Y, upper Y - lower Y)›
using assms LeftOf abs_neg[of Y] width_expanded[of Y] by simp
moreover have b3: ‹... = Interval(Min { (1 /¦lower Y¦ * 1 /¦lower Y¦), (1 /¦lower Y¦ * 1 /¦upper Y¦), (1 /¦upper Y¦ * 1 /¦lower Y¦), (1 /¦upper Y¦ * 1 /¦upper Y¦)}, Max { (1 /¦lower Y¦ * 1 /¦lower Y¦), (1 /¦lower Y¦ * 1 /¦upper Y¦), (1 /¦upper Y¦ * 1 /¦lower Y¦), (1 /¦upper Y¦ * 1 /¦upper Y¦)}) * Interval(upper Y - lower Y, upper Y - lower Y) ›
using assms a0 LeftOf interval_interval_times[of "Interval(1/¦lower Y¦, 1/¦upper Y¦)" "Interval(1/¦lower Y¦, 1/¦upper Y¦)"]
using lower_bounds upper_bounds b0 by simp
have b4: ‹Min {(1 /¦lower Y¦ * 1 /¦lower Y¦), (1 /¦lower Y¦ * 1 /¦upper Y¦), (1 /¦upper Y¦ * 1 /¦lower Y¦), (1 /¦upper Y¦ * 1 /¦upper Y¦)} = (1 /¦lower Y¦ * 1 /¦lower Y¦)›
using assms a0 LeftOf upper_leq_lower_div
apply(simp add: min_def, safe)
apply (smt (z3) divide_divide_eq_left' divide_less_cancel divide_minus_right nonzero_minus_divide_divide)
apply argo+
by (smt (z3) a0 divide_divide_eq_left' divide_le_cancel divide_nonneg_neg frac_le minus_divide_right mult.commute mult_left_mono mult_minus_left)
have b5: ‹Max {(1 /¦lower Y¦ * 1 /¦lower Y¦), (1 /¦lower Y¦ * 1 /¦upper Y¦), (1 /¦upper Y¦ * 1 /¦lower Y¦), (1 /¦upper Y¦ * 1 /¦upper Y¦)} = (1 /¦upper Y¦ * 1 /¦upper Y¦)›
using assms a0 LeftOf upper_leq_lower_div
apply (simp add: max_def, safe)
apply (smt (verit, del_insts) frac_le mult_mono_nonpos_nonpos mult_neg_neg)
apply argo
apply argo
apply (smt (z3) b0 divide_divide_eq_left' divide_less_cancel minus_divide_right nonzero_minus_divide_divide)
apply (smt (verit, best) division_leq mult_mono_nonpos_nonpos not_real_square_gt_zero)
by argo+
moreover have ‹(abs_interval((interval_of 1) / Y) * abs_interval((interval_of 1) / Y)) * interval_of(width Y) = Interval(1 /¦lower Y¦ * 1 /¦lower Y¦, 1 /¦upper Y¦ * 1 /¦upper Y¦) * Interval(upper Y - lower Y, upper Y - lower Y)›
using b2 b3 b4 b5 by presburger
moreover have ‹... = Interval((upper Y - lower Y) * 1 /¦lower Y¦ * 1 /¦lower Y¦, (upper Y - lower Y) * 1 /¦upper Y¦ * 1 /¦upper Y¦)›
using assms a0 LeftOf b4 b5 interval_times_scalar_pos_r[of "upper Y - lower Y" "Interval(1 /¦lower Y¦ * 1 /¦lower Y¦, 1 /¦upper Y¦ * 1 /¦upper Y¦)"]
unfolding interval_of_def by simp
ultimately show ?thesis by metis
qed
have a3: ‹(upper Y - lower Y) * 1 /¦lower Y¦ * 1 /¦lower Y¦ ≤ 1 / lower Y - 1 / upper Y ›
proof -
have "(1 / lower Y) - (1 / upper Y) = (upper Y - lower Y) / (lower Y * upper Y)"
using assms a0 LeftOf
by (smt (verit) diff_divide_distrib nonzero_divide_mult_cancel_left nonzero_divide_mult_cancel_right)
moreover have ‹(upper Y - lower Y) * 1 /¦lower Y¦ * 1 /¦lower Y¦ = (upper Y - lower Y) / ¦lower Y¦^2›
using assms LeftOf by (simp add: power2_eq_square)
moreover have ‹((upper Y - lower Y) / ¦lower Y¦^2) ≤ (upper Y - lower Y) / (lower Y * upper Y)›
using assms a0 LeftOf
by (smt (verit) frac_le minus_mult_minus mult_left_mono_neg mult_neg_neg power2_eq_square)
ultimately show ?thesis by metis
qed
have a4: ‹1 / lower Y - 1 / upper Y ≤ (upper Y - lower Y) * 1 /¦upper Y¦ * 1 /¦upper Y¦›
proof -
have "(1 / lower Y) - (1 / upper Y) = (upper Y - lower Y) / (lower Y * upper Y)"
using assms a0 LeftOf
by (smt (verit) diff_divide_distrib nonzero_divide_mult_cancel_left nonzero_divide_mult_cancel_right)
moreover have ‹(upper Y - lower Y) * 1 /¦upper Y¦ * 1 /¦upper Y¦ = (upper Y - lower Y) / ¦upper Y¦^2›
using assms LeftOf by (simp add: power2_eq_square)
moreover have ‹(upper Y - lower Y) / (lower Y * upper Y) ≤ ((upper Y - lower Y) / ¦upper Y¦^2) ›
using assms LeftOf
by (simp add: frac_le power2_eq_square zero_less_mult_iff)
ultimately show ?thesis by metis
qed
have ‹Interval( 1 / lower Y - 1 / upper Y, 1 / lower Y - 1 / upper Y) ≤ Interval((upper Y - lower Y) * 1 /¦lower Y¦ * 1 /¦lower Y¦, (upper Y - lower Y) * 1 /¦upper Y¦ * 1 /¦upper Y¦)›
using a3 a4 unfolding less_eq_interval_def by simp
then show ?case using a1 a2 a3 a4 by simp
next
case Including
then show ?case using assms by simp
next
case RightOf
have a0: ‹lower Y ≤ upper Y› using lower_le_upper by simp
have a1: ‹interval_of(width ((interval_of 1) / Y)) = Interval( 1 / lower Y - 1 / upper Y, 1 / lower Y - 1 / upper Y) ›
using assms interval_of_width by blast
have a2: ‹(abs_interval((interval_of 1) / Y) * abs_interval((interval_of 1) / Y)) * interval_of(width Y) = Interval((upper Y - lower Y) * 1 /upper Y * 1 /upper Y, (upper Y - lower Y) * 1 /lower Y * 1 /lower Y)›
proof -
have b0: ‹0 ≤ upper Y - lower Y›
using assms RightOf by simp
moreover have b1: ‹(abs_interval((interval_of 1) / Y) * abs_interval((interval_of 1) / Y)) * interval_of(width Y) = Interval(1/upper Y, 1/lower Y) * Interval(1/upper Y, 1/lower Y) * Interval(upper Y - lower Y, upper Y - lower Y)›
using assms RightOf abs_pos[of Y] width_expanded[of Y] by simp
moreover have b2: ‹... = Interval(Min { (1 /upper Y * 1 /upper Y), (1 /upper Y * 1 /lower Y), (1 /lower Y * 1 /upper Y), (1 /lower Y * 1 /lower Y)}, Max { (1 /upper Y * 1 /upper Y), (1 /upper Y * 1 /lower Y), (1 /lower Y * 1 /upper Y), (1 /lower Y * 1 /lower Y)}) * Interval(upper Y - lower Y, upper Y - lower Y) ›
using assms RightOf upper_leq_lower_div interval_interval_times[of "Interval(1 /upper Y, 1 / lower Y)" "Interval(1 /upper Y, 1 / lower Y)"]
by fastforce
have b3: ‹Min {(1 /upper Y * 1 /upper Y), (1 /upper Y * 1 /lower Y), (1 /lower Y * 1 /upper Y), (1 /lower Y * 1 /lower Y)} = (1 /upper Y * 1 /upper Y)›
using assms a0 RightOf upper_leq_lower_div
apply(simp add: min_def, safe)
apply (smt (verit, ccfv_SIG) frac_le mult_less_cancel_left_pos zero_less_mult_iff)
apply argo+
by (simp add: frac_le)
have b4: ‹Max { (1 /upper Y * 1 /upper Y), (1 /upper Y * 1 /lower Y), (1 /lower Y * 1 /upper Y), (1 /lower Y * 1 /lower Y)} = (1 /lower Y * 1 /lower Y)›
using assms a0 RightOf upper_leq_lower_div
apply (simp add: max_def, safe)
subgoal
using frac_le le_numeral_extra(4) less_numeral_extra(3) linordered_nonzero_semiring_class.zero_le_one
mult_mono' not_real_square_gt_zero order_less_imp_le by metis
apply argo+
apply (simp add: frac_le)
subgoal
using frac_le linordered_nonzero_semiring_class.zero_le_one mult_mono' mult_pos_pos
order.refl order_less_imp_le by meson
by argo+
moreover have ‹(abs_interval((interval_of 1) / Y) * abs_interval((interval_of 1) / Y)) * interval_of(width Y) = Interval(1 /upper Y * 1 /upper Y, 1 /lower Y * 1 /lower Y) * Interval(upper Y - lower Y, upper Y - lower Y)›
using b1 b2 b3 b4 by presburger
moreover have ‹... = Interval((upper Y - lower Y) * 1 /upper Y * 1 /upper Y, (upper Y - lower Y) * 1 /lower Y * 1 /lower Y)›
using assms RightOf b0 interval_times_scalar_pos_r[of "upper Y - lower Y" "Interval(1 /upper Y * 1 /upper Y, 1 /lower Y * 1 /lower Y)"]
unfolding interval_of_def
by (smt (verit, del_insts) divide_cancel_left divide_nonneg_nonneg frac_le interval_times_scalar_pos_r lower_bounds nonzero_divide_mult_cancel_right times_divide_eq_right upper_bounds width_def width_expanded)
ultimately show ?thesis by simp
qed
have a3: ‹1 /upper Y * 1 /upper Y * (upper Y - lower Y) ≤ 1 / lower Y - 1 / upper Y›
proof -
have b0: ‹0 < upper Y› using assms a0 RightOf by argo
then have "(1 / lower Y) - (1 / upper Y) = (upper Y - lower Y) / (lower Y * upper Y)"
using assms RightOf b0 by (simp add: diff_divide_distrib)
then have b1: ‹((1/ upper Y) * (1/ upper Y) * (upper Y - lower Y) * (lower Y * upper Y) ≤ (upper Y - lower Y)) = ((1/ upper Y) * (1/ upper Y) * (upper Y - lower Y) ≤ 1 / lower Y - 1 / upper Y)›
using assms RightOf b0 by (simp add: pos_le_divide_eq)
then have b2: ‹((upper Y - lower Y) * lower Y / upper Y) ≤ upper Y - lower Y›
using assms a0 RightOf b0 by (smt (verit) mult_left_less_imp_less pos_less_divide_eq)
moreover have ‹(upper Y - lower Y) * lower Y ≤ (upper Y - lower Y) * upper Y›
using assms RightOf b0 calculation pos_divide_le_eq by blast
show ?thesis using assms b0 b1 b2 by force
qed
have a4: ‹1 / lower Y - 1 / upper Y ≤ 1 /lower Y * 1 /lower Y * (upper Y - lower Y)›
proof -
have b0: ‹0 < upper Y› using assms a0 RightOf by argo
then have "(1 / lower Y) - (1 / upper Y) = (upper Y - lower Y) / (lower Y * upper Y)"
using assms RightOf b0 by (simp add: diff_divide_distrib)
then have b1: ‹(upper Y - lower Y ≤ (1/ lower Y) * (1/ lower Y) * (upper Y - lower Y) * (lower Y * upper Y)) = (1 / lower Y - 1 / upper Y ≤ ((1/ lower Y) * (1/ lower Y) * (upper Y - lower Y) ))›
using assms RightOf b0 by (simp add: pos_divide_le_eq)
then have b2: ‹upper Y - lower Y ≤ ((upper Y - lower Y) * upper Y / lower Y)›
using assms a0 RightOf b0 by (smt (verit) division_leq mult_pos_pos nonzero_mult_div_cancel_right)
moreover have ‹(upper Y - lower Y) * lower Y ≤ (upper Y - lower Y) * upper Y›
using calculation pos_divide_le_eq by (simp add: RightOf pos_le_divide_eq)
show ?thesis using assms b0 b1 b2 RightOf by simp
qed
have ‹Interval( 1 / lower Y - 1 / upper Y, 1 / lower Y - 1 / upper Y) ≤ Interval((upper Y - lower Y) * 1 /upper Y * 1 /upper Y, (upper Y - lower Y) * 1 /lower Y * 1 /lower Y)›
using a3 a4 unfolding less_eq_interval_def by simp
then show ?case using a1 a2 a3 a4 by simp
qed
end