src/HOL/Analysis/Cauchy_Integral_Theorem.thy
author paulson <lp15@cam.ac.uk>
Mon Jun 04 21:00:12 2018 +0100 (14 months ago)
changeset 68371 17c3b22a9575
parent 68359 8cd3d0305269
child 68403 223172b97d0b
permissions -rw-r--r--
more tweaks of Cauchy
     1 section \<open>Complex path integrals and Cauchy's integral theorem\<close>
     2 
     3 text\<open>By John Harrison et al.  Ported from HOL Light by L C Paulson (2015)\<close>
     4 
     5 theory Cauchy_Integral_Theorem
     6 imports Complex_Transcendental Weierstrass_Theorems Ordered_Euclidean_Space
     7 begin
     8 
     9 subsection\<open>Homeomorphisms of arc images\<close>
    10 
    11 lemma homeomorphism_arc:
    12   fixes g :: "real \<Rightarrow> 'a::t2_space"
    13   assumes "arc g"
    14   obtains h where "homeomorphism {0..1} (path_image g) g h"
    15 using assms by (force simp: arc_def homeomorphism_compact path_def path_image_def)
    16 
    17 lemma homeomorphic_arc_image_interval:
    18   fixes g :: "real \<Rightarrow> 'a::t2_space" and a::real
    19   assumes "arc g" "a < b"
    20   shows "(path_image g) homeomorphic {a..b}"
    21 proof -
    22   have "(path_image g) homeomorphic {0..1::real}"
    23     by (meson assms(1) homeomorphic_def homeomorphic_sym homeomorphism_arc)
    24   also have "\<dots> homeomorphic {a..b}"
    25     using assms by (force intro: homeomorphic_closed_intervals_real)
    26   finally show ?thesis .
    27 qed
    28 
    29 lemma homeomorphic_arc_images:
    30   fixes g :: "real \<Rightarrow> 'a::t2_space" and h :: "real \<Rightarrow> 'b::t2_space"
    31   assumes "arc g" "arc h"
    32   shows "(path_image g) homeomorphic (path_image h)"
    33 proof -
    34   have "(path_image g) homeomorphic {0..1::real}"
    35     by (meson assms homeomorphic_def homeomorphic_sym homeomorphism_arc)
    36   also have "\<dots> homeomorphic (path_image h)"
    37     by (meson assms homeomorphic_def homeomorphism_arc)
    38   finally show ?thesis .
    39 qed
    40 
    41 lemma path_connected_arc_complement:
    42   fixes \<gamma> :: "real \<Rightarrow> 'a::euclidean_space"
    43   assumes "arc \<gamma>" "2 \<le> DIM('a)"
    44   shows "path_connected(- path_image \<gamma>)"
    45 proof -
    46   have "path_image \<gamma> homeomorphic {0..1::real}"
    47     by (simp add: assms homeomorphic_arc_image_interval)
    48   then
    49   show ?thesis
    50     apply (rule path_connected_complement_homeomorphic_convex_compact)
    51       apply (auto simp: assms)
    52     done
    53 qed
    54 
    55 lemma connected_arc_complement:
    56   fixes \<gamma> :: "real \<Rightarrow> 'a::euclidean_space"
    57   assumes "arc \<gamma>" "2 \<le> DIM('a)"
    58   shows "connected(- path_image \<gamma>)"
    59   by (simp add: assms path_connected_arc_complement path_connected_imp_connected)
    60 
    61 lemma inside_arc_empty:
    62   fixes \<gamma> :: "real \<Rightarrow> 'a::euclidean_space"
    63   assumes "arc \<gamma>"
    64     shows "inside(path_image \<gamma>) = {}"
    65 proof (cases "DIM('a) = 1")
    66   case True
    67   then show ?thesis
    68     using assms connected_arc_image connected_convex_1_gen inside_convex by blast
    69 next
    70   case False
    71   show ?thesis
    72   proof (rule inside_bounded_complement_connected_empty)
    73     show "connected (- path_image \<gamma>)"
    74       apply (rule connected_arc_complement [OF assms])
    75       using False
    76       by (metis DIM_ge_Suc0 One_nat_def Suc_1 not_less_eq_eq order_class.order.antisym)
    77     show "bounded (path_image \<gamma>)"
    78       by (simp add: assms bounded_arc_image)
    79   qed
    80 qed
    81 
    82 lemma inside_simple_curve_imp_closed:
    83   fixes \<gamma> :: "real \<Rightarrow> 'a::euclidean_space"
    84     shows "\<lbrakk>simple_path \<gamma>; x \<in> inside(path_image \<gamma>)\<rbrakk> \<Longrightarrow> pathfinish \<gamma> = pathstart \<gamma>"
    85   using arc_simple_path  inside_arc_empty by blast
    86 
    87     
    88 subsection \<open>Piecewise differentiable functions\<close>
    89 
    90 definition piecewise_differentiable_on
    91            (infixr "piecewise'_differentiable'_on" 50)
    92   where "f piecewise_differentiable_on i  \<equiv>
    93            continuous_on i f \<and>
    94            (\<exists>S. finite S \<and> (\<forall>x \<in> i - S. f differentiable (at x within i)))"
    95 
    96 lemma piecewise_differentiable_on_imp_continuous_on:
    97     "f piecewise_differentiable_on S \<Longrightarrow> continuous_on S f"
    98 by (simp add: piecewise_differentiable_on_def)
    99 
   100 lemma piecewise_differentiable_on_subset:
   101     "f piecewise_differentiable_on S \<Longrightarrow> T \<le> S \<Longrightarrow> f piecewise_differentiable_on T"
   102   using continuous_on_subset
   103   unfolding piecewise_differentiable_on_def
   104   apply safe
   105   apply (blast elim: continuous_on_subset)
   106   by (meson Diff_iff differentiable_within_subset subsetCE)
   107 
   108 lemma differentiable_on_imp_piecewise_differentiable:
   109   fixes a:: "'a::{linorder_topology,real_normed_vector}"
   110   shows "f differentiable_on {a..b} \<Longrightarrow> f piecewise_differentiable_on {a..b}"
   111   apply (simp add: piecewise_differentiable_on_def differentiable_imp_continuous_on)
   112   apply (rule_tac x="{a,b}" in exI, simp add: differentiable_on_def)
   113   done
   114 
   115 lemma differentiable_imp_piecewise_differentiable:
   116     "(\<And>x. x \<in> S \<Longrightarrow> f differentiable (at x within S))
   117          \<Longrightarrow> f piecewise_differentiable_on S"
   118 by (auto simp: piecewise_differentiable_on_def differentiable_imp_continuous_on differentiable_on_def
   119          intro: differentiable_within_subset)
   120 
   121 lemma piecewise_differentiable_const [iff]: "(\<lambda>x. z) piecewise_differentiable_on S"
   122   by (simp add: differentiable_imp_piecewise_differentiable)
   123 
   124 lemma piecewise_differentiable_compose:
   125     "\<lbrakk>f piecewise_differentiable_on S; g piecewise_differentiable_on (f ` S);
   126       \<And>x. finite (S \<inter> f-`{x})\<rbrakk>
   127       \<Longrightarrow> (g \<circ> f) piecewise_differentiable_on S"
   128   apply (simp add: piecewise_differentiable_on_def, safe)
   129   apply (blast intro: continuous_on_compose2)
   130   apply (rename_tac A B)
   131   apply (rule_tac x="A \<union> (\<Union>x\<in>B. S \<inter> f-`{x})" in exI)
   132   apply (blast intro!: differentiable_chain_within)
   133   done
   134 
   135 lemma piecewise_differentiable_affine:
   136   fixes m::real
   137   assumes "f piecewise_differentiable_on ((\<lambda>x. m *\<^sub>R x + c) ` S)"
   138   shows "(f \<circ> (\<lambda>x. m *\<^sub>R x + c)) piecewise_differentiable_on S"
   139 proof (cases "m = 0")
   140   case True
   141   then show ?thesis
   142     unfolding o_def
   143     by (force intro: differentiable_imp_piecewise_differentiable differentiable_const)
   144 next
   145   case False
   146   show ?thesis
   147     apply (rule piecewise_differentiable_compose [OF differentiable_imp_piecewise_differentiable])
   148     apply (rule assms derivative_intros | simp add: False vimage_def real_vector_affinity_eq)+
   149     done
   150 qed
   151 
   152 lemma piecewise_differentiable_cases:
   153   fixes c::real
   154   assumes "f piecewise_differentiable_on {a..c}"
   155           "g piecewise_differentiable_on {c..b}"
   156            "a \<le> c" "c \<le> b" "f c = g c"
   157   shows "(\<lambda>x. if x \<le> c then f x else g x) piecewise_differentiable_on {a..b}"
   158 proof -
   159   obtain S T where st: "finite S" "finite T"
   160                and fd: "\<And>x. x \<in> {a..c} - S \<Longrightarrow> f differentiable at x within {a..c}"
   161                and gd: "\<And>x. x \<in> {c..b} - T \<Longrightarrow> g differentiable at x within {c..b}"
   162     using assms
   163     by (auto simp: piecewise_differentiable_on_def)
   164   have finabc: "finite ({a,b,c} \<union> (S \<union> T))"
   165     by (metis \<open>finite S\<close> \<open>finite T\<close> finite_Un finite_insert finite.emptyI)
   166   have "continuous_on {a..c} f" "continuous_on {c..b} g"
   167     using assms piecewise_differentiable_on_def by auto
   168   then have "continuous_on {a..b} (\<lambda>x. if x \<le> c then f x else g x)"
   169     using continuous_on_cases [OF closed_real_atLeastAtMost [of a c],
   170                                OF closed_real_atLeastAtMost [of c b],
   171                                of f g "\<lambda>x. x\<le>c"]  assms
   172     by (force simp: ivl_disj_un_two_touch)
   173   moreover
   174   { fix x
   175     assume x: "x \<in> {a..b} - ({a,b,c} \<union> (S \<union> T))"
   176     have "(\<lambda>x. if x \<le> c then f x else g x) differentiable at x within {a..b}" (is "?diff_fg")
   177     proof (cases x c rule: le_cases)
   178       case le show ?diff_fg
   179       proof (rule differentiable_transform_within [where d = "dist x c"])
   180         have "f differentiable at x"
   181           using x le fd [of x] at_within_interior [of x "{a..c}"] by simp
   182         then show "f differentiable at x within {a..b}"
   183           by (simp add: differentiable_at_withinI)
   184       qed (use x le st dist_real_def in auto)
   185     next
   186       case ge show ?diff_fg
   187       proof (rule differentiable_transform_within [where d = "dist x c"])
   188         have "g differentiable at x"
   189           using x ge gd [of x] at_within_interior [of x "{c..b}"] by simp
   190         then show "g differentiable at x within {a..b}"
   191           by (simp add: differentiable_at_withinI)
   192       qed (use x ge st dist_real_def in auto)
   193     qed
   194   }
   195   then have "\<exists>S. finite S \<and>
   196                  (\<forall>x\<in>{a..b} - S. (\<lambda>x. if x \<le> c then f x else g x) differentiable at x within {a..b})"
   197     by (meson finabc)
   198   ultimately show ?thesis
   199     by (simp add: piecewise_differentiable_on_def)
   200 qed
   201 
   202 lemma piecewise_differentiable_neg:
   203     "f piecewise_differentiable_on S \<Longrightarrow> (\<lambda>x. -(f x)) piecewise_differentiable_on S"
   204   by (auto simp: piecewise_differentiable_on_def continuous_on_minus)
   205 
   206 lemma piecewise_differentiable_add:
   207   assumes "f piecewise_differentiable_on i"
   208           "g piecewise_differentiable_on i"
   209     shows "(\<lambda>x. f x + g x) piecewise_differentiable_on i"
   210 proof -
   211   obtain S T where st: "finite S" "finite T"
   212                        "\<forall>x\<in>i - S. f differentiable at x within i"
   213                        "\<forall>x\<in>i - T. g differentiable at x within i"
   214     using assms by (auto simp: piecewise_differentiable_on_def)
   215   then have "finite (S \<union> T) \<and> (\<forall>x\<in>i - (S \<union> T). (\<lambda>x. f x + g x) differentiable at x within i)"
   216     by auto
   217   moreover have "continuous_on i f" "continuous_on i g"
   218     using assms piecewise_differentiable_on_def by auto
   219   ultimately show ?thesis
   220     by (auto simp: piecewise_differentiable_on_def continuous_on_add)
   221 qed
   222 
   223 lemma piecewise_differentiable_diff:
   224     "\<lbrakk>f piecewise_differentiable_on S;  g piecewise_differentiable_on S\<rbrakk>
   225      \<Longrightarrow> (\<lambda>x. f x - g x) piecewise_differentiable_on S"
   226   unfolding diff_conv_add_uminus
   227   by (metis piecewise_differentiable_add piecewise_differentiable_neg)
   228 
   229 lemma continuous_on_joinpaths_D1:
   230     "continuous_on {0..1} (g1 +++ g2) \<Longrightarrow> continuous_on {0..1} g1"
   231   apply (rule continuous_on_eq [of _ "(g1 +++ g2) \<circ> (( *)(inverse 2))"])
   232   apply (rule continuous_intros | simp)+
   233   apply (auto elim!: continuous_on_subset simp: joinpaths_def)
   234   done
   235 
   236 lemma continuous_on_joinpaths_D2:
   237     "\<lbrakk>continuous_on {0..1} (g1 +++ g2); pathfinish g1 = pathstart g2\<rbrakk> \<Longrightarrow> continuous_on {0..1} g2"
   238   apply (rule continuous_on_eq [of _ "(g1 +++ g2) \<circ> (\<lambda>x. inverse 2*x + 1/2)"])
   239   apply (rule continuous_intros | simp)+
   240   apply (auto elim!: continuous_on_subset simp add: joinpaths_def pathfinish_def pathstart_def Ball_def)
   241   done
   242 
   243 lemma piecewise_differentiable_D1:
   244   assumes "(g1 +++ g2) piecewise_differentiable_on {0..1}"
   245   shows "g1 piecewise_differentiable_on {0..1}"
   246 proof -
   247   obtain S where cont: "continuous_on {0..1} g1" and "finite S"
   248     and S: "\<And>x. x \<in> {0..1} - S \<Longrightarrow> g1 +++ g2 differentiable at x within {0..1}"
   249     using assms unfolding piecewise_differentiable_on_def
   250     by (blast dest!: continuous_on_joinpaths_D1)
   251   show ?thesis
   252     unfolding piecewise_differentiable_on_def
   253   proof (intro exI conjI ballI cont)
   254     show "finite (insert 1 ((( *)2) ` S))"
   255       by (simp add: \<open>finite S\<close>)
   256     show "g1 differentiable at x within {0..1}" if "x \<in> {0..1} - insert 1 (( *) 2 ` S)" for x
   257     proof (rule_tac d="dist (x/2) (1/2)" in differentiable_transform_within)
   258       have "g1 +++ g2 differentiable at (x / 2) within {0..1/2}"
   259         by (rule differentiable_subset [OF S [of "x/2"]] | use that in force)+
   260       then show "g1 +++ g2 \<circ> ( *) (inverse 2) differentiable at x within {0..1}"
   261         by (auto intro: differentiable_chain_within)
   262     qed (use that in \<open>auto simp: joinpaths_def\<close>)
   263   qed
   264 qed
   265 
   266 lemma piecewise_differentiable_D2:
   267   assumes "(g1 +++ g2) piecewise_differentiable_on {0..1}" and eq: "pathfinish g1 = pathstart g2"
   268   shows "g2 piecewise_differentiable_on {0..1}"
   269 proof -
   270   have [simp]: "g1 1 = g2 0"
   271     using eq by (simp add: pathfinish_def pathstart_def)
   272   obtain S where cont: "continuous_on {0..1} g2" and "finite S"
   273     and S: "\<And>x. x \<in> {0..1} - S \<Longrightarrow> g1 +++ g2 differentiable at x within {0..1}"
   274     using assms unfolding piecewise_differentiable_on_def
   275     by (blast dest!: continuous_on_joinpaths_D2)
   276   show ?thesis
   277     unfolding piecewise_differentiable_on_def
   278   proof (intro exI conjI ballI cont)
   279     show "finite (insert 0 ((\<lambda>x. 2*x-1)`S))"
   280       by (simp add: \<open>finite S\<close>)
   281     show "g2 differentiable at x within {0..1}" if "x \<in> {0..1} - insert 0 ((\<lambda>x. 2*x-1)`S)" for x
   282     proof (rule_tac d="dist ((x+1)/2) (1/2)" in differentiable_transform_within)
   283       have x2: "(x + 1) / 2 \<notin> S"
   284         using that
   285         apply (clarsimp simp: image_iff)
   286         by (metis add.commute add_diff_cancel_left' mult_2 real_sum_of_halves)
   287       have "g1 +++ g2 \<circ> (\<lambda>x. (x+1) / 2) differentiable at x within {0..1}"
   288         by (rule differentiable_chain_within differentiable_subset [OF S [of "(x+1)/2"]] | use x2 that in force)+
   289       then show "g1 +++ g2 \<circ> (\<lambda>x. (x+1) / 2) differentiable at x within {0..1}"
   290         by (auto intro: differentiable_chain_within)
   291       show "(g1 +++ g2 \<circ> (\<lambda>x. (x + 1) / 2)) x' = g2 x'" if "x' \<in> {0..1}" "dist x' x < dist ((x + 1) / 2) (1/2)" for x'
   292       proof -
   293         have [simp]: "(2*x'+2)/2 = x'+1"
   294           by (simp add: divide_simps)
   295         show ?thesis
   296           using that by (auto simp: joinpaths_def)
   297       qed
   298     qed (use that in \<open>auto simp: joinpaths_def\<close>)
   299   qed
   300 qed
   301 
   302 
   303 subsubsection\<open>The concept of continuously differentiable\<close>
   304 
   305 text \<open>
   306 John Harrison writes as follows:
   307 
   308 ``The usual assumption in complex analysis texts is that a path \<open>\<gamma>\<close> should be piecewise
   309 continuously differentiable, which ensures that the path integral exists at least for any continuous
   310 f, since all piecewise continuous functions are integrable. However, our notion of validity is
   311 weaker, just piecewise differentiability\ldots{} [namely] continuity plus differentiability except on a
   312 finite set\ldots{} [Our] underlying theory of integration is the Kurzweil-Henstock theory. In contrast to
   313 the Riemann or Lebesgue theory (but in common with a simple notion based on antiderivatives), this
   314 can integrate all derivatives.''
   315 
   316 "Formalizing basic complex analysis." From Insight to Proof: Festschrift in Honour of Andrzej Trybulec.
   317 Studies in Logic, Grammar and Rhetoric 10.23 (2007): 151-165.
   318 
   319 And indeed he does not assume that his derivatives are continuous, but the penalty is unreasonably
   320 difficult proofs concerning winding numbers. We need a self-contained and straightforward theorem
   321 asserting that all derivatives can be integrated before we can adopt Harrison's choice.\<close>
   322 
   323 definition C1_differentiable_on :: "(real \<Rightarrow> 'a::real_normed_vector) \<Rightarrow> real set \<Rightarrow> bool"
   324            (infix "C1'_differentiable'_on" 50)
   325   where
   326   "f C1_differentiable_on S \<longleftrightarrow>
   327    (\<exists>D. (\<forall>x \<in> S. (f has_vector_derivative (D x)) (at x)) \<and> continuous_on S D)"
   328 
   329 lemma C1_differentiable_on_eq:
   330     "f C1_differentiable_on S \<longleftrightarrow>
   331      (\<forall>x \<in> S. f differentiable at x) \<and> continuous_on S (\<lambda>x. vector_derivative f (at x))"
   332      (is "?lhs = ?rhs")
   333 proof
   334   assume ?lhs
   335   then show ?rhs
   336     unfolding C1_differentiable_on_def
   337     by (metis (no_types, lifting) continuous_on_eq  differentiableI_vector vector_derivative_at)
   338 next
   339   assume ?rhs
   340   then show ?lhs
   341     using C1_differentiable_on_def vector_derivative_works by fastforce
   342 qed
   343 
   344 lemma C1_differentiable_on_subset:
   345   "f C1_differentiable_on T \<Longrightarrow> S \<subseteq> T \<Longrightarrow> f C1_differentiable_on S"
   346   unfolding C1_differentiable_on_def  continuous_on_eq_continuous_within
   347   by (blast intro:  continuous_within_subset)
   348 
   349 lemma C1_differentiable_compose:
   350   assumes fg: "f C1_differentiable_on S" "g C1_differentiable_on (f ` S)" and fin: "\<And>x. finite (S \<inter> f-`{x})"
   351   shows "(g \<circ> f) C1_differentiable_on S"
   352 proof -
   353   have "\<And>x. x \<in> S \<Longrightarrow> g \<circ> f differentiable at x"
   354     by (meson C1_differentiable_on_eq assms differentiable_chain_at imageI)
   355   moreover have "continuous_on S (\<lambda>x. vector_derivative (g \<circ> f) (at x))"
   356   proof (rule continuous_on_eq [of _ "\<lambda>x. vector_derivative f (at x) *\<^sub>R vector_derivative g (at (f x))"])
   357     show "continuous_on S (\<lambda>x. vector_derivative f (at x) *\<^sub>R vector_derivative g (at (f x)))"
   358       using fg
   359       apply (clarsimp simp add: C1_differentiable_on_eq)
   360       apply (rule Limits.continuous_on_scaleR, assumption)
   361       by (metis (mono_tags, lifting) continuous_at_imp_continuous_on continuous_on_compose continuous_on_cong differentiable_imp_continuous_within o_def)
   362     show "\<And>x. x \<in> S \<Longrightarrow> vector_derivative f (at x) *\<^sub>R vector_derivative g (at (f x)) = vector_derivative (g \<circ> f) (at x)"
   363       by (metis (mono_tags, hide_lams) C1_differentiable_on_eq fg imageI vector_derivative_chain_at)
   364   qed
   365   ultimately show ?thesis
   366     by (simp add: C1_differentiable_on_eq)
   367 qed
   368 
   369 lemma C1_diff_imp_diff: "f C1_differentiable_on S \<Longrightarrow> f differentiable_on S"
   370   by (simp add: C1_differentiable_on_eq differentiable_at_imp_differentiable_on)
   371 
   372 lemma C1_differentiable_on_ident [simp, derivative_intros]: "(\<lambda>x. x) C1_differentiable_on S"
   373   by (auto simp: C1_differentiable_on_eq continuous_on_const)
   374 
   375 lemma C1_differentiable_on_const [simp, derivative_intros]: "(\<lambda>z. a) C1_differentiable_on S"
   376   by (auto simp: C1_differentiable_on_eq continuous_on_const)
   377 
   378 lemma C1_differentiable_on_add [simp, derivative_intros]:
   379   "f C1_differentiable_on S \<Longrightarrow> g C1_differentiable_on S \<Longrightarrow> (\<lambda>x. f x + g x) C1_differentiable_on S"
   380   unfolding C1_differentiable_on_eq  by (auto intro: continuous_intros)
   381 
   382 lemma C1_differentiable_on_minus [simp, derivative_intros]:
   383   "f C1_differentiable_on S \<Longrightarrow> (\<lambda>x. - f x) C1_differentiable_on S"
   384   unfolding C1_differentiable_on_eq  by (auto intro: continuous_intros)
   385 
   386 lemma C1_differentiable_on_diff [simp, derivative_intros]:
   387   "f C1_differentiable_on S \<Longrightarrow> g C1_differentiable_on S \<Longrightarrow> (\<lambda>x. f x - g x) C1_differentiable_on S"
   388   unfolding C1_differentiable_on_eq  by (auto intro: continuous_intros)
   389 
   390 lemma C1_differentiable_on_mult [simp, derivative_intros]:
   391   fixes f g :: "real \<Rightarrow> 'a :: real_normed_algebra"
   392   shows "f C1_differentiable_on S \<Longrightarrow> g C1_differentiable_on S \<Longrightarrow> (\<lambda>x. f x * g x) C1_differentiable_on S"
   393   unfolding C1_differentiable_on_eq
   394   by (auto simp: continuous_on_add continuous_on_mult continuous_at_imp_continuous_on differentiable_imp_continuous_within)
   395 
   396 lemma C1_differentiable_on_scaleR [simp, derivative_intros]:
   397   "f C1_differentiable_on S \<Longrightarrow> g C1_differentiable_on S \<Longrightarrow> (\<lambda>x. f x *\<^sub>R g x) C1_differentiable_on S"
   398   unfolding C1_differentiable_on_eq
   399   by (rule continuous_intros | simp add: continuous_at_imp_continuous_on differentiable_imp_continuous_within)+
   400 
   401 
   402 definition piecewise_C1_differentiable_on
   403            (infixr "piecewise'_C1'_differentiable'_on" 50)
   404   where "f piecewise_C1_differentiable_on i  \<equiv>
   405            continuous_on i f \<and>
   406            (\<exists>S. finite S \<and> (f C1_differentiable_on (i - S)))"
   407 
   408 lemma C1_differentiable_imp_piecewise:
   409     "f C1_differentiable_on S \<Longrightarrow> f piecewise_C1_differentiable_on S"
   410   by (auto simp: piecewise_C1_differentiable_on_def C1_differentiable_on_eq continuous_at_imp_continuous_on differentiable_imp_continuous_within)
   411 
   412 lemma piecewise_C1_imp_differentiable:
   413     "f piecewise_C1_differentiable_on i \<Longrightarrow> f piecewise_differentiable_on i"
   414   by (auto simp: piecewise_C1_differentiable_on_def piecewise_differentiable_on_def
   415            C1_differentiable_on_def differentiable_def has_vector_derivative_def
   416            intro: has_derivative_at_withinI)
   417 
   418 lemma piecewise_C1_differentiable_compose:
   419   assumes fg: "f piecewise_C1_differentiable_on S" "g piecewise_C1_differentiable_on (f ` S)" and fin: "\<And>x. finite (S \<inter> f-`{x})"
   420   shows "(g \<circ> f) piecewise_C1_differentiable_on S"
   421 proof -
   422   have "continuous_on S (\<lambda>x. g (f x))"
   423     by (metis continuous_on_compose2 fg order_refl piecewise_C1_differentiable_on_def)
   424   moreover have "\<exists>T. finite T \<and> g \<circ> f C1_differentiable_on S - T"
   425   proof -
   426     obtain F where "finite F" and F: "f C1_differentiable_on S - F" and f: "f piecewise_C1_differentiable_on S"
   427       using fg by (auto simp: piecewise_C1_differentiable_on_def)
   428     obtain G where "finite G" and G: "g C1_differentiable_on f ` S - G" and g: "g piecewise_C1_differentiable_on f ` S"
   429       using fg by (auto simp: piecewise_C1_differentiable_on_def)
   430     show ?thesis
   431     proof (intro exI conjI)
   432       show "finite (F \<union> (\<Union>x\<in>G. S \<inter> f-`{x}))"
   433         using fin by (auto simp only: Int_Union \<open>finite F\<close> \<open>finite G\<close> finite_UN finite_imageI)
   434       show "g \<circ> f C1_differentiable_on S - (F \<union> (\<Union>x\<in>G. S \<inter> f -` {x}))"
   435         apply (rule C1_differentiable_compose)
   436           apply (blast intro: C1_differentiable_on_subset [OF F])
   437           apply (blast intro: C1_differentiable_on_subset [OF G])
   438         by (simp add:  C1_differentiable_on_subset G Diff_Int_distrib2 fin)
   439     qed
   440   qed
   441   ultimately show ?thesis
   442     by (simp add: piecewise_C1_differentiable_on_def)
   443 qed
   444 
   445 lemma piecewise_C1_differentiable_on_subset:
   446     "f piecewise_C1_differentiable_on S \<Longrightarrow> T \<le> S \<Longrightarrow> f piecewise_C1_differentiable_on T"
   447   by (auto simp: piecewise_C1_differentiable_on_def elim!: continuous_on_subset C1_differentiable_on_subset)
   448 
   449 lemma C1_differentiable_imp_continuous_on:
   450   "f C1_differentiable_on S \<Longrightarrow> continuous_on S f"
   451   unfolding C1_differentiable_on_eq continuous_on_eq_continuous_within
   452   using differentiable_at_withinI differentiable_imp_continuous_within by blast
   453 
   454 lemma C1_differentiable_on_empty [iff]: "f C1_differentiable_on {}"
   455   unfolding C1_differentiable_on_def
   456   by auto
   457 
   458 lemma piecewise_C1_differentiable_affine:
   459   fixes m::real
   460   assumes "f piecewise_C1_differentiable_on ((\<lambda>x. m * x + c) ` S)"
   461   shows "(f \<circ> (\<lambda>x. m *\<^sub>R x + c)) piecewise_C1_differentiable_on S"
   462 proof (cases "m = 0")
   463   case True
   464   then show ?thesis
   465     unfolding o_def by (auto simp: piecewise_C1_differentiable_on_def continuous_on_const)
   466 next
   467   case False
   468   have *: "\<And>x. finite (S \<inter> {y. m * y + c = x})"
   469     using False not_finite_existsD by fastforce 
   470   show ?thesis
   471     apply (rule piecewise_C1_differentiable_compose [OF C1_differentiable_imp_piecewise])
   472     apply (rule * assms derivative_intros | simp add: False vimage_def)+
   473     done
   474 qed
   475 
   476 lemma piecewise_C1_differentiable_cases:
   477   fixes c::real
   478   assumes "f piecewise_C1_differentiable_on {a..c}"
   479           "g piecewise_C1_differentiable_on {c..b}"
   480            "a \<le> c" "c \<le> b" "f c = g c"
   481   shows "(\<lambda>x. if x \<le> c then f x else g x) piecewise_C1_differentiable_on {a..b}"
   482 proof -
   483   obtain S T where st: "f C1_differentiable_on ({a..c} - S)"
   484                        "g C1_differentiable_on ({c..b} - T)"
   485                        "finite S" "finite T"
   486     using assms
   487     by (force simp: piecewise_C1_differentiable_on_def)
   488   then have f_diff: "f differentiable_on {a..<c} - S"
   489         and g_diff: "g differentiable_on {c<..b} - T"
   490     by (simp_all add: C1_differentiable_on_eq differentiable_at_withinI differentiable_on_def)
   491   have "continuous_on {a..c} f" "continuous_on {c..b} g"
   492     using assms piecewise_C1_differentiable_on_def by auto
   493   then have cab: "continuous_on {a..b} (\<lambda>x. if x \<le> c then f x else g x)"
   494     using continuous_on_cases [OF closed_real_atLeastAtMost [of a c],
   495                                OF closed_real_atLeastAtMost [of c b],
   496                                of f g "\<lambda>x. x\<le>c"]  assms
   497     by (force simp: ivl_disj_un_two_touch)
   498   { fix x
   499     assume x: "x \<in> {a..b} - insert c (S \<union> T)"
   500     have "(\<lambda>x. if x \<le> c then f x else g x) differentiable at x" (is "?diff_fg")
   501     proof (cases x c rule: le_cases)
   502       case le show ?diff_fg
   503         apply (rule differentiable_transform_within [where f=f and d = "dist x c"])
   504         using x dist_real_def le st by (auto simp: C1_differentiable_on_eq)
   505     next
   506       case ge show ?diff_fg
   507         apply (rule differentiable_transform_within [where f=g and d = "dist x c"])
   508         using dist_nz x dist_real_def ge st x by (auto simp: C1_differentiable_on_eq)
   509     qed
   510   }
   511   then have "(\<forall>x \<in> {a..b} - insert c (S \<union> T). (\<lambda>x. if x \<le> c then f x else g x) differentiable at x)"
   512     by auto
   513   moreover
   514   { assume fcon: "continuous_on ({a<..<c} - S) (\<lambda>x. vector_derivative f (at x))"
   515        and gcon: "continuous_on ({c<..<b} - T) (\<lambda>x. vector_derivative g (at x))"
   516     have "open ({a<..<c} - S)"  "open ({c<..<b} - T)"
   517       using st by (simp_all add: open_Diff finite_imp_closed)
   518     moreover have "continuous_on ({a<..<c} - S) (\<lambda>x. vector_derivative (\<lambda>x. if x \<le> c then f x else g x) (at x))"
   519     proof -
   520       have "((\<lambda>x. if x \<le> c then f x else g x) has_vector_derivative vector_derivative f (at x))            (at x)"
   521         if "a < x" "x < c" "x \<notin> S" for x
   522       proof -
   523         have f: "f differentiable at x"
   524           by (meson C1_differentiable_on_eq Diff_iff atLeastAtMost_iff less_eq_real_def st(1) that)
   525         show ?thesis
   526           using that
   527           apply (rule_tac f=f and d="dist x c" in has_vector_derivative_transform_within)
   528              apply (auto simp: dist_norm vector_derivative_works [symmetric] f)
   529           done
   530       qed
   531       then show ?thesis
   532         by (metis (no_types, lifting) continuous_on_eq [OF fcon] DiffE greaterThanLessThan_iff vector_derivative_at)
   533     qed
   534     moreover have "continuous_on ({c<..<b} - T) (\<lambda>x. vector_derivative (\<lambda>x. if x \<le> c then f x else g x) (at x))"
   535     proof -
   536       have "((\<lambda>x. if x \<le> c then f x else g x) has_vector_derivative vector_derivative g (at x))            (at x)"
   537         if "c < x" "x < b" "x \<notin> T" for x
   538       proof -
   539         have g: "g differentiable at x"
   540           by (metis C1_differentiable_on_eq DiffD1 DiffI atLeastAtMost_diff_ends greaterThanLessThan_iff st(2) that)
   541         show ?thesis
   542           using that
   543           apply (rule_tac f=g and d="dist x c" in has_vector_derivative_transform_within)
   544              apply (auto simp: dist_norm vector_derivative_works [symmetric] g)
   545           done
   546       qed
   547       then show ?thesis
   548         by (metis (no_types, lifting) continuous_on_eq [OF gcon] DiffE greaterThanLessThan_iff vector_derivative_at)
   549     qed
   550     ultimately have "continuous_on ({a<..<b} - insert c (S \<union> T))
   551         (\<lambda>x. vector_derivative (\<lambda>x. if x \<le> c then f x else g x) (at x))"
   552       by (rule continuous_on_subset [OF continuous_on_open_Un], auto)
   553   } note * = this
   554   have "continuous_on ({a<..<b} - insert c (S \<union> T)) (\<lambda>x. vector_derivative (\<lambda>x. if x \<le> c then f x else g x) (at x))"
   555     using st
   556     by (auto simp: C1_differentiable_on_eq elim!: continuous_on_subset intro: *)
   557   ultimately have "\<exists>S. finite S \<and> ((\<lambda>x. if x \<le> c then f x else g x) C1_differentiable_on {a..b} - S)"
   558     apply (rule_tac x="{a,b,c} \<union> S \<union> T" in exI)
   559     using st  by (auto simp: C1_differentiable_on_eq elim!: continuous_on_subset)
   560   with cab show ?thesis
   561     by (simp add: piecewise_C1_differentiable_on_def)
   562 qed
   563 
   564 lemma piecewise_C1_differentiable_neg:
   565     "f piecewise_C1_differentiable_on S \<Longrightarrow> (\<lambda>x. -(f x)) piecewise_C1_differentiable_on S"
   566   unfolding piecewise_C1_differentiable_on_def
   567   by (auto intro!: continuous_on_minus C1_differentiable_on_minus)
   568 
   569 lemma piecewise_C1_differentiable_add:
   570   assumes "f piecewise_C1_differentiable_on i"
   571           "g piecewise_C1_differentiable_on i"
   572     shows "(\<lambda>x. f x + g x) piecewise_C1_differentiable_on i"
   573 proof -
   574   obtain S t where st: "finite S" "finite t"
   575                        "f C1_differentiable_on (i-S)"
   576                        "g C1_differentiable_on (i-t)"
   577     using assms by (auto simp: piecewise_C1_differentiable_on_def)
   578   then have "finite (S \<union> t) \<and> (\<lambda>x. f x + g x) C1_differentiable_on i - (S \<union> t)"
   579     by (auto intro: C1_differentiable_on_add elim!: C1_differentiable_on_subset)
   580   moreover have "continuous_on i f" "continuous_on i g"
   581     using assms piecewise_C1_differentiable_on_def by auto
   582   ultimately show ?thesis
   583     by (auto simp: piecewise_C1_differentiable_on_def continuous_on_add)
   584 qed
   585 
   586 lemma piecewise_C1_differentiable_diff:
   587     "\<lbrakk>f piecewise_C1_differentiable_on S;  g piecewise_C1_differentiable_on S\<rbrakk>
   588      \<Longrightarrow> (\<lambda>x. f x - g x) piecewise_C1_differentiable_on S"
   589   unfolding diff_conv_add_uminus
   590   by (metis piecewise_C1_differentiable_add piecewise_C1_differentiable_neg)
   591 
   592 lemma piecewise_C1_differentiable_D1:
   593   fixes g1 :: "real \<Rightarrow> 'a::real_normed_field"
   594   assumes "(g1 +++ g2) piecewise_C1_differentiable_on {0..1}"
   595     shows "g1 piecewise_C1_differentiable_on {0..1}"
   596 proof -
   597   obtain S where "finite S"
   598              and co12: "continuous_on ({0..1} - S) (\<lambda>x. vector_derivative (g1 +++ g2) (at x))"
   599              and g12D: "\<forall>x\<in>{0..1} - S. g1 +++ g2 differentiable at x"
   600     using assms  by (auto simp: piecewise_C1_differentiable_on_def C1_differentiable_on_eq)
   601   have g1D: "g1 differentiable at x" if "x \<in> {0..1} - insert 1 (( *) 2 ` S)" for x
   602   proof (rule differentiable_transform_within)
   603     show "g1 +++ g2 \<circ> ( *) (inverse 2) differentiable at x"
   604       using that g12D 
   605       apply (simp only: joinpaths_def)
   606       by (rule differentiable_chain_at derivative_intros | force)+
   607     show "\<And>x'. \<lbrakk>dist x' x < dist (x/2) (1/2)\<rbrakk>
   608           \<Longrightarrow> (g1 +++ g2 \<circ> ( *) (inverse 2)) x' = g1 x'"
   609       using that by (auto simp: dist_real_def joinpaths_def)
   610   qed (use that in \<open>auto simp: dist_real_def\<close>)
   611   have [simp]: "vector_derivative (g1 \<circ> ( *) 2) (at (x/2)) = 2 *\<^sub>R vector_derivative g1 (at x)"
   612                if "x \<in> {0..1} - insert 1 (( *) 2 ` S)" for x
   613     apply (subst vector_derivative_chain_at)
   614     using that
   615     apply (rule derivative_eq_intros g1D | simp)+
   616     done
   617   have "continuous_on ({0..1/2} - insert (1/2) S) (\<lambda>x. vector_derivative (g1 +++ g2) (at x))"
   618     using co12 by (rule continuous_on_subset) force
   619   then have coDhalf: "continuous_on ({0..1/2} - insert (1/2) S) (\<lambda>x. vector_derivative (g1 \<circ> ( *)2) (at x))"
   620   proof (rule continuous_on_eq [OF _ vector_derivative_at])
   621     show "(g1 +++ g2 has_vector_derivative vector_derivative (g1 \<circ> ( *) 2) (at x)) (at x)"
   622       if "x \<in> {0..1/2} - insert (1/2) S" for x
   623     proof (rule has_vector_derivative_transform_within)
   624       show "(g1 \<circ> ( *) 2 has_vector_derivative vector_derivative (g1 \<circ> ( *) 2) (at x)) (at x)"
   625         using that
   626         by (force intro: g1D differentiable_chain_at simp: vector_derivative_works [symmetric])
   627       show "\<And>x'. \<lbrakk>dist x' x < dist x (1/2)\<rbrakk> \<Longrightarrow> (g1 \<circ> ( *) 2) x' = (g1 +++ g2) x'"
   628         using that by (auto simp: dist_norm joinpaths_def)
   629     qed (use that in \<open>auto simp: dist_norm\<close>)
   630   qed
   631   have "continuous_on ({0..1} - insert 1 (( *) 2 ` S))
   632                       ((\<lambda>x. 1/2 * vector_derivative (g1 \<circ> ( *)2) (at x)) \<circ> ( *)(1/2))"
   633     apply (rule continuous_intros)+
   634     using coDhalf
   635     apply (simp add: scaleR_conv_of_real image_set_diff image_image)
   636     done
   637   then have con_g1: "continuous_on ({0..1} - insert 1 (( *) 2 ` S)) (\<lambda>x. vector_derivative g1 (at x))"
   638     by (rule continuous_on_eq) (simp add: scaleR_conv_of_real)
   639   have "continuous_on {0..1} g1"
   640     using continuous_on_joinpaths_D1 assms piecewise_C1_differentiable_on_def by blast
   641   with \<open>finite S\<close> show ?thesis
   642     apply (clarsimp simp add: piecewise_C1_differentiable_on_def C1_differentiable_on_eq)
   643     apply (rule_tac x="insert 1 ((( *)2)`S)" in exI)
   644     apply (simp add: g1D con_g1)
   645   done
   646 qed
   647 
   648 lemma piecewise_C1_differentiable_D2:
   649   fixes g2 :: "real \<Rightarrow> 'a::real_normed_field"
   650   assumes "(g1 +++ g2) piecewise_C1_differentiable_on {0..1}" "pathfinish g1 = pathstart g2"
   651     shows "g2 piecewise_C1_differentiable_on {0..1}"
   652 proof -
   653   obtain S where "finite S"
   654              and co12: "continuous_on ({0..1} - S) (\<lambda>x. vector_derivative (g1 +++ g2) (at x))"
   655              and g12D: "\<forall>x\<in>{0..1} - S. g1 +++ g2 differentiable at x"
   656     using assms  by (auto simp: piecewise_C1_differentiable_on_def C1_differentiable_on_eq)
   657   have g2D: "g2 differentiable at x" if "x \<in> {0..1} - insert 0 ((\<lambda>x. 2*x-1) ` S)" for x
   658   proof (rule differentiable_transform_within)
   659     show "g1 +++ g2 \<circ> (\<lambda>x. (x + 1) / 2) differentiable at x"
   660       using g12D that
   661       apply (simp only: joinpaths_def)
   662       apply (drule_tac x= "(x+1) / 2" in bspec, force simp: divide_simps)
   663       apply (rule differentiable_chain_at derivative_intros | force)+
   664       done
   665     show "\<And>x'. dist x' x < dist ((x + 1) / 2) (1/2) \<Longrightarrow> (g1 +++ g2 \<circ> (\<lambda>x. (x + 1) / 2)) x' = g2 x'"
   666       using that by (auto simp: dist_real_def joinpaths_def field_simps)
   667     qed (use that in \<open>auto simp: dist_norm\<close>)
   668   have [simp]: "vector_derivative (g2 \<circ> (\<lambda>x. 2*x-1)) (at ((x+1)/2)) = 2 *\<^sub>R vector_derivative g2 (at x)"
   669                if "x \<in> {0..1} - insert 0 ((\<lambda>x. 2*x-1) ` S)" for x
   670     using that  by (auto simp: vector_derivative_chain_at divide_simps g2D)
   671   have "continuous_on ({1/2..1} - insert (1/2) S) (\<lambda>x. vector_derivative (g1 +++ g2) (at x))"
   672     using co12 by (rule continuous_on_subset) force
   673   then have coDhalf: "continuous_on ({1/2..1} - insert (1/2) S) (\<lambda>x. vector_derivative (g2 \<circ> (\<lambda>x. 2*x-1)) (at x))"
   674   proof (rule continuous_on_eq [OF _ vector_derivative_at])
   675     show "(g1 +++ g2 has_vector_derivative vector_derivative (g2 \<circ> (\<lambda>x. 2 * x - 1)) (at x))
   676           (at x)"
   677       if "x \<in> {1 / 2..1} - insert (1 / 2) S" for x
   678     proof (rule_tac f="g2 \<circ> (\<lambda>x. 2*x-1)" and d="dist (3/4) ((x+1)/2)" in has_vector_derivative_transform_within)
   679       show "(g2 \<circ> (\<lambda>x. 2 * x - 1) has_vector_derivative vector_derivative (g2 \<circ> (\<lambda>x. 2 * x - 1)) (at x))
   680             (at x)"
   681         using that by (force intro: g2D differentiable_chain_at simp: vector_derivative_works [symmetric])
   682       show "\<And>x'. \<lbrakk>dist x' x < dist (3 / 4) ((x + 1) / 2)\<rbrakk> \<Longrightarrow> (g2 \<circ> (\<lambda>x. 2 * x - 1)) x' = (g1 +++ g2) x'"
   683         using that by (auto simp: dist_norm joinpaths_def add_divide_distrib)
   684     qed (use that in \<open>auto simp: dist_norm\<close>)
   685   qed
   686   have [simp]: "((\<lambda>x. (x+1) / 2) ` ({0..1} - insert 0 ((\<lambda>x. 2 * x - 1) ` S))) = ({1/2..1} - insert (1/2) S)"
   687     apply (simp add: image_set_diff inj_on_def image_image)
   688     apply (auto simp: image_affinity_atLeastAtMost_div add_divide_distrib)
   689     done
   690   have "continuous_on ({0..1} - insert 0 ((\<lambda>x. 2*x-1) ` S))
   691                       ((\<lambda>x. 1/2 * vector_derivative (g2 \<circ> (\<lambda>x. 2*x-1)) (at x)) \<circ> (\<lambda>x. (x+1)/2))"
   692     by (rule continuous_intros | simp add:  coDhalf)+
   693   then have con_g2: "continuous_on ({0..1} - insert 0 ((\<lambda>x. 2*x-1) ` S)) (\<lambda>x. vector_derivative g2 (at x))"
   694     by (rule continuous_on_eq) (simp add: scaleR_conv_of_real)
   695   have "continuous_on {0..1} g2"
   696     using continuous_on_joinpaths_D2 assms piecewise_C1_differentiable_on_def by blast
   697   with \<open>finite S\<close> show ?thesis
   698     apply (clarsimp simp add: piecewise_C1_differentiable_on_def C1_differentiable_on_eq)
   699     apply (rule_tac x="insert 0 ((\<lambda>x. 2 * x - 1) ` S)" in exI)
   700     apply (simp add: g2D con_g2)
   701   done
   702 qed
   703 
   704 subsection \<open>Valid paths, and their start and finish\<close>
   705 
   706 definition valid_path :: "(real \<Rightarrow> 'a :: real_normed_vector) \<Rightarrow> bool"
   707   where "valid_path f \<equiv> f piecewise_C1_differentiable_on {0..1::real}"
   708 
   709 definition closed_path :: "(real \<Rightarrow> 'a :: real_normed_vector) \<Rightarrow> bool"
   710   where "closed_path g \<equiv> g 0 = g 1"
   711 
   712 subsubsection\<open>In particular, all results for paths apply\<close>
   713 
   714 lemma valid_path_imp_path: "valid_path g \<Longrightarrow> path g"
   715 by (simp add: path_def piecewise_C1_differentiable_on_def valid_path_def)
   716 
   717 lemma connected_valid_path_image: "valid_path g \<Longrightarrow> connected(path_image g)"
   718   by (metis connected_path_image valid_path_imp_path)
   719 
   720 lemma compact_valid_path_image: "valid_path g \<Longrightarrow> compact(path_image g)"
   721   by (metis compact_path_image valid_path_imp_path)
   722 
   723 lemma bounded_valid_path_image: "valid_path g \<Longrightarrow> bounded(path_image g)"
   724   by (metis bounded_path_image valid_path_imp_path)
   725 
   726 lemma closed_valid_path_image: "valid_path g \<Longrightarrow> closed(path_image g)"
   727   by (metis closed_path_image valid_path_imp_path)
   728 
   729 proposition valid_path_compose:
   730   assumes "valid_path g"
   731       and der: "\<And>x. x \<in> path_image g \<Longrightarrow> f field_differentiable (at x)"
   732       and con: "continuous_on (path_image g) (deriv f)"
   733     shows "valid_path (f \<circ> g)"
   734 proof -
   735   obtain S where "finite S" and g_diff: "g C1_differentiable_on {0..1} - S"
   736     using \<open>valid_path g\<close> unfolding valid_path_def piecewise_C1_differentiable_on_def by auto
   737   have "f \<circ> g differentiable at t" when "t\<in>{0..1} - S" for t
   738     proof (rule differentiable_chain_at)
   739       show "g differentiable at t" using \<open>valid_path g\<close>
   740         by (meson C1_differentiable_on_eq \<open>g C1_differentiable_on {0..1} - S\<close> that)
   741     next
   742       have "g t\<in>path_image g" using that DiffD1 image_eqI path_image_def by metis
   743       then show "f differentiable at (g t)" 
   744         using der[THEN field_differentiable_imp_differentiable] by auto
   745     qed
   746   moreover have "continuous_on ({0..1} - S) (\<lambda>x. vector_derivative (f \<circ> g) (at x))"
   747     proof (rule continuous_on_eq [where f = "\<lambda>x. vector_derivative g (at x) * deriv f (g x)"],
   748         rule continuous_intros)
   749       show "continuous_on ({0..1} - S) (\<lambda>x. vector_derivative g (at x))"
   750         using g_diff C1_differentiable_on_eq by auto
   751     next
   752       have "continuous_on {0..1} (\<lambda>x. deriv f (g x))"
   753         using continuous_on_compose[OF _ con[unfolded path_image_def],unfolded comp_def]
   754           \<open>valid_path g\<close> piecewise_C1_differentiable_on_def valid_path_def
   755         by blast
   756       then show "continuous_on ({0..1} - S) (\<lambda>x. deriv f (g x))"
   757         using continuous_on_subset by blast
   758     next
   759       show "vector_derivative g (at t) * deriv f (g t) = vector_derivative (f \<circ> g) (at t)"
   760           when "t \<in> {0..1} - S" for t
   761         proof (rule vector_derivative_chain_at_general[symmetric])
   762           show "g differentiable at t" by (meson C1_differentiable_on_eq g_diff that)
   763         next
   764           have "g t\<in>path_image g" using that DiffD1 image_eqI path_image_def by metis
   765           then show "f field_differentiable at (g t)" using der by auto
   766         qed
   767     qed
   768   ultimately have "f \<circ> g C1_differentiable_on {0..1} - S"
   769     using C1_differentiable_on_eq by blast
   770   moreover have "path (f \<circ> g)" 
   771     apply (rule path_continuous_image[OF valid_path_imp_path[OF \<open>valid_path g\<close>]])
   772     using der
   773     by (simp add: continuous_at_imp_continuous_on field_differentiable_imp_continuous_at)
   774   ultimately show ?thesis unfolding valid_path_def piecewise_C1_differentiable_on_def path_def
   775     using \<open>finite S\<close> by auto
   776 qed
   777 
   778 
   779 subsection\<open>Contour Integrals along a path\<close>
   780 
   781 text\<open>This definition is for complex numbers only, and does not generalise to line integrals in a vector field\<close>
   782 
   783 text\<open>piecewise differentiable function on [0,1]\<close>
   784 
   785 definition has_contour_integral :: "(complex \<Rightarrow> complex) \<Rightarrow> complex \<Rightarrow> (real \<Rightarrow> complex) \<Rightarrow> bool"
   786            (infixr "has'_contour'_integral" 50)
   787   where "(f has_contour_integral i) g \<equiv>
   788            ((\<lambda>x. f(g x) * vector_derivative g (at x within {0..1}))
   789             has_integral i) {0..1}"
   790 
   791 definition contour_integrable_on
   792            (infixr "contour'_integrable'_on" 50)
   793   where "f contour_integrable_on g \<equiv> \<exists>i. (f has_contour_integral i) g"
   794 
   795 definition contour_integral
   796   where "contour_integral g f \<equiv> SOME i. (f has_contour_integral i) g \<or> \<not> f contour_integrable_on g \<and> i=0"
   797 
   798 lemma not_integrable_contour_integral: "\<not> f contour_integrable_on g \<Longrightarrow> contour_integral g f = 0"
   799   unfolding contour_integrable_on_def contour_integral_def by blast
   800 
   801 lemma contour_integral_unique: "(f has_contour_integral i) g \<Longrightarrow> contour_integral g f = i"
   802   apply (simp add: contour_integral_def has_contour_integral_def contour_integrable_on_def)
   803   using has_integral_unique by blast
   804 
   805 corollary has_contour_integral_eqpath:
   806      "\<lbrakk>(f has_contour_integral y) p; f contour_integrable_on \<gamma>;
   807        contour_integral p f = contour_integral \<gamma> f\<rbrakk>
   808       \<Longrightarrow> (f has_contour_integral y) \<gamma>"
   809 using contour_integrable_on_def contour_integral_unique by auto
   810 
   811 lemma has_contour_integral_integral:
   812     "f contour_integrable_on i \<Longrightarrow> (f has_contour_integral (contour_integral i f)) i"
   813   by (metis contour_integral_unique contour_integrable_on_def)
   814 
   815 lemma has_contour_integral_unique:
   816     "(f has_contour_integral i) g \<Longrightarrow> (f has_contour_integral j) g \<Longrightarrow> i = j"
   817   using has_integral_unique
   818   by (auto simp: has_contour_integral_def)
   819 
   820 lemma has_contour_integral_integrable: "(f has_contour_integral i) g \<Longrightarrow> f contour_integrable_on g"
   821   using contour_integrable_on_def by blast
   822 
   823 subsubsection\<open>Show that we can forget about the localized derivative.\<close>
   824 
   825 lemma has_integral_localized_vector_derivative:
   826     "((\<lambda>x. f (g x) * vector_derivative g (at x within {a..b})) has_integral i) {a..b} \<longleftrightarrow>
   827      ((\<lambda>x. f (g x) * vector_derivative g (at x)) has_integral i) {a..b}"
   828 proof -
   829   have *: "{a..b} - {a,b} = interior {a..b}"
   830     by (simp add: atLeastAtMost_diff_ends)
   831   show ?thesis
   832     apply (rule has_integral_spike_eq [of "{a,b}"])
   833     apply (auto simp: at_within_interior [of _ "{a..b}"])
   834     done
   835 qed
   836 
   837 lemma integrable_on_localized_vector_derivative:
   838     "(\<lambda>x. f (g x) * vector_derivative g (at x within {a..b})) integrable_on {a..b} \<longleftrightarrow>
   839      (\<lambda>x. f (g x) * vector_derivative g (at x)) integrable_on {a..b}"
   840   by (simp add: integrable_on_def has_integral_localized_vector_derivative)
   841 
   842 lemma has_contour_integral:
   843      "(f has_contour_integral i) g \<longleftrightarrow>
   844       ((\<lambda>x. f (g x) * vector_derivative g (at x)) has_integral i) {0..1}"
   845   by (simp add: has_integral_localized_vector_derivative has_contour_integral_def)
   846 
   847 lemma contour_integrable_on:
   848      "f contour_integrable_on g \<longleftrightarrow>
   849       (\<lambda>t. f(g t) * vector_derivative g (at t)) integrable_on {0..1}"
   850   by (simp add: has_contour_integral integrable_on_def contour_integrable_on_def)
   851 
   852 subsection\<open>Reversing a path\<close>
   853 
   854 lemma valid_path_imp_reverse:
   855   assumes "valid_path g"
   856     shows "valid_path(reversepath g)"
   857 proof -
   858   obtain S where "finite S" and S: "g C1_differentiable_on ({0..1} - S)"
   859     using assms by (auto simp: valid_path_def piecewise_C1_differentiable_on_def)
   860   then have "finite ((-) 1 ` S)"
   861     by auto
   862   moreover have "(reversepath g C1_differentiable_on ({0..1} - (-) 1 ` S))"
   863     unfolding reversepath_def
   864     apply (rule C1_differentiable_compose [of "\<lambda>x::real. 1-x" _ g, unfolded o_def])
   865     using S
   866     by (force simp: finite_vimageI inj_on_def C1_differentiable_on_eq continuous_on_const elim!: continuous_on_subset)+
   867   ultimately show ?thesis using assms
   868     by (auto simp: valid_path_def piecewise_C1_differentiable_on_def path_def [symmetric])
   869 qed
   870 
   871 lemma valid_path_reversepath [simp]: "valid_path(reversepath g) \<longleftrightarrow> valid_path g"
   872   using valid_path_imp_reverse by force
   873 
   874 lemma has_contour_integral_reversepath:
   875   assumes "valid_path g" and f: "(f has_contour_integral i) g"
   876     shows "(f has_contour_integral (-i)) (reversepath g)"
   877 proof -
   878   { fix S x
   879     assume xs: "g C1_differentiable_on ({0..1} - S)" "x \<notin> (-) 1 ` S" "0 \<le> x" "x \<le> 1"
   880     have "vector_derivative (\<lambda>x. g (1 - x)) (at x within {0..1}) =
   881             - vector_derivative g (at (1 - x) within {0..1})"
   882     proof -
   883       obtain f' where f': "(g has_vector_derivative f') (at (1 - x))"
   884         using xs
   885         by (force simp: has_vector_derivative_def C1_differentiable_on_def)
   886       have "(g \<circ> (\<lambda>x. 1 - x) has_vector_derivative -1 *\<^sub>R f') (at x)"
   887         by (intro vector_diff_chain_within has_vector_derivative_at_within [OF f'] derivative_eq_intros | simp)+
   888       then have mf': "((\<lambda>x. g (1 - x)) has_vector_derivative -f') (at x)"
   889         by (simp add: o_def)
   890       show ?thesis
   891         using xs
   892         by (auto simp: vector_derivative_at_within_ivl [OF mf'] vector_derivative_at_within_ivl [OF f'])
   893     qed
   894   } note * = this
   895   obtain S where S: "continuous_on {0..1} g" "finite S" "g C1_differentiable_on {0..1} - S"
   896     using assms by (auto simp: valid_path_def piecewise_C1_differentiable_on_def)
   897   have "((\<lambda>x. - (f (g (1 - x)) * vector_derivative g (at (1 - x) within {0..1}))) has_integral -i)
   898        {0..1}"
   899     using has_integral_affinity01 [where m= "-1" and c=1, OF f [unfolded has_contour_integral_def]]
   900     by (simp add: has_integral_neg)
   901   then show ?thesis 
   902     using S
   903     apply (clarsimp simp: reversepath_def has_contour_integral_def)
   904     apply (rule_tac S = "(\<lambda>x. 1 - x) ` S" in has_integral_spike_finite)
   905       apply (auto simp: *)
   906     done
   907 qed
   908 
   909 lemma contour_integrable_reversepath:
   910     "valid_path g \<Longrightarrow> f contour_integrable_on g \<Longrightarrow> f contour_integrable_on (reversepath g)"
   911   using has_contour_integral_reversepath contour_integrable_on_def by blast
   912 
   913 lemma contour_integrable_reversepath_eq:
   914     "valid_path g \<Longrightarrow> (f contour_integrable_on (reversepath g) \<longleftrightarrow> f contour_integrable_on g)"
   915   using contour_integrable_reversepath valid_path_reversepath by fastforce
   916 
   917 lemma contour_integral_reversepath:
   918   assumes "valid_path g"
   919     shows "contour_integral (reversepath g) f = - (contour_integral g f)"
   920 proof (cases "f contour_integrable_on g")
   921   case True then show ?thesis
   922     by (simp add: assms contour_integral_unique has_contour_integral_integral has_contour_integral_reversepath)
   923 next
   924   case False then have "~ f contour_integrable_on (reversepath g)"
   925     by (simp add: assms contour_integrable_reversepath_eq)
   926   with False show ?thesis by (simp add: not_integrable_contour_integral)
   927 qed
   928 
   929 
   930 subsection\<open>Joining two paths together\<close>
   931 
   932 lemma valid_path_join:
   933   assumes "valid_path g1" "valid_path g2" "pathfinish g1 = pathstart g2"
   934     shows "valid_path(g1 +++ g2)"
   935 proof -
   936   have "g1 1 = g2 0"
   937     using assms by (auto simp: pathfinish_def pathstart_def)
   938   moreover have "(g1 \<circ> (\<lambda>x. 2*x)) piecewise_C1_differentiable_on {0..1/2}"
   939     apply (rule piecewise_C1_differentiable_compose)
   940     using assms
   941     apply (auto simp: valid_path_def piecewise_C1_differentiable_on_def continuous_on_joinpaths)
   942     apply (force intro: finite_vimageI [where h = "( *)2"] inj_onI)
   943     done
   944   moreover have "(g2 \<circ> (\<lambda>x. 2*x-1)) piecewise_C1_differentiable_on {1/2..1}"
   945     apply (rule piecewise_C1_differentiable_compose)
   946     using assms unfolding valid_path_def piecewise_C1_differentiable_on_def
   947     by (auto intro!: continuous_intros finite_vimageI [where h = "(\<lambda>x. 2*x - 1)"] inj_onI
   948              simp: image_affinity_atLeastAtMost_diff continuous_on_joinpaths)
   949   ultimately show ?thesis
   950     apply (simp only: valid_path_def continuous_on_joinpaths joinpaths_def)
   951     apply (rule piecewise_C1_differentiable_cases)
   952     apply (auto simp: o_def)
   953     done
   954 qed
   955 
   956 lemma valid_path_join_D1:
   957   fixes g1 :: "real \<Rightarrow> 'a::real_normed_field"
   958   shows "valid_path (g1 +++ g2) \<Longrightarrow> valid_path g1"
   959   unfolding valid_path_def
   960   by (rule piecewise_C1_differentiable_D1)
   961 
   962 lemma valid_path_join_D2:
   963   fixes g2 :: "real \<Rightarrow> 'a::real_normed_field"
   964   shows "\<lbrakk>valid_path (g1 +++ g2); pathfinish g1 = pathstart g2\<rbrakk> \<Longrightarrow> valid_path g2"
   965   unfolding valid_path_def
   966   by (rule piecewise_C1_differentiable_D2)
   967 
   968 lemma valid_path_join_eq [simp]:
   969   fixes g2 :: "real \<Rightarrow> 'a::real_normed_field"
   970   shows "pathfinish g1 = pathstart g2 \<Longrightarrow> (valid_path(g1 +++ g2) \<longleftrightarrow> valid_path g1 \<and> valid_path g2)"
   971   using valid_path_join_D1 valid_path_join_D2 valid_path_join by blast
   972 
   973 lemma has_contour_integral_join:
   974   assumes "(f has_contour_integral i1) g1" "(f has_contour_integral i2) g2"
   975           "valid_path g1" "valid_path g2"
   976     shows "(f has_contour_integral (i1 + i2)) (g1 +++ g2)"
   977 proof -
   978   obtain s1 s2
   979     where s1: "finite s1" "\<forall>x\<in>{0..1} - s1. g1 differentiable at x"
   980       and s2: "finite s2" "\<forall>x\<in>{0..1} - s2. g2 differentiable at x"
   981     using assms
   982     by (auto simp: valid_path_def piecewise_C1_differentiable_on_def C1_differentiable_on_eq)
   983   have 1: "((\<lambda>x. f (g1 x) * vector_derivative g1 (at x)) has_integral i1) {0..1}"
   984    and 2: "((\<lambda>x. f (g2 x) * vector_derivative g2 (at x)) has_integral i2) {0..1}"
   985     using assms
   986     by (auto simp: has_contour_integral)
   987   have i1: "((\<lambda>x. (2*f (g1 (2*x))) * vector_derivative g1 (at (2*x))) has_integral i1) {0..1/2}"
   988    and i2: "((\<lambda>x. (2*f (g2 (2*x - 1))) * vector_derivative g2 (at (2*x - 1))) has_integral i2) {1/2..1}"
   989     using has_integral_affinity01 [OF 1, where m= 2 and c=0, THEN has_integral_cmul [where c=2]]
   990           has_integral_affinity01 [OF 2, where m= 2 and c="-1", THEN has_integral_cmul [where c=2]]
   991     by (simp_all only: image_affinity_atLeastAtMost_div_diff, simp_all add: scaleR_conv_of_real mult_ac)
   992   have g1: "\<lbrakk>0 \<le> z; z*2 < 1; z*2 \<notin> s1\<rbrakk> \<Longrightarrow>
   993             vector_derivative (\<lambda>x. if x*2 \<le> 1 then g1 (2*x) else g2 (2*x - 1)) (at z) =
   994             2 *\<^sub>R vector_derivative g1 (at (z*2))" for z
   995     apply (rule vector_derivative_at [OF has_vector_derivative_transform_within [where f = "(\<lambda>x. g1(2*x))" and d = "\<bar>z - 1/2\<bar>"]])
   996     apply (simp_all add: dist_real_def abs_if split: if_split_asm)
   997     apply (rule vector_diff_chain_at [of "\<lambda>x. 2*x" 2 _ g1, simplified o_def])
   998     apply (simp add: has_vector_derivative_def has_derivative_def bounded_linear_mult_left)
   999     using s1
  1000     apply (auto simp: algebra_simps vector_derivative_works)
  1001     done
  1002   have g2: "\<lbrakk>1 < z*2; z \<le> 1; z*2 - 1 \<notin> s2\<rbrakk> \<Longrightarrow>
  1003             vector_derivative (\<lambda>x. if x*2 \<le> 1 then g1 (2*x) else g2 (2*x - 1)) (at z) =
  1004             2 *\<^sub>R vector_derivative g2 (at (z*2 - 1))" for z
  1005     apply (rule vector_derivative_at [OF has_vector_derivative_transform_within [where f = "(\<lambda>x. g2 (2*x - 1))" and d = "\<bar>z - 1/2\<bar>"]])
  1006     apply (simp_all add: dist_real_def abs_if split: if_split_asm)
  1007     apply (rule vector_diff_chain_at [of "\<lambda>x. 2*x - 1" 2 _ g2, simplified o_def])
  1008     apply (simp add: has_vector_derivative_def has_derivative_def bounded_linear_mult_left)
  1009     using s2
  1010     apply (auto simp: algebra_simps vector_derivative_works)
  1011     done
  1012   have "((\<lambda>x. f ((g1 +++ g2) x) * vector_derivative (g1 +++ g2) (at x)) has_integral i1) {0..1/2}"
  1013     apply (rule has_integral_spike_finite [OF _ _ i1, of "insert (1/2) (( *)2 -` s1)"])
  1014     using s1
  1015     apply (force intro: finite_vimageI [where h = "( *)2"] inj_onI)
  1016     apply (clarsimp simp add: joinpaths_def scaleR_conv_of_real mult_ac g1)
  1017     done
  1018   moreover have "((\<lambda>x. f ((g1 +++ g2) x) * vector_derivative (g1 +++ g2) (at x)) has_integral i2) {1/2..1}"
  1019     apply (rule has_integral_spike_finite [OF _ _ i2, of "insert (1/2) ((\<lambda>x. 2*x-1) -` s2)"])
  1020     using s2
  1021     apply (force intro: finite_vimageI [where h = "\<lambda>x. 2*x-1"] inj_onI)
  1022     apply (clarsimp simp add: joinpaths_def scaleR_conv_of_real mult_ac g2)
  1023     done
  1024   ultimately
  1025   show ?thesis
  1026     apply (simp add: has_contour_integral)
  1027     apply (rule has_integral_combine [where c = "1/2"], auto)
  1028     done
  1029 qed
  1030 
  1031 lemma contour_integrable_joinI:
  1032   assumes "f contour_integrable_on g1" "f contour_integrable_on g2"
  1033           "valid_path g1" "valid_path g2"
  1034     shows "f contour_integrable_on (g1 +++ g2)"
  1035   using assms
  1036   by (meson has_contour_integral_join contour_integrable_on_def)
  1037 
  1038 lemma contour_integrable_joinD1:
  1039   assumes "f contour_integrable_on (g1 +++ g2)" "valid_path g1"
  1040     shows "f contour_integrable_on g1"
  1041 proof -
  1042   obtain s1
  1043     where s1: "finite s1" "\<forall>x\<in>{0..1} - s1. g1 differentiable at x"
  1044     using assms by (auto simp: valid_path_def piecewise_C1_differentiable_on_def C1_differentiable_on_eq)
  1045   have "(\<lambda>x. f ((g1 +++ g2) (x/2)) * vector_derivative (g1 +++ g2) (at (x/2))) integrable_on {0..1}"
  1046     using assms
  1047     apply (auto simp: contour_integrable_on)
  1048     apply (drule integrable_on_subcbox [where a=0 and b="1/2"])
  1049     apply (auto intro: integrable_affinity [of _ 0 "1/2::real" "1/2" 0, simplified])
  1050     done
  1051   then have *: "(\<lambda>x. (f ((g1 +++ g2) (x/2))/2) * vector_derivative (g1 +++ g2) (at (x/2))) integrable_on {0..1}"
  1052     by (auto dest: integrable_cmul [where c="1/2"] simp: scaleR_conv_of_real)
  1053   have g1: "\<lbrakk>0 < z; z < 1; z \<notin> s1\<rbrakk> \<Longrightarrow>
  1054             vector_derivative (\<lambda>x. if x*2 \<le> 1 then g1 (2*x) else g2 (2*x - 1)) (at (z/2)) =
  1055             2 *\<^sub>R vector_derivative g1 (at z)"  for z
  1056     apply (rule vector_derivative_at [OF has_vector_derivative_transform_within [where f = "(\<lambda>x. g1(2*x))" and d = "\<bar>(z-1)/2\<bar>"]])
  1057     apply (simp_all add: field_simps dist_real_def abs_if split: if_split_asm)
  1058     apply (rule vector_diff_chain_at [of "\<lambda>x. x*2" 2 _ g1, simplified o_def])
  1059     using s1
  1060     apply (auto simp: vector_derivative_works has_vector_derivative_def has_derivative_def bounded_linear_mult_left)
  1061     done
  1062   show ?thesis
  1063     using s1
  1064     apply (auto simp: contour_integrable_on)
  1065     apply (rule integrable_spike_finite [of "{0,1} \<union> s1", OF _ _ *])
  1066     apply (auto simp: joinpaths_def scaleR_conv_of_real g1)
  1067     done
  1068 qed
  1069 
  1070 lemma contour_integrable_joinD2:
  1071   assumes "f contour_integrable_on (g1 +++ g2)" "valid_path g2"
  1072     shows "f contour_integrable_on g2"
  1073 proof -
  1074   obtain s2
  1075     where s2: "finite s2" "\<forall>x\<in>{0..1} - s2. g2 differentiable at x"
  1076     using assms by (auto simp: valid_path_def piecewise_C1_differentiable_on_def C1_differentiable_on_eq)
  1077   have "(\<lambda>x. f ((g1 +++ g2) (x/2 + 1/2)) * vector_derivative (g1 +++ g2) (at (x/2 + 1/2))) integrable_on {0..1}"
  1078     using assms
  1079     apply (auto simp: contour_integrable_on)
  1080     apply (drule integrable_on_subcbox [where a="1/2" and b=1], auto)
  1081     apply (drule integrable_affinity [of _ "1/2::real" 1 "1/2" "1/2", simplified])
  1082     apply (simp add: image_affinity_atLeastAtMost_diff)
  1083     done
  1084   then have *: "(\<lambda>x. (f ((g1 +++ g2) (x/2 + 1/2))/2) * vector_derivative (g1 +++ g2) (at (x/2 + 1/2)))
  1085                 integrable_on {0..1}"
  1086     by (auto dest: integrable_cmul [where c="1/2"] simp: scaleR_conv_of_real)
  1087   have g2: "\<lbrakk>0 < z; z < 1; z \<notin> s2\<rbrakk> \<Longrightarrow>
  1088             vector_derivative (\<lambda>x. if x*2 \<le> 1 then g1 (2*x) else g2 (2*x - 1)) (at (z/2+1/2)) =
  1089             2 *\<^sub>R vector_derivative g2 (at z)" for z
  1090     apply (rule vector_derivative_at [OF has_vector_derivative_transform_within [where f = "(\<lambda>x. g2(2*x-1))" and d = "\<bar>z/2\<bar>"]])
  1091     apply (simp_all add: field_simps dist_real_def abs_if split: if_split_asm)
  1092     apply (rule vector_diff_chain_at [of "\<lambda>x. x*2-1" 2 _ g2, simplified o_def])
  1093     using s2
  1094     apply (auto simp: has_vector_derivative_def has_derivative_def bounded_linear_mult_left
  1095                       vector_derivative_works add_divide_distrib)
  1096     done
  1097   show ?thesis
  1098     using s2
  1099     apply (auto simp: contour_integrable_on)
  1100     apply (rule integrable_spike_finite [of "{0,1} \<union> s2", OF _ _ *])
  1101     apply (auto simp: joinpaths_def scaleR_conv_of_real g2)
  1102     done
  1103 qed
  1104 
  1105 lemma contour_integrable_join [simp]:
  1106   shows
  1107     "\<lbrakk>valid_path g1; valid_path g2\<rbrakk>
  1108      \<Longrightarrow> f contour_integrable_on (g1 +++ g2) \<longleftrightarrow> f contour_integrable_on g1 \<and> f contour_integrable_on g2"
  1109 using contour_integrable_joinD1 contour_integrable_joinD2 contour_integrable_joinI by blast
  1110 
  1111 lemma contour_integral_join [simp]:
  1112   shows
  1113     "\<lbrakk>f contour_integrable_on g1; f contour_integrable_on g2; valid_path g1; valid_path g2\<rbrakk>
  1114         \<Longrightarrow> contour_integral (g1 +++ g2) f = contour_integral g1 f + contour_integral g2 f"
  1115   by (simp add: has_contour_integral_integral has_contour_integral_join contour_integral_unique)
  1116 
  1117 
  1118 subsection\<open>Shifting the starting point of a (closed) path\<close>
  1119 
  1120 lemma shiftpath_alt_def: "shiftpath a f = (\<lambda>x. if x \<le> 1-a then f (a + x) else f (a + x - 1))"
  1121   by (auto simp: shiftpath_def)
  1122 
  1123 lemma valid_path_shiftpath [intro]:
  1124   assumes "valid_path g" "pathfinish g = pathstart g" "a \<in> {0..1}"
  1125     shows "valid_path(shiftpath a g)"
  1126   using assms
  1127   apply (auto simp: valid_path_def shiftpath_alt_def)
  1128   apply (rule piecewise_C1_differentiable_cases)
  1129   apply (auto simp: algebra_simps)
  1130   apply (rule piecewise_C1_differentiable_affine [of g 1 a, simplified o_def scaleR_one])
  1131   apply (auto simp: pathfinish_def pathstart_def elim: piecewise_C1_differentiable_on_subset)
  1132   apply (rule piecewise_C1_differentiable_affine [of g 1 "a-1", simplified o_def scaleR_one algebra_simps])
  1133   apply (auto simp: pathfinish_def pathstart_def elim: piecewise_C1_differentiable_on_subset)
  1134   done
  1135 
  1136 lemma has_contour_integral_shiftpath:
  1137   assumes f: "(f has_contour_integral i) g" "valid_path g"
  1138       and a: "a \<in> {0..1}"
  1139     shows "(f has_contour_integral i) (shiftpath a g)"
  1140 proof -
  1141   obtain s
  1142     where s: "finite s" and g: "\<forall>x\<in>{0..1} - s. g differentiable at x"
  1143     using assms by (auto simp: valid_path_def piecewise_C1_differentiable_on_def C1_differentiable_on_eq)
  1144   have *: "((\<lambda>x. f (g x) * vector_derivative g (at x)) has_integral i) {0..1}"
  1145     using assms by (auto simp: has_contour_integral)
  1146   then have i: "i = integral {a..1} (\<lambda>x. f (g x) * vector_derivative g (at x)) +
  1147                     integral {0..a} (\<lambda>x. f (g x) * vector_derivative g (at x))"
  1148     apply (rule has_integral_unique)
  1149     apply (subst add.commute)
  1150     apply (subst integral_combine)
  1151     using assms * integral_unique by auto
  1152   { fix x
  1153     have "0 \<le> x \<Longrightarrow> x + a < 1 \<Longrightarrow> x \<notin> (\<lambda>x. x - a) ` s \<Longrightarrow>
  1154          vector_derivative (shiftpath a g) (at x) = vector_derivative g (at (x + a))"
  1155       unfolding shiftpath_def
  1156       apply (rule vector_derivative_at [OF has_vector_derivative_transform_within [where f = "(\<lambda>x. g(a+x))" and d = "dist(1-a) x"]])
  1157         apply (auto simp: field_simps dist_real_def abs_if split: if_split_asm)
  1158       apply (rule vector_diff_chain_at [of "\<lambda>x. x+a" 1 _ g, simplified o_def scaleR_one])
  1159        apply (intro derivative_eq_intros | simp)+
  1160       using g
  1161        apply (drule_tac x="x+a" in bspec)
  1162       using a apply (auto simp: has_vector_derivative_def vector_derivative_works image_def add.commute)
  1163       done
  1164   } note vd1 = this
  1165   { fix x
  1166     have "1 < x + a \<Longrightarrow> x \<le> 1 \<Longrightarrow> x \<notin> (\<lambda>x. x - a + 1) ` s \<Longrightarrow>
  1167           vector_derivative (shiftpath a g) (at x) = vector_derivative g (at (x + a - 1))"
  1168       unfolding shiftpath_def
  1169       apply (rule vector_derivative_at [OF has_vector_derivative_transform_within [where f = "(\<lambda>x. g(a+x-1))" and d = "dist (1-a) x"]])
  1170         apply (auto simp: field_simps dist_real_def abs_if split: if_split_asm)
  1171       apply (rule vector_diff_chain_at [of "\<lambda>x. x+a-1" 1 _ g, simplified o_def scaleR_one])
  1172        apply (intro derivative_eq_intros | simp)+
  1173       using g
  1174       apply (drule_tac x="x+a-1" in bspec)
  1175       using a apply (auto simp: has_vector_derivative_def vector_derivative_works image_def add.commute)
  1176       done
  1177   } note vd2 = this
  1178   have va1: "(\<lambda>x. f (g x) * vector_derivative g (at x)) integrable_on ({a..1})"
  1179     using * a   by (fastforce intro: integrable_subinterval_real)
  1180   have v0a: "(\<lambda>x. f (g x) * vector_derivative g (at x)) integrable_on ({0..a})"
  1181     apply (rule integrable_subinterval_real)
  1182     using * a by auto
  1183   have "((\<lambda>x. f (shiftpath a g x) * vector_derivative (shiftpath a g) (at x))
  1184         has_integral  integral {a..1} (\<lambda>x. f (g x) * vector_derivative g (at x)))  {0..1 - a}"
  1185     apply (rule has_integral_spike_finite
  1186              [where S = "{1-a} \<union> (\<lambda>x. x-a) ` s" and f = "\<lambda>x. f(g(a+x)) * vector_derivative g (at(a+x))"])
  1187       using s apply blast
  1188      using a apply (auto simp: algebra_simps vd1)
  1189      apply (force simp: shiftpath_def add.commute)
  1190     using has_integral_affinity [where m=1 and c=a, simplified, OF integrable_integral [OF va1]]
  1191     apply (simp add: image_affinity_atLeastAtMost_diff [where m=1 and c=a, simplified] add.commute)
  1192     done
  1193   moreover
  1194   have "((\<lambda>x. f (shiftpath a g x) * vector_derivative (shiftpath a g) (at x))
  1195         has_integral  integral {0..a} (\<lambda>x. f (g x) * vector_derivative g (at x)))  {1 - a..1}"
  1196     apply (rule has_integral_spike_finite
  1197              [where S = "{1-a} \<union> (\<lambda>x. x-a+1) ` s" and f = "\<lambda>x. f(g(a+x-1)) * vector_derivative g (at(a+x-1))"])
  1198       using s apply blast
  1199      using a apply (auto simp: algebra_simps vd2)
  1200      apply (force simp: shiftpath_def add.commute)
  1201     using has_integral_affinity [where m=1 and c="a-1", simplified, OF integrable_integral [OF v0a]]
  1202     apply (simp add: image_affinity_atLeastAtMost [where m=1 and c="1-a", simplified])
  1203     apply (simp add: algebra_simps)
  1204     done
  1205   ultimately show ?thesis
  1206     using a
  1207     by (auto simp: i has_contour_integral intro: has_integral_combine [where c = "1-a"])
  1208 qed
  1209 
  1210 lemma has_contour_integral_shiftpath_D:
  1211   assumes "(f has_contour_integral i) (shiftpath a g)"
  1212           "valid_path g" "pathfinish g = pathstart g" "a \<in> {0..1}"
  1213     shows "(f has_contour_integral i) g"
  1214 proof -
  1215   obtain s
  1216     where s: "finite s" and g: "\<forall>x\<in>{0..1} - s. g differentiable at x"
  1217     using assms by (auto simp: valid_path_def piecewise_C1_differentiable_on_def C1_differentiable_on_eq)
  1218   { fix x
  1219     assume x: "0 < x" "x < 1" "x \<notin> s"
  1220     then have gx: "g differentiable at x"
  1221       using g by auto
  1222     have "vector_derivative g (at x within {0..1}) =
  1223           vector_derivative (shiftpath (1 - a) (shiftpath a g)) (at x within {0..1})"
  1224       apply (rule vector_derivative_at_within_ivl
  1225                   [OF has_vector_derivative_transform_within_open
  1226                       [where f = "(shiftpath (1 - a) (shiftpath a g))" and S = "{0<..<1}-s"]])
  1227       using s g assms x
  1228       apply (auto simp: finite_imp_closed open_Diff shiftpath_shiftpath
  1229                         at_within_interior [of _ "{0..1}"] vector_derivative_works [symmetric])
  1230       apply (rule differentiable_transform_within [OF gx, of "min x (1-x)"])
  1231       apply (auto simp: dist_real_def shiftpath_shiftpath abs_if split: if_split_asm)
  1232       done
  1233   } note vd = this
  1234   have fi: "(f has_contour_integral i) (shiftpath (1 - a) (shiftpath a g))"
  1235     using assms  by (auto intro!: has_contour_integral_shiftpath)
  1236   show ?thesis
  1237     apply (simp add: has_contour_integral_def)
  1238     apply (rule has_integral_spike_finite [of "{0,1} \<union> s", OF _ _  fi [unfolded has_contour_integral_def]])
  1239     using s assms vd
  1240     apply (auto simp: Path_Connected.shiftpath_shiftpath)
  1241     done
  1242 qed
  1243 
  1244 lemma has_contour_integral_shiftpath_eq:
  1245   assumes "valid_path g" "pathfinish g = pathstart g" "a \<in> {0..1}"
  1246     shows "(f has_contour_integral i) (shiftpath a g) \<longleftrightarrow> (f has_contour_integral i) g"
  1247   using assms has_contour_integral_shiftpath has_contour_integral_shiftpath_D by blast
  1248 
  1249 lemma contour_integrable_on_shiftpath_eq:
  1250   assumes "valid_path g" "pathfinish g = pathstart g" "a \<in> {0..1}"
  1251     shows "f contour_integrable_on (shiftpath a g) \<longleftrightarrow> f contour_integrable_on g"
  1252 using assms contour_integrable_on_def has_contour_integral_shiftpath_eq by auto
  1253 
  1254 lemma contour_integral_shiftpath:
  1255   assumes "valid_path g" "pathfinish g = pathstart g" "a \<in> {0..1}"
  1256     shows "contour_integral (shiftpath a g) f = contour_integral g f"
  1257    using assms
  1258    by (simp add: contour_integral_def contour_integrable_on_def has_contour_integral_shiftpath_eq)
  1259 
  1260 
  1261 subsection\<open>More about straight-line paths\<close>
  1262 
  1263 lemma has_vector_derivative_linepath_within:
  1264     "(linepath a b has_vector_derivative (b - a)) (at x within s)"
  1265 apply (simp add: linepath_def has_vector_derivative_def algebra_simps)
  1266 apply (rule derivative_eq_intros | simp)+
  1267 done
  1268 
  1269 lemma vector_derivative_linepath_within:
  1270     "x \<in> {0..1} \<Longrightarrow> vector_derivative (linepath a b) (at x within {0..1}) = b - a"
  1271   apply (rule vector_derivative_within_cbox [of 0 "1::real", simplified])
  1272   apply (auto simp: has_vector_derivative_linepath_within)
  1273   done
  1274 
  1275 lemma vector_derivative_linepath_at [simp]: "vector_derivative (linepath a b) (at x) = b - a"
  1276   by (simp add: has_vector_derivative_linepath_within vector_derivative_at)
  1277 
  1278 lemma valid_path_linepath [iff]: "valid_path (linepath a b)"
  1279   apply (simp add: valid_path_def piecewise_C1_differentiable_on_def C1_differentiable_on_eq continuous_on_linepath)
  1280   apply (rule_tac x="{}" in exI)
  1281   apply (simp add: differentiable_on_def differentiable_def)
  1282   using has_vector_derivative_def has_vector_derivative_linepath_within
  1283   apply (fastforce simp add: continuous_on_eq_continuous_within)
  1284   done
  1285 
  1286 lemma has_contour_integral_linepath:
  1287   shows "(f has_contour_integral i) (linepath a b) \<longleftrightarrow>
  1288          ((\<lambda>x. f(linepath a b x) * (b - a)) has_integral i) {0..1}"
  1289   by (simp add: has_contour_integral vector_derivative_linepath_at)
  1290 
  1291 lemma linepath_in_path:
  1292   shows "x \<in> {0..1} \<Longrightarrow> linepath a b x \<in> closed_segment a b"
  1293   by (auto simp: segment linepath_def)
  1294 
  1295 lemma linepath_image_01: "linepath a b ` {0..1} = closed_segment a b"
  1296   by (auto simp: segment linepath_def)
  1297 
  1298 lemma linepath_in_convex_hull:
  1299     fixes x::real
  1300     assumes a: "a \<in> convex hull s"
  1301         and b: "b \<in> convex hull s"
  1302         and x: "0\<le>x" "x\<le>1"
  1303        shows "linepath a b x \<in> convex hull s"
  1304   apply (rule closed_segment_subset_convex_hull [OF a b, THEN subsetD])
  1305   using x
  1306   apply (auto simp: linepath_image_01 [symmetric])
  1307   done
  1308 
  1309 lemma Re_linepath: "Re(linepath (of_real a) (of_real b) x) = (1 - x)*a + x*b"
  1310   by (simp add: linepath_def)
  1311 
  1312 lemma Im_linepath: "Im(linepath (of_real a) (of_real b) x) = 0"
  1313   by (simp add: linepath_def)
  1314 
  1315 lemma has_contour_integral_trivial [iff]: "(f has_contour_integral 0) (linepath a a)"
  1316   by (simp add: has_contour_integral_linepath)
  1317 
  1318 lemma has_contour_integral_trivial_iff [simp]: "(f has_contour_integral i) (linepath a a) \<longleftrightarrow> i=0"
  1319   using has_contour_integral_unique by blast
  1320 
  1321 lemma contour_integral_trivial [simp]: "contour_integral (linepath a a) f = 0"
  1322   using has_contour_integral_trivial contour_integral_unique by blast
  1323 
  1324 
  1325 subsection\<open>Relation to subpath construction\<close>
  1326 
  1327 lemma valid_path_subpath:
  1328   fixes g :: "real \<Rightarrow> 'a :: real_normed_vector"
  1329   assumes "valid_path g" "u \<in> {0..1}" "v \<in> {0..1}"
  1330     shows "valid_path(subpath u v g)"
  1331 proof (cases "v=u")
  1332   case True
  1333   then show ?thesis
  1334     unfolding valid_path_def subpath_def
  1335     by (force intro: C1_differentiable_on_const C1_differentiable_imp_piecewise)
  1336 next
  1337   case False
  1338   have "(g \<circ> (\<lambda>x. ((v-u) * x + u))) piecewise_C1_differentiable_on {0..1}"
  1339     apply (rule piecewise_C1_differentiable_compose)
  1340     apply (simp add: C1_differentiable_imp_piecewise)
  1341      apply (simp add: image_affinity_atLeastAtMost)
  1342     using assms False
  1343     apply (auto simp: algebra_simps valid_path_def piecewise_C1_differentiable_on_subset)
  1344     apply (subst Int_commute)
  1345     apply (auto simp: inj_on_def algebra_simps crossproduct_eq finite_vimage_IntI)
  1346     done
  1347   then show ?thesis
  1348     by (auto simp: o_def valid_path_def subpath_def)
  1349 qed
  1350 
  1351 lemma has_contour_integral_subpath_refl [iff]: "(f has_contour_integral 0) (subpath u u g)"
  1352   by (simp add: has_contour_integral subpath_def)
  1353 
  1354 lemma contour_integrable_subpath_refl [iff]: "f contour_integrable_on (subpath u u g)"
  1355   using has_contour_integral_subpath_refl contour_integrable_on_def by blast
  1356 
  1357 lemma contour_integral_subpath_refl [simp]: "contour_integral (subpath u u g) f = 0"
  1358   by (simp add: has_contour_integral_subpath_refl contour_integral_unique)
  1359 
  1360 lemma has_contour_integral_subpath:
  1361   assumes f: "f contour_integrable_on g" and g: "valid_path g"
  1362       and uv: "u \<in> {0..1}" "v \<in> {0..1}" "u \<le> v"
  1363     shows "(f has_contour_integral  integral {u..v} (\<lambda>x. f(g x) * vector_derivative g (at x)))
  1364            (subpath u v g)"
  1365 proof (cases "v=u")
  1366   case True
  1367   then show ?thesis
  1368     using f   by (simp add: contour_integrable_on_def subpath_def has_contour_integral)
  1369 next
  1370   case False
  1371   obtain s where s: "\<And>x. x \<in> {0..1} - s \<Longrightarrow> g differentiable at x" and fs: "finite s"
  1372     using g unfolding piecewise_C1_differentiable_on_def C1_differentiable_on_eq valid_path_def by blast
  1373   have *: "((\<lambda>x. f (g ((v - u) * x + u)) * vector_derivative g (at ((v - u) * x + u)))
  1374             has_integral (1 / (v - u)) * integral {u..v} (\<lambda>t. f (g t) * vector_derivative g (at t)))
  1375            {0..1}"
  1376     using f uv
  1377     apply (simp add: contour_integrable_on subpath_def has_contour_integral)
  1378     apply (drule integrable_on_subcbox [where a=u and b=v, simplified])
  1379     apply (simp_all add: has_integral_integral)
  1380     apply (drule has_integral_affinity [where m="v-u" and c=u, simplified])
  1381     apply (simp_all add: False image_affinity_atLeastAtMost_div_diff scaleR_conv_of_real)
  1382     apply (simp add: divide_simps False)
  1383     done
  1384   { fix x
  1385     have "x \<in> {0..1} \<Longrightarrow>
  1386            x \<notin> (\<lambda>t. (v-u) *\<^sub>R t + u) -` s \<Longrightarrow>
  1387            vector_derivative (\<lambda>x. g ((v-u) * x + u)) (at x) = (v-u) *\<^sub>R vector_derivative g (at ((v-u) * x + u))"
  1388       apply (rule vector_derivative_at [OF vector_diff_chain_at [simplified o_def]])
  1389       apply (intro derivative_eq_intros | simp)+
  1390       apply (cut_tac s [of "(v - u) * x + u"])
  1391       using uv mult_left_le [of x "v-u"]
  1392       apply (auto simp:  vector_derivative_works)
  1393       done
  1394   } note vd = this
  1395   show ?thesis
  1396     apply (cut_tac has_integral_cmul [OF *, where c = "v-u"])
  1397     using fs assms
  1398     apply (simp add: False subpath_def has_contour_integral)
  1399     apply (rule_tac S = "(\<lambda>t. ((v-u) *\<^sub>R t + u)) -` s" in has_integral_spike_finite)
  1400     apply (auto simp: inj_on_def False finite_vimageI vd scaleR_conv_of_real)
  1401     done
  1402 qed
  1403 
  1404 lemma contour_integrable_subpath:
  1405   assumes "f contour_integrable_on g" "valid_path g" "u \<in> {0..1}" "v \<in> {0..1}"
  1406     shows "f contour_integrable_on (subpath u v g)"
  1407   apply (cases u v rule: linorder_class.le_cases)
  1408    apply (metis contour_integrable_on_def has_contour_integral_subpath [OF assms])
  1409   apply (subst reversepath_subpath [symmetric])
  1410   apply (rule contour_integrable_reversepath)
  1411    using assms apply (blast intro: valid_path_subpath)
  1412   apply (simp add: contour_integrable_on_def)
  1413   using assms apply (blast intro: has_contour_integral_subpath)
  1414   done
  1415 
  1416 lemma has_integral_contour_integral_subpath:
  1417   assumes "f contour_integrable_on g" "valid_path g" "u \<in> {0..1}" "v \<in> {0..1}" "u \<le> v"
  1418     shows "(((\<lambda>x. f(g x) * vector_derivative g (at x)))
  1419             has_integral  contour_integral (subpath u v g) f) {u..v}"
  1420   using assms
  1421   apply (auto simp: has_integral_integrable_integral)
  1422   apply (rule integrable_on_subcbox [where a=u and b=v and S = "{0..1}", simplified])
  1423   apply (auto simp: contour_integral_unique [OF has_contour_integral_subpath] contour_integrable_on)
  1424   done
  1425 
  1426 lemma contour_integral_subcontour_integral:
  1427   assumes "f contour_integrable_on g" "valid_path g" "u \<in> {0..1}" "v \<in> {0..1}" "u \<le> v"
  1428     shows "contour_integral (subpath u v g) f =
  1429            integral {u..v} (\<lambda>x. f(g x) * vector_derivative g (at x))"
  1430   using assms has_contour_integral_subpath contour_integral_unique by blast
  1431 
  1432 lemma contour_integral_subpath_combine_less:
  1433   assumes "f contour_integrable_on g" "valid_path g" "u \<in> {0..1}" "v \<in> {0..1}" "w \<in> {0..1}"
  1434           "u<v" "v<w"
  1435     shows "contour_integral (subpath u v g) f + contour_integral (subpath v w g) f =
  1436            contour_integral (subpath u w g) f"
  1437   using assms apply (auto simp: contour_integral_subcontour_integral)
  1438   apply (rule integral_combine, auto)
  1439   apply (rule integrable_on_subcbox [where a=u and b=w and S = "{0..1}", simplified])
  1440   apply (auto simp: contour_integrable_on)
  1441   done
  1442 
  1443 lemma contour_integral_subpath_combine:
  1444   assumes "f contour_integrable_on g" "valid_path g" "u \<in> {0..1}" "v \<in> {0..1}" "w \<in> {0..1}"
  1445     shows "contour_integral (subpath u v g) f + contour_integral (subpath v w g) f =
  1446            contour_integral (subpath u w g) f"
  1447 proof (cases "u\<noteq>v \<and> v\<noteq>w \<and> u\<noteq>w")
  1448   case True
  1449     have *: "subpath v u g = reversepath(subpath u v g) \<and>
  1450              subpath w u g = reversepath(subpath u w g) \<and>
  1451              subpath w v g = reversepath(subpath v w g)"
  1452       by (auto simp: reversepath_subpath)
  1453     have "u < v \<and> v < w \<or>
  1454           u < w \<and> w < v \<or>
  1455           v < u \<and> u < w \<or>
  1456           v < w \<and> w < u \<or>
  1457           w < u \<and> u < v \<or>
  1458           w < v \<and> v < u"
  1459       using True assms by linarith
  1460     with assms show ?thesis
  1461       using contour_integral_subpath_combine_less [of f g u v w]
  1462             contour_integral_subpath_combine_less [of f g u w v]
  1463             contour_integral_subpath_combine_less [of f g v u w]
  1464             contour_integral_subpath_combine_less [of f g v w u]
  1465             contour_integral_subpath_combine_less [of f g w u v]
  1466             contour_integral_subpath_combine_less [of f g w v u]
  1467       apply simp
  1468       apply (elim disjE)
  1469       apply (auto simp: * contour_integral_reversepath contour_integrable_subpath
  1470                    valid_path_reversepath valid_path_subpath algebra_simps)
  1471       done
  1472 next
  1473   case False
  1474   then show ?thesis
  1475     apply (auto simp: contour_integral_subpath_refl)
  1476     using assms
  1477     by (metis eq_neg_iff_add_eq_0 contour_integrable_subpath contour_integral_reversepath reversepath_subpath valid_path_subpath)
  1478 qed
  1479 
  1480 lemma contour_integral_integral:
  1481      "contour_integral g f = integral {0..1} (\<lambda>x. f (g x) * vector_derivative g (at x))"
  1482   by (simp add: contour_integral_def integral_def has_contour_integral contour_integrable_on)
  1483 
  1484 
  1485 text\<open>Cauchy's theorem where there's a primitive\<close>
  1486 
  1487 lemma contour_integral_primitive_lemma:
  1488   fixes f :: "complex \<Rightarrow> complex" and g :: "real \<Rightarrow> complex"
  1489   assumes "a \<le> b"
  1490       and "\<And>x. x \<in> s \<Longrightarrow> (f has_field_derivative f' x) (at x within s)"
  1491       and "g piecewise_differentiable_on {a..b}"  "\<And>x. x \<in> {a..b} \<Longrightarrow> g x \<in> s"
  1492     shows "((\<lambda>x. f'(g x) * vector_derivative g (at x within {a..b}))
  1493              has_integral (f(g b) - f(g a))) {a..b}"
  1494 proof -
  1495   obtain k where k: "finite k" "\<forall>x\<in>{a..b} - k. g differentiable (at x within {a..b})" and cg: "continuous_on {a..b} g"
  1496     using assms by (auto simp: piecewise_differentiable_on_def)
  1497   have cfg: "continuous_on {a..b} (\<lambda>x. f (g x))"
  1498     apply (rule continuous_on_compose [OF cg, unfolded o_def])
  1499     using assms
  1500     apply (metis field_differentiable_def field_differentiable_imp_continuous_at continuous_on_eq_continuous_within continuous_on_subset image_subset_iff)
  1501     done
  1502   { fix x::real
  1503     assume a: "a < x" and b: "x < b" and xk: "x \<notin> k"
  1504     then have "g differentiable at x within {a..b}"
  1505       using k by (simp add: differentiable_at_withinI)
  1506     then have "(g has_vector_derivative vector_derivative g (at x within {a..b})) (at x within {a..b})"
  1507       by (simp add: vector_derivative_works has_field_derivative_def scaleR_conv_of_real)
  1508     then have gdiff: "(g has_derivative (\<lambda>u. u * vector_derivative g (at x within {a..b}))) (at x within {a..b})"
  1509       by (simp add: has_vector_derivative_def scaleR_conv_of_real)
  1510     have "(f has_field_derivative (f' (g x))) (at (g x) within g ` {a..b})"
  1511       using assms by (metis a atLeastAtMost_iff b DERIV_subset image_subset_iff less_eq_real_def)
  1512     then have fdiff: "(f has_derivative ( *) (f' (g x))) (at (g x) within g ` {a..b})"
  1513       by (simp add: has_field_derivative_def)
  1514     have "((\<lambda>x. f (g x)) has_vector_derivative f' (g x) * vector_derivative g (at x within {a..b})) (at x within {a..b})"
  1515       using diff_chain_within [OF gdiff fdiff]
  1516       by (simp add: has_vector_derivative_def scaleR_conv_of_real o_def mult_ac)
  1517   } note * = this
  1518   show ?thesis
  1519     apply (rule fundamental_theorem_of_calculus_interior_strong)
  1520     using k assms cfg *
  1521     apply (auto simp: at_within_Icc_at)
  1522     done
  1523 qed
  1524 
  1525 lemma contour_integral_primitive:
  1526   assumes "\<And>x. x \<in> s \<Longrightarrow> (f has_field_derivative f' x) (at x within s)"
  1527       and "valid_path g" "path_image g \<subseteq> s"
  1528     shows "(f' has_contour_integral (f(pathfinish g) - f(pathstart g))) g"
  1529   using assms
  1530   apply (simp add: valid_path_def path_image_def pathfinish_def pathstart_def has_contour_integral_def)
  1531   apply (auto intro!: piecewise_C1_imp_differentiable contour_integral_primitive_lemma [of 0 1 s])
  1532   done
  1533 
  1534 corollary Cauchy_theorem_primitive:
  1535   assumes "\<And>x. x \<in> s \<Longrightarrow> (f has_field_derivative f' x) (at x within s)"
  1536       and "valid_path g"  "path_image g \<subseteq> s" "pathfinish g = pathstart g"
  1537     shows "(f' has_contour_integral 0) g"
  1538   using assms
  1539   by (metis diff_self contour_integral_primitive)
  1540 
  1541 
  1542 text\<open>Existence of path integral for continuous function\<close>
  1543 lemma contour_integrable_continuous_linepath:
  1544   assumes "continuous_on (closed_segment a b) f"
  1545   shows "f contour_integrable_on (linepath a b)"
  1546 proof -
  1547   have "continuous_on {0..1} ((\<lambda>x. f x * (b - a)) \<circ> linepath a b)"
  1548     apply (rule continuous_on_compose [OF continuous_on_linepath], simp add: linepath_image_01)
  1549     apply (rule continuous_intros | simp add: assms)+
  1550     done
  1551   then show ?thesis
  1552     apply (simp add: contour_integrable_on_def has_contour_integral_def integrable_on_def [symmetric])
  1553     apply (rule integrable_continuous [of 0 "1::real", simplified])
  1554     apply (rule continuous_on_eq [where f = "\<lambda>x. f(linepath a b x)*(b - a)"])
  1555     apply (auto simp: vector_derivative_linepath_within)
  1556     done
  1557 qed
  1558 
  1559 lemma has_field_der_id: "((\<lambda>x. x\<^sup>2 / 2) has_field_derivative x) (at x)"
  1560   by (rule has_derivative_imp_has_field_derivative)
  1561      (rule derivative_intros | simp)+
  1562 
  1563 lemma contour_integral_id [simp]: "contour_integral (linepath a b) (\<lambda>y. y) = (b^2 - a^2)/2"
  1564   apply (rule contour_integral_unique)
  1565   using contour_integral_primitive [of UNIV "\<lambda>x. x^2/2" "\<lambda>x. x" "linepath a b"]
  1566   apply (auto simp: field_simps has_field_der_id)
  1567   done
  1568 
  1569 lemma contour_integrable_on_const [iff]: "(\<lambda>x. c) contour_integrable_on (linepath a b)"
  1570   by (simp add: continuous_on_const contour_integrable_continuous_linepath)
  1571 
  1572 lemma contour_integrable_on_id [iff]: "(\<lambda>x. x) contour_integrable_on (linepath a b)"
  1573   by (simp add: continuous_on_id contour_integrable_continuous_linepath)
  1574 
  1575 
  1576 subsection\<open>Arithmetical combining theorems\<close>
  1577 
  1578 lemma has_contour_integral_neg:
  1579     "(f has_contour_integral i) g \<Longrightarrow> ((\<lambda>x. -(f x)) has_contour_integral (-i)) g"
  1580   by (simp add: has_integral_neg has_contour_integral_def)
  1581 
  1582 lemma has_contour_integral_add:
  1583     "\<lbrakk>(f1 has_contour_integral i1) g; (f2 has_contour_integral i2) g\<rbrakk>
  1584      \<Longrightarrow> ((\<lambda>x. f1 x + f2 x) has_contour_integral (i1 + i2)) g"
  1585   by (simp add: has_integral_add has_contour_integral_def algebra_simps)
  1586 
  1587 lemma has_contour_integral_diff:
  1588   "\<lbrakk>(f1 has_contour_integral i1) g; (f2 has_contour_integral i2) g\<rbrakk>
  1589          \<Longrightarrow> ((\<lambda>x. f1 x - f2 x) has_contour_integral (i1 - i2)) g"
  1590   by (simp add: has_integral_diff has_contour_integral_def algebra_simps)
  1591 
  1592 lemma has_contour_integral_lmul:
  1593   "(f has_contour_integral i) g \<Longrightarrow> ((\<lambda>x. c * (f x)) has_contour_integral (c*i)) g"
  1594 apply (simp add: has_contour_integral_def)
  1595 apply (drule has_integral_mult_right)
  1596 apply (simp add: algebra_simps)
  1597 done
  1598 
  1599 lemma has_contour_integral_rmul:
  1600   "(f has_contour_integral i) g \<Longrightarrow> ((\<lambda>x. (f x) * c) has_contour_integral (i*c)) g"
  1601 apply (drule has_contour_integral_lmul)
  1602 apply (simp add: mult.commute)
  1603 done
  1604 
  1605 lemma has_contour_integral_div:
  1606   "(f has_contour_integral i) g \<Longrightarrow> ((\<lambda>x. f x/c) has_contour_integral (i/c)) g"
  1607   by (simp add: field_class.field_divide_inverse) (metis has_contour_integral_rmul)
  1608 
  1609 lemma has_contour_integral_eq:
  1610     "\<lbrakk>(f has_contour_integral y) p; \<And>x. x \<in> path_image p \<Longrightarrow> f x = g x\<rbrakk> \<Longrightarrow> (g has_contour_integral y) p"
  1611 apply (simp add: path_image_def has_contour_integral_def)
  1612 by (metis (no_types, lifting) image_eqI has_integral_eq)
  1613 
  1614 lemma has_contour_integral_bound_linepath:
  1615   assumes "(f has_contour_integral i) (linepath a b)"
  1616           "0 \<le> B" "\<And>x. x \<in> closed_segment a b \<Longrightarrow> norm(f x) \<le> B"
  1617     shows "norm i \<le> B * norm(b - a)"
  1618 proof -
  1619   { fix x::real
  1620     assume x: "0 \<le> x" "x \<le> 1"
  1621   have "norm (f (linepath a b x)) *
  1622         norm (vector_derivative (linepath a b) (at x within {0..1})) \<le> B * norm (b - a)"
  1623     by (auto intro: mult_mono simp: assms linepath_in_path of_real_linepath vector_derivative_linepath_within x)
  1624   } note * = this
  1625   have "norm i \<le> (B * norm (b - a)) * content (cbox 0 (1::real))"
  1626     apply (rule has_integral_bound
  1627        [of _ "\<lambda>x. f (linepath a b x) * vector_derivative (linepath a b) (at x within {0..1})"])
  1628     using assms * unfolding has_contour_integral_def
  1629     apply (auto simp: norm_mult)
  1630     done
  1631   then show ?thesis
  1632     by (auto simp: content_real)
  1633 qed
  1634 
  1635 (*UNUSED
  1636 lemma has_contour_integral_bound_linepath_strong:
  1637   fixes a :: real and f :: "complex \<Rightarrow> real"
  1638   assumes "(f has_contour_integral i) (linepath a b)"
  1639           "finite k"
  1640           "0 \<le> B" "\<And>x::real. x \<in> closed_segment a b - k \<Longrightarrow> norm(f x) \<le> B"
  1641     shows "norm i \<le> B*norm(b - a)"
  1642 *)
  1643 
  1644 lemma has_contour_integral_const_linepath: "((\<lambda>x. c) has_contour_integral c*(b - a))(linepath a b)"
  1645   unfolding has_contour_integral_linepath
  1646   by (metis content_real diff_0_right has_integral_const_real lambda_one of_real_1 scaleR_conv_of_real zero_le_one)
  1647 
  1648 lemma has_contour_integral_0: "((\<lambda>x. 0) has_contour_integral 0) g"
  1649   by (simp add: has_contour_integral_def)
  1650 
  1651 lemma has_contour_integral_is_0:
  1652     "(\<And>z. z \<in> path_image g \<Longrightarrow> f z = 0) \<Longrightarrow> (f has_contour_integral 0) g"
  1653   by (rule has_contour_integral_eq [OF has_contour_integral_0]) auto
  1654 
  1655 lemma has_contour_integral_sum:
  1656     "\<lbrakk>finite s; \<And>a. a \<in> s \<Longrightarrow> (f a has_contour_integral i a) p\<rbrakk>
  1657      \<Longrightarrow> ((\<lambda>x. sum (\<lambda>a. f a x) s) has_contour_integral sum i s) p"
  1658   by (induction s rule: finite_induct) (auto simp: has_contour_integral_0 has_contour_integral_add)
  1659 
  1660 
  1661 subsection \<open>Operations on path integrals\<close>
  1662 
  1663 lemma contour_integral_const_linepath [simp]: "contour_integral (linepath a b) (\<lambda>x. c) = c*(b - a)"
  1664   by (rule contour_integral_unique [OF has_contour_integral_const_linepath])
  1665 
  1666 lemma contour_integral_neg:
  1667     "f contour_integrable_on g \<Longrightarrow> contour_integral g (\<lambda>x. -(f x)) = -(contour_integral g f)"
  1668   by (simp add: contour_integral_unique has_contour_integral_integral has_contour_integral_neg)
  1669 
  1670 lemma contour_integral_add:
  1671     "f1 contour_integrable_on g \<Longrightarrow> f2 contour_integrable_on g \<Longrightarrow> contour_integral g (\<lambda>x. f1 x + f2 x) =
  1672                 contour_integral g f1 + contour_integral g f2"
  1673   by (simp add: contour_integral_unique has_contour_integral_integral has_contour_integral_add)
  1674 
  1675 lemma contour_integral_diff:
  1676     "f1 contour_integrable_on g \<Longrightarrow> f2 contour_integrable_on g \<Longrightarrow> contour_integral g (\<lambda>x. f1 x - f2 x) =
  1677                 contour_integral g f1 - contour_integral g f2"
  1678   by (simp add: contour_integral_unique has_contour_integral_integral has_contour_integral_diff)
  1679 
  1680 lemma contour_integral_lmul:
  1681   shows "f contour_integrable_on g
  1682            \<Longrightarrow> contour_integral g (\<lambda>x. c * f x) = c*contour_integral g f"
  1683   by (simp add: contour_integral_unique has_contour_integral_integral has_contour_integral_lmul)
  1684 
  1685 lemma contour_integral_rmul:
  1686   shows "f contour_integrable_on g
  1687         \<Longrightarrow> contour_integral g (\<lambda>x. f x * c) = contour_integral g f * c"
  1688   by (simp add: contour_integral_unique has_contour_integral_integral has_contour_integral_rmul)
  1689 
  1690 lemma contour_integral_div:
  1691   shows "f contour_integrable_on g
  1692         \<Longrightarrow> contour_integral g (\<lambda>x. f x / c) = contour_integral g f / c"
  1693   by (simp add: contour_integral_unique has_contour_integral_integral has_contour_integral_div)
  1694 
  1695 lemma contour_integral_eq:
  1696     "(\<And>x. x \<in> path_image p \<Longrightarrow> f x = g x) \<Longrightarrow> contour_integral p f = contour_integral p g"
  1697   apply (simp add: contour_integral_def)
  1698   using has_contour_integral_eq
  1699   by (metis contour_integral_unique has_contour_integral_integrable has_contour_integral_integral)
  1700 
  1701 lemma contour_integral_eq_0:
  1702     "(\<And>z. z \<in> path_image g \<Longrightarrow> f z = 0) \<Longrightarrow> contour_integral g f = 0"
  1703   by (simp add: has_contour_integral_is_0 contour_integral_unique)
  1704 
  1705 lemma contour_integral_bound_linepath:
  1706   shows
  1707     "\<lbrakk>f contour_integrable_on (linepath a b);
  1708       0 \<le> B; \<And>x. x \<in> closed_segment a b \<Longrightarrow> norm(f x) \<le> B\<rbrakk>
  1709      \<Longrightarrow> norm(contour_integral (linepath a b) f) \<le> B*norm(b - a)"
  1710   apply (rule has_contour_integral_bound_linepath [of f])
  1711   apply (auto simp: has_contour_integral_integral)
  1712   done
  1713 
  1714 lemma contour_integral_0 [simp]: "contour_integral g (\<lambda>x. 0) = 0"
  1715   by (simp add: contour_integral_unique has_contour_integral_0)
  1716 
  1717 lemma contour_integral_sum:
  1718     "\<lbrakk>finite s; \<And>a. a \<in> s \<Longrightarrow> (f a) contour_integrable_on p\<rbrakk>
  1719      \<Longrightarrow> contour_integral p (\<lambda>x. sum (\<lambda>a. f a x) s) = sum (\<lambda>a. contour_integral p (f a)) s"
  1720   by (auto simp: contour_integral_unique has_contour_integral_sum has_contour_integral_integral)
  1721 
  1722 lemma contour_integrable_eq:
  1723     "\<lbrakk>f contour_integrable_on p; \<And>x. x \<in> path_image p \<Longrightarrow> f x = g x\<rbrakk> \<Longrightarrow> g contour_integrable_on p"
  1724   unfolding contour_integrable_on_def
  1725   by (metis has_contour_integral_eq)
  1726 
  1727 
  1728 subsection \<open>Arithmetic theorems for path integrability\<close>
  1729 
  1730 lemma contour_integrable_neg:
  1731     "f contour_integrable_on g \<Longrightarrow> (\<lambda>x. -(f x)) contour_integrable_on g"
  1732   using has_contour_integral_neg contour_integrable_on_def by blast
  1733 
  1734 lemma contour_integrable_add:
  1735     "\<lbrakk>f1 contour_integrable_on g; f2 contour_integrable_on g\<rbrakk> \<Longrightarrow> (\<lambda>x. f1 x + f2 x) contour_integrable_on g"
  1736   using has_contour_integral_add contour_integrable_on_def
  1737   by fastforce
  1738 
  1739 lemma contour_integrable_diff:
  1740     "\<lbrakk>f1 contour_integrable_on g; f2 contour_integrable_on g\<rbrakk> \<Longrightarrow> (\<lambda>x. f1 x - f2 x) contour_integrable_on g"
  1741   using has_contour_integral_diff contour_integrable_on_def
  1742   by fastforce
  1743 
  1744 lemma contour_integrable_lmul:
  1745     "f contour_integrable_on g \<Longrightarrow> (\<lambda>x. c * f x) contour_integrable_on g"
  1746   using has_contour_integral_lmul contour_integrable_on_def
  1747   by fastforce
  1748 
  1749 lemma contour_integrable_rmul:
  1750     "f contour_integrable_on g \<Longrightarrow> (\<lambda>x. f x * c) contour_integrable_on g"
  1751   using has_contour_integral_rmul contour_integrable_on_def
  1752   by fastforce
  1753 
  1754 lemma contour_integrable_div:
  1755     "f contour_integrable_on g \<Longrightarrow> (\<lambda>x. f x / c) contour_integrable_on g"
  1756   using has_contour_integral_div contour_integrable_on_def
  1757   by fastforce
  1758 
  1759 lemma contour_integrable_sum:
  1760     "\<lbrakk>finite s; \<And>a. a \<in> s \<Longrightarrow> (f a) contour_integrable_on p\<rbrakk>
  1761      \<Longrightarrow> (\<lambda>x. sum (\<lambda>a. f a x) s) contour_integrable_on p"
  1762    unfolding contour_integrable_on_def
  1763    by (metis has_contour_integral_sum)
  1764 
  1765 
  1766 subsection\<open>Reversing a path integral\<close>
  1767 
  1768 lemma has_contour_integral_reverse_linepath:
  1769     "(f has_contour_integral i) (linepath a b)
  1770      \<Longrightarrow> (f has_contour_integral (-i)) (linepath b a)"
  1771   using has_contour_integral_reversepath valid_path_linepath by fastforce
  1772 
  1773 lemma contour_integral_reverse_linepath:
  1774     "continuous_on (closed_segment a b) f
  1775      \<Longrightarrow> contour_integral (linepath a b) f = - (contour_integral(linepath b a) f)"
  1776 apply (rule contour_integral_unique)
  1777 apply (rule has_contour_integral_reverse_linepath)
  1778 by (simp add: closed_segment_commute contour_integrable_continuous_linepath has_contour_integral_integral)
  1779 
  1780 
  1781 (* Splitting a path integral in a flat way.*)
  1782 
  1783 lemma has_contour_integral_split:
  1784   assumes f: "(f has_contour_integral i) (linepath a c)" "(f has_contour_integral j) (linepath c b)"
  1785       and k: "0 \<le> k" "k \<le> 1"
  1786       and c: "c - a = k *\<^sub>R (b - a)"
  1787     shows "(f has_contour_integral (i + j)) (linepath a b)"
  1788 proof (cases "k = 0 \<or> k = 1")
  1789   case True
  1790   then show ?thesis
  1791     using assms by auto
  1792 next
  1793   case False
  1794   then have k: "0 < k" "k < 1" "complex_of_real k \<noteq> 1"
  1795     using assms by auto
  1796   have c': "c = k *\<^sub>R (b - a) + a"
  1797     by (metis diff_add_cancel c)
  1798   have bc: "(b - c) = (1 - k) *\<^sub>R (b - a)"
  1799     by (simp add: algebra_simps c')
  1800   { assume *: "((\<lambda>x. f ((1 - x) *\<^sub>R a + x *\<^sub>R c) * (c - a)) has_integral i) {0..1}"
  1801     have **: "\<And>x. ((k - x) / k) *\<^sub>R a + (x / k) *\<^sub>R c = (1 - x) *\<^sub>R a + x *\<^sub>R b"
  1802       using False apply (simp add: c' algebra_simps)
  1803       apply (simp add: real_vector.scale_left_distrib [symmetric] divide_simps)
  1804       done
  1805     have "((\<lambda>x. f ((1 - x) *\<^sub>R a + x *\<^sub>R b) * (b - a)) has_integral i) {0..k}"
  1806       using k has_integral_affinity01 [OF *, of "inverse k" "0"]
  1807       apply (simp add: divide_simps mult.commute [of _ "k"] image_affinity_atLeastAtMost ** c)
  1808       apply (auto dest: has_integral_cmul [where c = "inverse k"])
  1809       done
  1810   } note fi = this
  1811   { assume *: "((\<lambda>x. f ((1 - x) *\<^sub>R c + x *\<^sub>R b) * (b - c)) has_integral j) {0..1}"
  1812     have **: "\<And>x. (((1 - x) / (1 - k)) *\<^sub>R c + ((x - k) / (1 - k)) *\<^sub>R b) = ((1 - x) *\<^sub>R a + x *\<^sub>R b)"
  1813       using k
  1814       apply (simp add: c' field_simps)
  1815       apply (simp add: scaleR_conv_of_real divide_simps)
  1816       apply (simp add: field_simps)
  1817       done
  1818     have "((\<lambda>x. f ((1 - x) *\<^sub>R a + x *\<^sub>R b) * (b - a)) has_integral j) {k..1}"
  1819       using k has_integral_affinity01 [OF *, of "inverse(1 - k)" "-(k/(1 - k))"]
  1820       apply (simp add: divide_simps mult.commute [of _ "1-k"] image_affinity_atLeastAtMost ** bc)
  1821       apply (auto dest: has_integral_cmul [where k = "(1 - k) *\<^sub>R j" and c = "inverse (1 - k)"])
  1822       done
  1823   } note fj = this
  1824   show ?thesis
  1825     using f k
  1826     apply (simp add: has_contour_integral_linepath)
  1827     apply (simp add: linepath_def)
  1828     apply (rule has_integral_combine [OF _ _ fi fj], simp_all)
  1829     done
  1830 qed
  1831 
  1832 lemma continuous_on_closed_segment_transform:
  1833   assumes f: "continuous_on (closed_segment a b) f"
  1834       and k: "0 \<le> k" "k \<le> 1"
  1835       and c: "c - a = k *\<^sub>R (b - a)"
  1836     shows "continuous_on (closed_segment a c) f"
  1837 proof -
  1838   have c': "c = (1 - k) *\<^sub>R a + k *\<^sub>R b"
  1839     using c by (simp add: algebra_simps)
  1840   have "closed_segment a c \<subseteq> closed_segment a b"
  1841     by (metis c' ends_in_segment(1) in_segment(1) k subset_closed_segment)
  1842   then show "continuous_on (closed_segment a c) f"
  1843     by (rule continuous_on_subset [OF f])
  1844 qed
  1845 
  1846 lemma contour_integral_split:
  1847   assumes f: "continuous_on (closed_segment a b) f"
  1848       and k: "0 \<le> k" "k \<le> 1"
  1849       and c: "c - a = k *\<^sub>R (b - a)"
  1850     shows "contour_integral(linepath a b) f = contour_integral(linepath a c) f + contour_integral(linepath c b) f"
  1851 proof -
  1852   have c': "c = (1 - k) *\<^sub>R a + k *\<^sub>R b"
  1853     using c by (simp add: algebra_simps)
  1854   have "closed_segment a c \<subseteq> closed_segment a b"
  1855     by (metis c' ends_in_segment(1) in_segment(1) k subset_closed_segment)
  1856   moreover have "closed_segment c b \<subseteq> closed_segment a b"
  1857     by (metis c' ends_in_segment(2) in_segment(1) k subset_closed_segment)
  1858   ultimately
  1859   have *: "continuous_on (closed_segment a c) f" "continuous_on (closed_segment c b) f"
  1860     by (auto intro: continuous_on_subset [OF f])
  1861   show ?thesis
  1862     by (rule contour_integral_unique) (meson "*" c contour_integrable_continuous_linepath has_contour_integral_integral has_contour_integral_split k)
  1863 qed
  1864 
  1865 lemma contour_integral_split_linepath:
  1866   assumes f: "continuous_on (closed_segment a b) f"
  1867       and c: "c \<in> closed_segment a b"
  1868     shows "contour_integral(linepath a b) f = contour_integral(linepath a c) f + contour_integral(linepath c b) f"
  1869   using c by (auto simp: closed_segment_def algebra_simps intro!: contour_integral_split [OF f])
  1870 
  1871 text\<open>The special case of midpoints used in the main quadrisection\<close>
  1872 
  1873 lemma has_contour_integral_midpoint:
  1874   assumes "(f has_contour_integral i) (linepath a (midpoint a b))"
  1875           "(f has_contour_integral j) (linepath (midpoint a b) b)"
  1876     shows "(f has_contour_integral (i + j)) (linepath a b)"
  1877   apply (rule has_contour_integral_split [where c = "midpoint a b" and k = "1/2"])
  1878   using assms
  1879   apply (auto simp: midpoint_def algebra_simps scaleR_conv_of_real)
  1880   done
  1881 
  1882 lemma contour_integral_midpoint:
  1883    "continuous_on (closed_segment a b) f
  1884     \<Longrightarrow> contour_integral (linepath a b) f =
  1885         contour_integral (linepath a (midpoint a b)) f + contour_integral (linepath (midpoint a b) b) f"
  1886   apply (rule contour_integral_split [where c = "midpoint a b" and k = "1/2"])
  1887   apply (auto simp: midpoint_def algebra_simps scaleR_conv_of_real)
  1888   done
  1889 
  1890 
  1891 text\<open>A couple of special case lemmas that are useful below\<close>
  1892 
  1893 lemma triangle_linear_has_chain_integral:
  1894     "((\<lambda>x. m*x + d) has_contour_integral 0) (linepath a b +++ linepath b c +++ linepath c a)"
  1895   apply (rule Cauchy_theorem_primitive [of UNIV "\<lambda>x. m/2 * x^2 + d*x"])
  1896   apply (auto intro!: derivative_eq_intros)
  1897   done
  1898 
  1899 lemma has_chain_integral_chain_integral3:
  1900      "(f has_contour_integral i) (linepath a b +++ linepath b c +++ linepath c d)
  1901       \<Longrightarrow> contour_integral (linepath a b) f + contour_integral (linepath b c) f + contour_integral (linepath c d) f = i"
  1902   apply (subst contour_integral_unique [symmetric], assumption)
  1903   apply (drule has_contour_integral_integrable)
  1904   apply (simp add: valid_path_join)
  1905   done
  1906 
  1907 lemma has_chain_integral_chain_integral4:
  1908      "(f has_contour_integral i) (linepath a b +++ linepath b c +++ linepath c d +++ linepath d e)
  1909       \<Longrightarrow> contour_integral (linepath a b) f + contour_integral (linepath b c) f + contour_integral (linepath c d) f + contour_integral (linepath d e) f = i"
  1910   apply (subst contour_integral_unique [symmetric], assumption)
  1911   apply (drule has_contour_integral_integrable)
  1912   apply (simp add: valid_path_join)
  1913   done
  1914 
  1915 subsection\<open>Reversing the order in a double path integral\<close>
  1916 
  1917 text\<open>The condition is stronger than needed but it's often true in typical situations\<close>
  1918 
  1919 lemma fst_im_cbox [simp]: "cbox c d \<noteq> {} \<Longrightarrow> (fst ` cbox (a,c) (b,d)) = cbox a b"
  1920   by (auto simp: cbox_Pair_eq)
  1921 
  1922 lemma snd_im_cbox [simp]: "cbox a b \<noteq> {} \<Longrightarrow> (snd ` cbox (a,c) (b,d)) = cbox c d"
  1923   by (auto simp: cbox_Pair_eq)
  1924 
  1925 lemma contour_integral_swap:
  1926   assumes fcon:  "continuous_on (path_image g \<times> path_image h) (\<lambda>(y1,y2). f y1 y2)"
  1927       and vp:    "valid_path g" "valid_path h"
  1928       and gvcon: "continuous_on {0..1} (\<lambda>t. vector_derivative g (at t))"
  1929       and hvcon: "continuous_on {0..1} (\<lambda>t. vector_derivative h (at t))"
  1930   shows "contour_integral g (\<lambda>w. contour_integral h (f w)) =
  1931          contour_integral h (\<lambda>z. contour_integral g (\<lambda>w. f w z))"
  1932 proof -
  1933   have gcon: "continuous_on {0..1} g" and hcon: "continuous_on {0..1} h"
  1934     using assms by (auto simp: valid_path_def piecewise_C1_differentiable_on_def)
  1935   have fgh1: "\<And>x. (\<lambda>t. f (g x) (h t)) = (\<lambda>(y1,y2). f y1 y2) \<circ> (\<lambda>t. (g x, h t))"
  1936     by (rule ext) simp
  1937   have fgh2: "\<And>x. (\<lambda>t. f (g t) (h x)) = (\<lambda>(y1,y2). f y1 y2) \<circ> (\<lambda>t. (g t, h x))"
  1938     by (rule ext) simp
  1939   have fcon_im1: "\<And>x. 0 \<le> x \<Longrightarrow> x \<le> 1 \<Longrightarrow> continuous_on ((\<lambda>t. (g x, h t)) ` {0..1}) (\<lambda>(x, y). f x y)"
  1940     by (rule continuous_on_subset [OF fcon]) (auto simp: path_image_def)
  1941   have fcon_im2: "\<And>x. 0 \<le> x \<Longrightarrow> x \<le> 1 \<Longrightarrow> continuous_on ((\<lambda>t. (g t, h x)) ` {0..1}) (\<lambda>(x, y). f x y)"
  1942     by (rule continuous_on_subset [OF fcon]) (auto simp: path_image_def)
  1943   have "\<And>y. y \<in> {0..1} \<Longrightarrow> continuous_on {0..1} (\<lambda>x. f (g x) (h y))"
  1944     by (subst fgh2) (rule fcon_im2 gcon continuous_intros | simp)+
  1945   then have vdg: "\<And>y. y \<in> {0..1} \<Longrightarrow> (\<lambda>x. f (g x) (h y) * vector_derivative g (at x)) integrable_on {0..1}"
  1946     using continuous_on_mult gvcon integrable_continuous_real by blast
  1947   have "(\<lambda>z. vector_derivative g (at (fst z))) = (\<lambda>x. vector_derivative g (at x)) \<circ> fst"
  1948     by auto
  1949   then have gvcon': "continuous_on (cbox (0, 0) (1, 1::real)) (\<lambda>x. vector_derivative g (at (fst x)))"
  1950     apply (rule ssubst)
  1951     apply (rule continuous_intros | simp add: gvcon)+
  1952     done
  1953   have "(\<lambda>z. vector_derivative h (at (snd z))) = (\<lambda>x. vector_derivative h (at x)) \<circ> snd"
  1954     by auto
  1955   then have hvcon': "continuous_on (cbox (0, 0) (1::real, 1)) (\<lambda>x. vector_derivative h (at (snd x)))"
  1956     apply (rule ssubst)
  1957     apply (rule continuous_intros | simp add: hvcon)+
  1958     done
  1959   have "(\<lambda>x. f (g (fst x)) (h (snd x))) = (\<lambda>(y1,y2). f y1 y2) \<circ> (\<lambda>w. ((g \<circ> fst) w, (h \<circ> snd) w))"
  1960     by auto
  1961   then have fgh: "continuous_on (cbox (0, 0) (1, 1)) (\<lambda>x. f (g (fst x)) (h (snd x)))"
  1962     apply (rule ssubst)
  1963     apply (rule gcon hcon continuous_intros | simp)+
  1964     apply (auto simp: path_image_def intro: continuous_on_subset [OF fcon])
  1965     done
  1966   have "integral {0..1} (\<lambda>x. contour_integral h (f (g x)) * vector_derivative g (at x)) =
  1967         integral {0..1} (\<lambda>x. contour_integral h (\<lambda>y. f (g x) y * vector_derivative g (at x)))"
  1968   proof (rule integral_cong [OF contour_integral_rmul [symmetric]])
  1969     show "\<And>x. x \<in> {0..1} \<Longrightarrow> f (g x) contour_integrable_on h"
  1970       unfolding contour_integrable_on
  1971     apply (rule integrable_continuous_real)
  1972     apply (rule continuous_on_mult [OF _ hvcon])
  1973     apply (subst fgh1)
  1974     apply (rule fcon_im1 hcon continuous_intros | simp)+
  1975       done
  1976   qed
  1977   also have "\<dots> = integral {0..1}
  1978                      (\<lambda>y. contour_integral g (\<lambda>x. f x (h y) * vector_derivative h (at y)))"
  1979     unfolding contour_integral_integral
  1980     apply (subst integral_swap_continuous [where 'a = real and 'b = real, of 0 0 1 1, simplified])
  1981      apply (rule fgh gvcon' hvcon' continuous_intros | simp add: split_def)+
  1982     unfolding integral_mult_left [symmetric]
  1983     apply (simp only: mult_ac)
  1984     done
  1985   also have "\<dots> = contour_integral h (\<lambda>z. contour_integral g (\<lambda>w. f w z))"
  1986     unfolding contour_integral_integral
  1987     apply (rule integral_cong)
  1988     unfolding integral_mult_left [symmetric]
  1989     apply (simp add: algebra_simps)
  1990     done
  1991   finally show ?thesis
  1992     by (simp add: contour_integral_integral)
  1993 qed
  1994 
  1995 
  1996 subsection\<open>The key quadrisection step\<close>
  1997 
  1998 lemma norm_sum_half:
  1999   assumes "norm(a + b) \<ge> e"
  2000     shows "norm a \<ge> e/2 \<or> norm b \<ge> e/2"
  2001 proof -
  2002   have "e \<le> norm (- a - b)"
  2003     by (simp add: add.commute assms norm_minus_commute)
  2004   thus ?thesis
  2005     using norm_triangle_ineq4 order_trans by fastforce
  2006 qed
  2007 
  2008 lemma norm_sum_lemma:
  2009   assumes "e \<le> norm (a + b + c + d)"
  2010     shows "e / 4 \<le> norm a \<or> e / 4 \<le> norm b \<or> e / 4 \<le> norm c \<or> e / 4 \<le> norm d"
  2011 proof -
  2012   have "e \<le> norm ((a + b) + (c + d))" using assms
  2013     by (simp add: algebra_simps)
  2014   then show ?thesis
  2015     by (auto dest!: norm_sum_half)
  2016 qed
  2017 
  2018 lemma Cauchy_theorem_quadrisection:
  2019   assumes f: "continuous_on (convex hull {a,b,c}) f"
  2020       and dist: "dist a b \<le> K" "dist b c \<le> K" "dist c a \<le> K"
  2021       and e: "e * K^2 \<le>
  2022               norm (contour_integral(linepath a b) f + contour_integral(linepath b c) f + contour_integral(linepath c a) f)"
  2023   shows "\<exists>a' b' c'.
  2024            a' \<in> convex hull {a,b,c} \<and> b' \<in> convex hull {a,b,c} \<and> c' \<in> convex hull {a,b,c} \<and>
  2025            dist a' b' \<le> K/2  \<and>  dist b' c' \<le> K/2  \<and>  dist c' a' \<le> K/2  \<and>
  2026            e * (K/2)^2 \<le> norm(contour_integral(linepath a' b') f + contour_integral(linepath b' c') f + contour_integral(linepath c' a') f)"
  2027          (is "\<exists>x y z. ?\<Phi> x y z")
  2028 proof -
  2029   note divide_le_eq_numeral1 [simp del]
  2030   define a' where "a' = midpoint b c"
  2031   define b' where "b' = midpoint c a"
  2032   define c' where "c' = midpoint a b"
  2033   have fabc: "continuous_on (closed_segment a b) f" "continuous_on (closed_segment b c) f" "continuous_on (closed_segment c a) f"
  2034     using f continuous_on_subset segments_subset_convex_hull by metis+
  2035   have fcont': "continuous_on (closed_segment c' b') f"
  2036                "continuous_on (closed_segment a' c') f"
  2037                "continuous_on (closed_segment b' a') f"
  2038     unfolding a'_def b'_def c'_def
  2039     by (rule continuous_on_subset [OF f],
  2040            metis midpoints_in_convex_hull convex_hull_subset hull_subset insert_subset segment_convex_hull)+
  2041   let ?pathint = "\<lambda>x y. contour_integral(linepath x y) f"
  2042   have *: "?pathint a b + ?pathint b c + ?pathint c a =
  2043           (?pathint a c' + ?pathint c' b' + ?pathint b' a) +
  2044           (?pathint a' c' + ?pathint c' b + ?pathint b a') +
  2045           (?pathint a' c + ?pathint c b' + ?pathint b' a') +
  2046           (?pathint a' b' + ?pathint b' c' + ?pathint c' a')"
  2047     by (simp add: fcont' contour_integral_reverse_linepath) (simp add: a'_def b'_def c'_def contour_integral_midpoint fabc)
  2048   have [simp]: "\<And>x y. cmod (x * 2 - y * 2) = cmod (x - y) * 2"
  2049     by (metis left_diff_distrib mult.commute norm_mult_numeral1)
  2050   have [simp]: "\<And>x y. cmod (x - y) = cmod (y - x)"
  2051     by (simp add: norm_minus_commute)
  2052   consider "e * K\<^sup>2 / 4 \<le> cmod (?pathint a c' + ?pathint c' b' + ?pathint b' a)" |
  2053            "e * K\<^sup>2 / 4 \<le> cmod (?pathint a' c' + ?pathint c' b + ?pathint b a')" |
  2054            "e * K\<^sup>2 / 4 \<le> cmod (?pathint a' c + ?pathint c b' + ?pathint b' a')" |
  2055            "e * K\<^sup>2 / 4 \<le> cmod (?pathint a' b' + ?pathint b' c' + ?pathint c' a')"
  2056     using assms unfolding * by (blast intro: that dest!: norm_sum_lemma)
  2057   then show ?thesis
  2058   proof cases
  2059     case 1 then have "?\<Phi> a c' b'"
  2060       using assms
  2061       apply (clarsimp simp: c'_def b'_def midpoints_in_convex_hull hull_subset [THEN subsetD])
  2062       apply (auto simp: midpoint_def dist_norm scaleR_conv_of_real divide_simps)
  2063       done
  2064     then show ?thesis by blast
  2065   next
  2066     case 2 then  have "?\<Phi> a' c' b"
  2067       using assms
  2068       apply (clarsimp simp: a'_def c'_def midpoints_in_convex_hull hull_subset [THEN subsetD])
  2069       apply (auto simp: midpoint_def dist_norm scaleR_conv_of_real divide_simps)
  2070       done
  2071     then show ?thesis by blast
  2072   next
  2073     case 3 then have "?\<Phi> a' c b'"
  2074       using assms
  2075       apply (clarsimp simp: a'_def b'_def midpoints_in_convex_hull hull_subset [THEN subsetD])
  2076       apply (auto simp: midpoint_def dist_norm scaleR_conv_of_real divide_simps)
  2077       done
  2078     then show ?thesis by blast
  2079   next
  2080     case 4 then have "?\<Phi> a' b' c'"
  2081       using assms
  2082       apply (clarsimp simp: a'_def c'_def b'_def midpoints_in_convex_hull hull_subset [THEN subsetD])
  2083       apply (auto simp: midpoint_def dist_norm scaleR_conv_of_real divide_simps)
  2084       done
  2085     then show ?thesis by blast
  2086   qed
  2087 qed
  2088 
  2089 subsection\<open>Cauchy's theorem for triangles\<close>
  2090 
  2091 lemma triangle_points_closer:
  2092   fixes a::complex
  2093   shows "\<lbrakk>x \<in> convex hull {a,b,c};  y \<in> convex hull {a,b,c}\<rbrakk>
  2094          \<Longrightarrow> norm(x - y) \<le> norm(a - b) \<or>
  2095              norm(x - y) \<le> norm(b - c) \<or>
  2096              norm(x - y) \<le> norm(c - a)"
  2097   using simplex_extremal_le [of "{a,b,c}"]
  2098   by (auto simp: norm_minus_commute)
  2099 
  2100 lemma holomorphic_point_small_triangle:
  2101   assumes x: "x \<in> S"
  2102       and f: "continuous_on S f"
  2103       and cd: "f field_differentiable (at x within S)"
  2104       and e: "0 < e"
  2105     shows "\<exists>k>0. \<forall>a b c. dist a b \<le> k \<and> dist b c \<le> k \<and> dist c a \<le> k \<and>
  2106               x \<in> convex hull {a,b,c} \<and> convex hull {a,b,c} \<subseteq> S
  2107               \<longrightarrow> norm(contour_integral(linepath a b) f + contour_integral(linepath b c) f +
  2108                        contour_integral(linepath c a) f)
  2109                   \<le> e*(dist a b + dist b c + dist c a)^2"
  2110            (is "\<exists>k>0. \<forall>a b c. _ \<longrightarrow> ?normle a b c")
  2111 proof -
  2112   have le_of_3: "\<And>a x y z. \<lbrakk>0 \<le> x*y; 0 \<le> x*z; 0 \<le> y*z; a \<le> (e*(x + y + z))*x + (e*(x + y + z))*y + (e*(x + y + z))*z\<rbrakk>
  2113                      \<Longrightarrow> a \<le> e*(x + y + z)^2"
  2114     by (simp add: algebra_simps power2_eq_square)
  2115   have disj_le: "\<lbrakk>x \<le> a \<or> x \<le> b \<or> x \<le> c; 0 \<le> a; 0 \<le> b; 0 \<le> c\<rbrakk> \<Longrightarrow> x \<le> a + b + c"
  2116              for x::real and a b c
  2117     by linarith
  2118   have fabc: "f contour_integrable_on linepath a b" "f contour_integrable_on linepath b c" "f contour_integrable_on linepath c a"
  2119               if "convex hull {a, b, c} \<subseteq> S" for a b c
  2120     using segments_subset_convex_hull that
  2121     by (metis continuous_on_subset f contour_integrable_continuous_linepath)+
  2122   note path_bound = has_contour_integral_bound_linepath [simplified norm_minus_commute, OF has_contour_integral_integral]
  2123   { fix f' a b c d
  2124     assume d: "0 < d"
  2125        and f': "\<And>y. \<lbrakk>cmod (y - x) \<le> d; y \<in> S\<rbrakk> \<Longrightarrow> cmod (f y - f x - f' * (y - x)) \<le> e * cmod (y - x)"
  2126        and le: "cmod (a - b) \<le> d" "cmod (b - c) \<le> d" "cmod (c - a) \<le> d"
  2127        and xc: "x \<in> convex hull {a, b, c}"
  2128        and S: "convex hull {a, b, c} \<subseteq> S"
  2129     have pa: "contour_integral (linepath a b) f + contour_integral (linepath b c) f + contour_integral (linepath c a) f =
  2130               contour_integral (linepath a b) (\<lambda>y. f y - f x - f'*(y - x)) +
  2131               contour_integral (linepath b c) (\<lambda>y. f y - f x - f'*(y - x)) +
  2132               contour_integral (linepath c a) (\<lambda>y. f y - f x - f'*(y - x))"
  2133       apply (simp add: contour_integral_diff contour_integral_lmul contour_integrable_lmul contour_integrable_diff fabc [OF S])
  2134       apply (simp add: field_simps)
  2135       done
  2136     { fix y
  2137       assume yc: "y \<in> convex hull {a,b,c}"
  2138       have "cmod (f y - f x - f' * (y - x)) \<le> e*norm(y - x)"
  2139       proof (rule f')
  2140         show "cmod (y - x) \<le> d"
  2141           by (metis triangle_points_closer [OF xc yc] le norm_minus_commute order_trans)
  2142       qed (use S yc in blast)
  2143       also have "\<dots> \<le> e * (cmod (a - b) + cmod (b - c) + cmod (c - a))"
  2144         by (simp add: yc e xc disj_le [OF triangle_points_closer])
  2145       finally have "cmod (f y - f x - f' * (y - x)) \<le> e * (cmod (a - b) + cmod (b - c) + cmod (c - a))" .
  2146     } note cm_le = this
  2147     have "?normle a b c"
  2148       unfolding dist_norm pa
  2149       apply (rule le_of_3)
  2150       using f' xc S e
  2151       apply simp_all
  2152       apply (intro norm_triangle_le add_mono path_bound)
  2153       apply (simp_all add: contour_integral_diff contour_integral_lmul contour_integrable_lmul contour_integrable_diff fabc)
  2154       apply (blast intro: cm_le elim: dest: segments_subset_convex_hull [THEN subsetD])+
  2155       done
  2156   } note * = this
  2157   show ?thesis
  2158     using cd e 
  2159     apply (simp add: field_differentiable_def has_field_derivative_def has_derivative_within_alt approachable_lt_le2 Ball_def)
  2160     apply (clarify dest!: spec mp)
  2161     using * unfolding dist_norm
  2162     apply blast
  2163     done
  2164 qed
  2165 
  2166 
  2167 text\<open>Hence the most basic theorem for a triangle.\<close>
  2168 
  2169 locale Chain =
  2170   fixes x0 At Follows
  2171   assumes At0: "At x0 0"
  2172       and AtSuc: "\<And>x n. At x n \<Longrightarrow> \<exists>x'. At x' (Suc n) \<and> Follows x' x"
  2173 begin
  2174   primrec f where
  2175     "f 0 = x0"
  2176   | "f (Suc n) = (SOME x. At x (Suc n) \<and> Follows x (f n))"
  2177 
  2178   lemma At: "At (f n) n"
  2179   proof (induct n)
  2180     case 0 show ?case
  2181       by (simp add: At0)
  2182   next
  2183     case (Suc n) show ?case
  2184       by (metis (no_types, lifting) AtSuc [OF Suc] f.simps(2) someI_ex)
  2185   qed
  2186 
  2187   lemma Follows: "Follows (f(Suc n)) (f n)"
  2188     by (metis (no_types, lifting) AtSuc [OF At [of n]] f.simps(2) someI_ex)
  2189 
  2190   declare f.simps(2) [simp del]
  2191 end
  2192 
  2193 lemma Chain3:
  2194   assumes At0: "At x0 y0 z0 0"
  2195       and AtSuc: "\<And>x y z n. At x y z n \<Longrightarrow> \<exists>x' y' z'. At x' y' z' (Suc n) \<and> Follows x' y' z' x y z"
  2196   obtains f g h where
  2197     "f 0 = x0" "g 0 = y0" "h 0 = z0"
  2198                       "\<And>n. At (f n) (g n) (h n) n"
  2199                        "\<And>n. Follows (f(Suc n)) (g(Suc n)) (h(Suc n)) (f n) (g n) (h n)"
  2200 proof -
  2201   interpret three: Chain "(x0,y0,z0)" "\<lambda>(x,y,z). At x y z" "\<lambda>(x',y',z'). \<lambda>(x,y,z). Follows x' y' z' x y z"
  2202     apply unfold_locales
  2203     using At0 AtSuc by auto
  2204   show ?thesis
  2205   apply (rule that [of "\<lambda>n. fst (three.f n)"  "\<lambda>n. fst (snd (three.f n))" "\<lambda>n. snd (snd (three.f n))"])
  2206   using three.At three.Follows
  2207   apply simp_all
  2208   apply (simp_all add: split_beta')
  2209   done
  2210 qed
  2211 
  2212 proposition Cauchy_theorem_triangle:
  2213   assumes "f holomorphic_on (convex hull {a,b,c})"
  2214     shows "(f has_contour_integral 0) (linepath a b +++ linepath b c +++ linepath c a)"
  2215 proof -
  2216   have contf: "continuous_on (convex hull {a,b,c}) f"
  2217     by (metis assms holomorphic_on_imp_continuous_on)
  2218   let ?pathint = "\<lambda>x y. contour_integral(linepath x y) f"
  2219   { fix y::complex
  2220     assume fy: "(f has_contour_integral y) (linepath a b +++ linepath b c +++ linepath c a)"
  2221        and ynz: "y \<noteq> 0"
  2222     define K where "K = 1 + max (dist a b) (max (dist b c) (dist c a))"
  2223     define e where "e = norm y / K^2"
  2224     have K1: "K \<ge> 1"  by (simp add: K_def max.coboundedI1)
  2225     then have K: "K > 0" by linarith
  2226     have [iff]: "dist a b \<le> K" "dist b c \<le> K" "dist c a \<le> K"
  2227       by (simp_all add: K_def)
  2228     have e: "e > 0"
  2229       unfolding e_def using ynz K1 by simp
  2230     define At where "At x y z n \<longleftrightarrow>
  2231         convex hull {x,y,z} \<subseteq> convex hull {a,b,c} \<and>
  2232         dist x y \<le> K/2^n \<and> dist y z \<le> K/2^n \<and> dist z x \<le> K/2^n \<and>
  2233         norm(?pathint x y + ?pathint y z + ?pathint z x) \<ge> e*(K/2^n)^2"
  2234       for x y z n
  2235     have At0: "At a b c 0"
  2236       using fy
  2237       by (simp add: At_def e_def has_chain_integral_chain_integral3)
  2238     { fix x y z n
  2239       assume At: "At x y z n"
  2240       then have contf': "continuous_on (convex hull {x,y,z}) f"
  2241         using contf At_def continuous_on_subset by metis
  2242       have "\<exists>x' y' z'. At x' y' z' (Suc n) \<and> convex hull {x',y',z'} \<subseteq> convex hull {x,y,z}"
  2243         using At Cauchy_theorem_quadrisection [OF contf', of "K/2^n" e]
  2244         apply (simp add: At_def algebra_simps)
  2245         apply (meson convex_hull_subset empty_subsetI insert_subset subsetCE)
  2246         done
  2247     } note AtSuc = this
  2248     obtain fa fb fc
  2249       where f0 [simp]: "fa 0 = a" "fb 0 = b" "fc 0 = c"
  2250         and cosb: "\<And>n. convex hull {fa n, fb n, fc n} \<subseteq> convex hull {a,b,c}"
  2251         and dist: "\<And>n. dist (fa n) (fb n) \<le> K/2^n"
  2252                   "\<And>n. dist (fb n) (fc n) \<le> K/2^n"
  2253                   "\<And>n. dist (fc n) (fa n) \<le> K/2^n"
  2254         and no: "\<And>n. norm(?pathint (fa n) (fb n) +
  2255                            ?pathint (fb n) (fc n) +
  2256                            ?pathint (fc n) (fa n)) \<ge> e * (K/2^n)^2"
  2257         and conv_le: "\<And>n. convex hull {fa(Suc n), fb(Suc n), fc(Suc n)} \<subseteq> convex hull {fa n, fb n, fc n}"
  2258       apply (rule Chain3 [of At, OF At0 AtSuc])
  2259       apply (auto simp: At_def)
  2260       done
  2261     obtain x where x: "\<And>n. x \<in> convex hull {fa n, fb n, fc n}"
  2262     proof (rule bounded_closed_nest)
  2263       show "\<And>n. closed (convex hull {fa n, fb n, fc n})"
  2264         by (simp add: compact_imp_closed finite_imp_compact_convex_hull)
  2265       show "\<And>m n. m \<le> n \<Longrightarrow> convex hull {fa n, fb n, fc n} \<subseteq> convex hull {fa m, fb m, fc m}"
  2266         by (erule transitive_stepwise_le) (auto simp: conv_le)
  2267     qed (fastforce intro: finite_imp_bounded_convex_hull)+
  2268     then have xin: "x \<in> convex hull {a,b,c}"
  2269       using assms f0 by blast
  2270     then have fx: "f field_differentiable at x within (convex hull {a,b,c})"
  2271       using assms holomorphic_on_def by blast
  2272     { fix k n
  2273       assume k: "0 < k"
  2274          and le:
  2275             "\<And>x' y' z'.
  2276                \<lbrakk>dist x' y' \<le> k; dist y' z' \<le> k; dist z' x' \<le> k;
  2277                 x \<in> convex hull {x',y',z'};
  2278                 convex hull {x',y',z'} \<subseteq> convex hull {a,b,c}\<rbrakk>
  2279                \<Longrightarrow>
  2280                cmod (?pathint x' y' + ?pathint y' z' + ?pathint z' x') * 10
  2281                      \<le> e * (dist x' y' + dist y' z' + dist z' x')\<^sup>2"
  2282          and Kk: "K / k < 2 ^ n"
  2283       have "K / 2 ^ n < k" using Kk k
  2284         by (auto simp: field_simps)
  2285       then have DD: "dist (fa n) (fb n) \<le> k" "dist (fb n) (fc n) \<le> k" "dist (fc n) (fa n) \<le> k"
  2286         using dist [of n]  k
  2287         by linarith+
  2288       have dle: "(dist (fa n) (fb n) + dist (fb n) (fc n) + dist (fc n) (fa n))\<^sup>2
  2289                \<le> (3 * K / 2 ^ n)\<^sup>2"
  2290         using dist [of n] e K
  2291         by (simp add: abs_le_square_iff [symmetric])
  2292       have less10: "\<And>x y::real. 0 < x \<Longrightarrow> y \<le> 9*x \<Longrightarrow> y < x*10"
  2293         by linarith
  2294       have "e * (dist (fa n) (fb n) + dist (fb n) (fc n) + dist (fc n) (fa n))\<^sup>2 \<le> e * (3 * K / 2 ^ n)\<^sup>2"
  2295         using ynz dle e mult_le_cancel_left_pos by blast
  2296       also have "\<dots> <
  2297           cmod (?pathint (fa n) (fb n) + ?pathint (fb n) (fc n) + ?pathint (fc n) (fa n)) * 10"
  2298         using no [of n] e K
  2299         apply (simp add: e_def field_simps)
  2300         apply (simp only: zero_less_norm_iff [symmetric])
  2301         done
  2302       finally have False
  2303         using le [OF DD x cosb] by auto
  2304     } then
  2305     have ?thesis
  2306       using holomorphic_point_small_triangle [OF xin contf fx, of "e/10"] e
  2307       apply clarsimp
  2308       apply (rule_tac y1="K/k" in exE [OF real_arch_pow[of 2]], force+)
  2309       done
  2310   }
  2311   moreover have "f contour_integrable_on (linepath a b +++ linepath b c +++ linepath c a)"
  2312     by simp (meson contf continuous_on_subset contour_integrable_continuous_linepath segments_subset_convex_hull(1)
  2313                    segments_subset_convex_hull(3) segments_subset_convex_hull(5))
  2314   ultimately show ?thesis
  2315     using has_contour_integral_integral by fastforce
  2316 qed
  2317 
  2318 
  2319 subsection\<open>Version needing function holomorphic in interior only\<close>
  2320 
  2321 lemma Cauchy_theorem_flat_lemma:
  2322   assumes f: "continuous_on (convex hull {a,b,c}) f"
  2323       and c: "c - a = k *\<^sub>R (b - a)"
  2324       and k: "0 \<le> k"
  2325     shows "contour_integral (linepath a b) f + contour_integral (linepath b c) f +
  2326           contour_integral (linepath c a) f = 0"
  2327 proof -
  2328   have fabc: "continuous_on (closed_segment a b) f" "continuous_on (closed_segment b c) f" "continuous_on (closed_segment c a) f"
  2329     using f continuous_on_subset segments_subset_convex_hull by metis+
  2330   show ?thesis
  2331   proof (cases "k \<le> 1")
  2332     case True show ?thesis
  2333       by (simp add: contour_integral_split [OF fabc(1) k True c] contour_integral_reverse_linepath fabc)
  2334   next
  2335     case False then show ?thesis
  2336       using fabc c
  2337       apply (subst contour_integral_split [of a c f "1/k" b, symmetric])
  2338       apply (metis closed_segment_commute fabc(3))
  2339       apply (auto simp: k contour_integral_reverse_linepath)
  2340       done
  2341   qed
  2342 qed
  2343 
  2344 lemma Cauchy_theorem_flat:
  2345   assumes f: "continuous_on (convex hull {a,b,c}) f"
  2346       and c: "c - a = k *\<^sub>R (b - a)"
  2347     shows "contour_integral (linepath a b) f +
  2348            contour_integral (linepath b c) f +
  2349            contour_integral (linepath c a) f = 0"
  2350 proof (cases "0 \<le> k")
  2351   case True with assms show ?thesis
  2352     by (blast intro: Cauchy_theorem_flat_lemma)
  2353 next
  2354   case False
  2355   have "continuous_on (closed_segment a b) f" "continuous_on (closed_segment b c) f" "continuous_on (closed_segment c a) f"
  2356     using f continuous_on_subset segments_subset_convex_hull by metis+
  2357   moreover have "contour_integral (linepath b a) f + contour_integral (linepath a c) f +
  2358         contour_integral (linepath c b) f = 0"
  2359     apply (rule Cauchy_theorem_flat_lemma [of b a c f "1-k"])
  2360     using False c
  2361     apply (auto simp: f insert_commute scaleR_conv_of_real algebra_simps)
  2362     done
  2363   ultimately show ?thesis
  2364     apply (auto simp: contour_integral_reverse_linepath)
  2365     using add_eq_0_iff by force
  2366 qed
  2367 
  2368 
  2369 proposition Cauchy_theorem_triangle_interior:
  2370   assumes contf: "continuous_on (convex hull {a,b,c}) f"
  2371       and holf:  "f holomorphic_on interior (convex hull {a,b,c})"
  2372      shows "(f has_contour_integral 0) (linepath a b +++ linepath b c +++ linepath c a)"
  2373 proof -
  2374   have fabc: "continuous_on (closed_segment a b) f" "continuous_on (closed_segment b c) f" "continuous_on (closed_segment c a) f"
  2375     using contf continuous_on_subset segments_subset_convex_hull by metis+
  2376   have "bounded (f ` (convex hull {a,b,c}))"
  2377     by (simp add: compact_continuous_image compact_convex_hull compact_imp_bounded contf)
  2378   then obtain B where "0 < B" and Bnf: "\<And>x. x \<in> convex hull {a,b,c} \<Longrightarrow> norm (f x) \<le> B"
  2379      by (auto simp: dest!: bounded_pos [THEN iffD1])
  2380   have "bounded (convex hull {a,b,c})"
  2381     by (simp add: bounded_convex_hull)
  2382   then obtain C where C: "0 < C" and Cno: "\<And>y. y \<in> convex hull {a,b,c} \<Longrightarrow> norm y < C"
  2383     using bounded_pos_less by blast
  2384   then have diff_2C: "norm(x - y) \<le> 2*C"
  2385            if x: "x \<in> convex hull {a, b, c}" and y: "y \<in> convex hull {a, b, c}" for x y
  2386   proof -
  2387     have "cmod x \<le> C"
  2388       using x by (meson Cno not_le not_less_iff_gr_or_eq)
  2389     hence "cmod (x - y) \<le> C + C"
  2390       using y by (meson Cno add_mono_thms_linordered_field(4) less_eq_real_def norm_triangle_ineq4 order_trans)
  2391     thus "cmod (x - y) \<le> 2 * C"
  2392       by (metis mult_2)
  2393   qed
  2394   have contf': "continuous_on (convex hull {b,a,c}) f"
  2395     using contf by (simp add: insert_commute)
  2396   { fix y::complex
  2397     assume fy: "(f has_contour_integral y) (linepath a b +++ linepath b c +++ linepath c a)"
  2398        and ynz: "y \<noteq> 0"
  2399     have pi_eq_y: "contour_integral (linepath a b) f + contour_integral (linepath b c) f + contour_integral (linepath c a) f = y"
  2400       by (rule has_chain_integral_chain_integral3 [OF fy])
  2401     have ?thesis
  2402     proof (cases "c=a \<or> a=b \<or> b=c")
  2403       case True then show ?thesis
  2404         using Cauchy_theorem_flat [OF contf, of 0]
  2405         using has_chain_integral_chain_integral3 [OF fy] ynz
  2406         by (force simp: fabc contour_integral_reverse_linepath)
  2407     next
  2408       case False
  2409       then have car3: "card {a, b, c} = Suc (DIM(complex))"
  2410         by auto
  2411       { assume "interior(convex hull {a,b,c}) = {}"
  2412         then have "collinear{a,b,c}"
  2413           using interior_convex_hull_eq_empty [OF car3]
  2414           by (simp add: collinear_3_eq_affine_dependent)
  2415         with False obtain d where "c \<noteq> a" "a \<noteq> b" "b \<noteq> c" "c - b = d *\<^sub>R (a - b)"
  2416           by (auto simp: collinear_3 collinear_lemma)
  2417         then have "False"
  2418           using False Cauchy_theorem_flat [OF contf'] pi_eq_y ynz
  2419           by (simp add: fabc add_eq_0_iff contour_integral_reverse_linepath)
  2420       }
  2421       then obtain d where d: "d \<in> interior (convex hull {a, b, c})"
  2422         by blast
  2423       { fix d1
  2424         assume d1_pos: "0 < d1"
  2425            and d1: "\<And>x x'. \<lbrakk>x\<in>convex hull {a, b, c}; x'\<in>convex hull {a, b, c}; cmod (x' - x) < d1\<rbrakk>
  2426                            \<Longrightarrow> cmod (f x' - f x) < cmod y / (24 * C)"
  2427         define e where "e = min 1 (min (d1/(4*C)) ((norm y / 24 / C) / B))"
  2428         define shrink where "shrink x = x - e *\<^sub>R (x - d)" for x
  2429         let ?pathint = "\<lambda>x y. contour_integral(linepath x y) f"
  2430         have e: "0 < e" "e \<le> 1" "e \<le> d1 / (4 * C)" "e \<le> cmod y / 24 / C / B"
  2431           using d1_pos \<open>C>0\<close> \<open>B>0\<close> ynz by (simp_all add: e_def)
  2432         then have eCB: "24 * e * C * B \<le> cmod y"
  2433           using \<open>C>0\<close> \<open>B>0\<close>  by (simp add: field_simps)
  2434         have e_le_d1: "e * (4 * C) \<le> d1"
  2435           using e \<open>C>0\<close> by (simp add: field_simps)
  2436         have "shrink a \<in> interior(convex hull {a,b,c})"
  2437              "shrink b \<in> interior(convex hull {a,b,c})"
  2438              "shrink c \<in> interior(convex hull {a,b,c})"
  2439           using d e by (auto simp: hull_inc mem_interior_convex_shrink shrink_def)
  2440         then have fhp0: "(f has_contour_integral 0)
  2441                 (linepath (shrink a) (shrink b) +++ linepath (shrink b) (shrink c) +++ linepath (shrink c) (shrink a))"
  2442           by (simp add: Cauchy_theorem_triangle holomorphic_on_subset [OF holf] hull_minimal)
  2443         then have f_0_shrink: "?pathint (shrink a) (shrink b) + ?pathint (shrink b) (shrink c) + ?pathint (shrink c) (shrink a) = 0"
  2444           by (simp add: has_chain_integral_chain_integral3)
  2445         have fpi_abc: "f contour_integrable_on linepath (shrink a) (shrink b)"
  2446                       "f contour_integrable_on linepath (shrink b) (shrink c)"
  2447                       "f contour_integrable_on linepath (shrink c) (shrink a)"
  2448           using fhp0  by (auto simp: valid_path_join dest: has_contour_integral_integrable)
  2449         have cmod_shr: "\<And>x y. cmod (shrink y - shrink x - (y - x)) = e * cmod (x - y)"
  2450           using e by (simp add: shrink_def real_vector.scale_right_diff_distrib [symmetric])
  2451         have sh_eq: "\<And>a b d::complex. (b - e *\<^sub>R (b - d)) - (a - e *\<^sub>R (a - d)) - (b - a) = e *\<^sub>R (a - b)"
  2452           by (simp add: algebra_simps)
  2453         have "cmod y / (24 * C) \<le> cmod y / cmod (b - a) / 12"
  2454           using False \<open>C>0\<close> diff_2C [of b a] ynz
  2455           by (auto simp: divide_simps hull_inc)
  2456         have less_C: "\<lbrakk>u \<in> convex hull {a, b, c}; 0 \<le> x; x \<le> 1\<rbrakk> \<Longrightarrow> x * cmod u < C" for x u
  2457           apply (cases "x=0", simp add: \<open>0<C\<close>)
  2458           using Cno [of u] mult_left_le_one_le [of "cmod u" x] le_less_trans norm_ge_zero by blast
  2459         { fix u v
  2460           assume uv: "u \<in> convex hull {a, b, c}" "v \<in> convex hull {a, b, c}" "u\<noteq>v"
  2461              and fpi_uv: "f contour_integrable_on linepath (shrink u) (shrink v)"
  2462           have shr_uv: "shrink u \<in> interior(convex hull {a,b,c})"
  2463                        "shrink v \<in> interior(convex hull {a,b,c})"
  2464             using d e uv
  2465             by (auto simp: hull_inc mem_interior_convex_shrink shrink_def)
  2466           have cmod_fuv: "\<And>x. 0\<le>x \<Longrightarrow> x\<le>1 \<Longrightarrow> cmod (f (linepath (shrink u) (shrink v) x)) \<le> B"
  2467             using shr_uv by (blast intro: Bnf linepath_in_convex_hull interior_subset [THEN subsetD])
  2468           have By_uv: "B * (12 * (e * cmod (u - v))) \<le> cmod y"
  2469             apply (rule order_trans [OF _ eCB])
  2470             using e \<open>B>0\<close> diff_2C [of u v] uv
  2471             by (auto simp: field_simps)
  2472           { fix x::real   assume x: "0\<le>x" "x\<le>1"
  2473             have cmod_less_4C: "cmod ((1 - x) *\<^sub>R u - (1 - x) *\<^sub>R d) + cmod (x *\<^sub>R v - x *\<^sub>R d) < (C+C) + (C+C)"
  2474               apply (rule add_strict_mono; rule norm_triangle_half_l [of _ 0])
  2475               using uv x d interior_subset
  2476               apply (auto simp: hull_inc intro!: less_C)
  2477               done
  2478             have ll: "linepath (shrink u) (shrink v) x - linepath u v x = -e * ((1 - x) *\<^sub>R (u - d) + x *\<^sub>R (v - d))"
  2479               by (simp add: linepath_def shrink_def algebra_simps scaleR_conv_of_real)
  2480             have cmod_less_dt: "cmod (linepath (shrink u) (shrink v) x - linepath u v x) < d1"
  2481               apply (simp only: ll norm_mult scaleR_diff_right)
  2482               using \<open>e>0\<close> cmod_less_4C apply (force intro: norm_triangle_lt less_le_trans [OF _ e_le_d1])
  2483               done
  2484             have "cmod (f (linepath (shrink u) (shrink v) x) - f (linepath u v x)) < cmod y / (24 * C)"
  2485               using x uv shr_uv cmod_less_dt
  2486               by (auto simp: hull_inc intro: d1 interior_subset [THEN subsetD] linepath_in_convex_hull)
  2487             also have "\<dots> \<le> cmod y / cmod (v - u) / 12"
  2488               using False uv \<open>C>0\<close> diff_2C [of v u] ynz
  2489               by (auto simp: divide_simps hull_inc)
  2490             finally have "cmod (f (linepath (shrink u) (shrink v) x) - f (linepath u v x)) \<le> cmod y / cmod (v - u) / 12"
  2491               by simp
  2492             then have cmod_12_le: "cmod (v - u) * cmod (f (linepath (shrink u) (shrink v) x) - f (linepath u v x)) * 12 \<le> cmod y"
  2493               using uv False by (auto simp: field_simps)
  2494             have "cmod (f (linepath (shrink u) (shrink v) x)) * cmod (shrink v - shrink u - (v - u)) +
  2495                           cmod (v - u) * cmod (f (linepath (shrink u) (shrink v) x) - f (linepath u v x))
  2496                           \<le> B * (cmod y / 24 / C / B * 2 * C) + 2 * C * (cmod y / 24 / C)"
  2497               apply (rule add_mono [OF mult_mono])
  2498               using By_uv e \<open>0 < B\<close> \<open>0 < C\<close> x apply (simp_all add: cmod_fuv cmod_shr cmod_12_le)
  2499               apply (simp add: field_simps)
  2500               done
  2501             also have "\<dots> \<le> cmod y / 6"
  2502               by simp
  2503             finally have "cmod (f (linepath (shrink u) (shrink v) x)) * cmod (shrink v - shrink u - (v - u)) +
  2504                           cmod (v - u) * cmod (f (linepath (shrink u) (shrink v) x) - f (linepath u v x))
  2505                           \<le> cmod y / 6" .
  2506           } note cmod_diff_le = this
  2507           have f_uv: "continuous_on (closed_segment u v) f"
  2508             by (blast intro: uv continuous_on_subset [OF contf closed_segment_subset_convex_hull])
  2509           have **: "\<And>f' x' f x::complex. f'*x' - f*x = f'*(x' - x) + x*(f' - f)"
  2510             by (simp add: algebra_simps)
  2511           have "norm (?pathint (shrink u) (shrink v) - ?pathint u v) 
  2512                 \<le> (B*(norm y /24/C/B)*2*C + (2*C)*(norm y/24/C)) * content (cbox 0 (1::real))"
  2513             apply (rule has_integral_bound
  2514                     [of _ "\<lambda>x. f(linepath (shrink u) (shrink v) x) * (shrink v - shrink u) - f(linepath u v x)*(v - u)"
  2515                         _ 0 1])
  2516             using ynz \<open>0 < B\<close> \<open>0 < C\<close>
  2517               apply (simp_all del: le_divide_eq_numeral1)
  2518             apply (simp add: has_integral_diff has_contour_integral_linepath [symmetric] has_contour_integral_integral
  2519                 fpi_uv f_uv contour_integrable_continuous_linepath)
  2520             apply (auto simp: ** norm_triangle_le norm_mult cmod_diff_le simp del: le_divide_eq_numeral1)
  2521             done
  2522           also have "\<dots> \<le> norm y / 6"
  2523             by simp
  2524           finally have "norm (?pathint (shrink u) (shrink v) - ?pathint u v) \<le> norm y / 6" .
  2525           } note * = this
  2526           have "norm (?pathint (shrink a) (shrink b) - ?pathint a b) \<le> norm y / 6"
  2527             using False fpi_abc by (rule_tac *) (auto simp: hull_inc)
  2528           moreover
  2529           have "norm (?pathint (shrink b) (shrink c) - ?pathint b c) \<le> norm y / 6"
  2530             using False fpi_abc by (rule_tac *) (auto simp: hull_inc)
  2531           moreover
  2532           have "norm (?pathint (shrink c) (shrink a) - ?pathint c a) \<le> norm y / 6"
  2533             using False fpi_abc by (rule_tac *) (auto simp: hull_inc)
  2534           ultimately
  2535           have "norm((?pathint (shrink a) (shrink b) - ?pathint a b) +
  2536                      (?pathint (shrink b) (shrink c) - ?pathint b c) + (?pathint (shrink c) (shrink a) - ?pathint c a))
  2537                 \<le> norm y / 6 + norm y / 6 + norm y / 6"
  2538             by (metis norm_triangle_le add_mono)
  2539           also have "\<dots> = norm y / 2"
  2540             by simp
  2541           finally have "norm((?pathint (shrink a) (shrink b) + ?pathint (shrink b) (shrink c) + ?pathint (shrink c) (shrink a)) -
  2542                           (?pathint a b + ?pathint b c + ?pathint c a))
  2543                 \<le> norm y / 2"
  2544             by (simp add: algebra_simps)
  2545           then
  2546           have "norm(?pathint a b + ?pathint b c + ?pathint c a) \<le> norm y / 2"
  2547             by (simp add: f_0_shrink) (metis (mono_tags) add.commute minus_add_distrib norm_minus_cancel uminus_add_conv_diff)
  2548           then have "False"
  2549             using pi_eq_y ynz by auto
  2550         }
  2551         moreover have "uniformly_continuous_on (convex hull {a,b,c}) f"
  2552           by (simp add: contf compact_convex_hull compact_uniformly_continuous)
  2553         ultimately have "False"
  2554           unfolding uniformly_continuous_on_def
  2555           by (force simp: ynz \<open>0 < C\<close> dist_norm)
  2556         then show ?thesis ..
  2557       qed
  2558   }
  2559   moreover have "f contour_integrable_on (linepath a b +++ linepath b c +++ linepath c a)"
  2560     using fabc contour_integrable_continuous_linepath by auto
  2561   ultimately show ?thesis
  2562     using has_contour_integral_integral by fastforce
  2563 qed
  2564 
  2565 
  2566 subsection\<open>Version allowing finite number of exceptional points\<close>
  2567 
  2568 proposition Cauchy_theorem_triangle_cofinite:
  2569   assumes "continuous_on (convex hull {a,b,c}) f"
  2570       and "finite S"
  2571       and "(\<And>x. x \<in> interior(convex hull {a,b,c}) - S \<Longrightarrow> f field_differentiable (at x))"
  2572      shows "(f has_contour_integral 0) (linepath a b +++ linepath b c +++ linepath c a)"
  2573 using assms
  2574 proof (induction "card S" arbitrary: a b c S rule: less_induct)
  2575   case (less S a b c)
  2576   show ?case
  2577   proof (cases "S={}")
  2578     case True with less show ?thesis
  2579       by (fastforce simp: holomorphic_on_def field_differentiable_at_within Cauchy_theorem_triangle_interior)
  2580   next
  2581     case False
  2582     then obtain d S' where d: "S = insert d S'" "d \<notin> S'"
  2583       by (meson Set.set_insert all_not_in_conv)
  2584     then show ?thesis
  2585     proof (cases "d \<in> convex hull {a,b,c}")
  2586       case False
  2587       show "(f has_contour_integral 0) (linepath a b +++ linepath b c +++ linepath c a)"
  2588       proof (rule less.hyps)
  2589         show "\<And>x. x \<in> interior (convex hull {a, b, c}) - S' \<Longrightarrow> f field_differentiable at x"
  2590         using False d interior_subset by (auto intro!: less.prems)
  2591     qed (use d less.prems in auto)
  2592     next
  2593       case True
  2594       have *: "convex hull {a, b, d} \<subseteq> convex hull {a, b, c}"
  2595         by (meson True hull_subset insert_subset convex_hull_subset)
  2596       have abd: "(f has_contour_integral 0) (linepath a b +++ linepath b d +++ linepath d a)"
  2597       proof (rule less.hyps)
  2598         show "\<And>x. x \<in> interior (convex hull {a, b, d}) - S' \<Longrightarrow> f field_differentiable at x"
  2599           using d not_in_interior_convex_hull_3
  2600           by (clarsimp intro!: less.prems) (metis * insert_absorb insert_subset interior_mono)
  2601       qed (use d continuous_on_subset [OF  _ *] less.prems in auto)
  2602       have *: "convex hull {b, c, d} \<subseteq> convex hull {a, b, c}"
  2603         by (meson True hull_subset insert_subset convex_hull_subset)
  2604       have bcd: "(f has_contour_integral 0) (linepath b c +++ linepath c d +++ linepath d b)"
  2605       proof (rule less.hyps)
  2606         show "\<And>x. x \<in> interior (convex hull {b, c, d}) - S' \<Longrightarrow> f field_differentiable at x"
  2607           using d not_in_interior_convex_hull_3
  2608           by (clarsimp intro!: less.prems) (metis * insert_absorb insert_subset interior_mono)
  2609       qed (use d continuous_on_subset [OF  _ *] less.prems in auto)
  2610       have *: "convex hull {c, a, d} \<subseteq> convex hull {a, b, c}"
  2611         by (meson True hull_subset insert_subset convex_hull_subset)
  2612       have cad: "(f has_contour_integral 0) (linepath c a +++ linepath a d +++ linepath d c)"
  2613       proof (rule less.hyps)
  2614         show "\<And>x. x \<in> interior (convex hull {c, a, d}) - S' \<Longrightarrow> f field_differentiable at x"
  2615           using d not_in_interior_convex_hull_3
  2616           by (clarsimp intro!: less.prems) (metis * insert_absorb insert_subset interior_mono)
  2617       qed (use d continuous_on_subset [OF  _ *] less.prems in auto)
  2618       have "f contour_integrable_on linepath a b"
  2619         using less.prems abd contour_integrable_joinD1 contour_integrable_on_def by blast
  2620       moreover have "f contour_integrable_on linepath b c"
  2621         using less.prems bcd contour_integrable_joinD1 contour_integrable_on_def by blast
  2622       moreover have "f contour_integrable_on linepath c a"
  2623         using less.prems cad contour_integrable_joinD1 contour_integrable_on_def by blast
  2624       ultimately have fpi: "f contour_integrable_on (linepath a b +++ linepath b c +++ linepath c a)"
  2625         by auto
  2626       { fix y::complex
  2627         assume fy: "(f has_contour_integral y) (linepath a b +++ linepath b c +++ linepath c a)"
  2628            and ynz: "y \<noteq> 0"
  2629         have cont_ad: "continuous_on (closed_segment a d) f"
  2630           by (meson "*" continuous_on_subset less.prems(1) segments_subset_convex_hull(3))
  2631         have cont_bd: "continuous_on (closed_segment b d) f"
  2632           by (meson True closed_segment_subset_convex_hull continuous_on_subset hull_subset insert_subset less.prems(1))
  2633         have cont_cd: "continuous_on (closed_segment c d) f"
  2634           by (meson "*" continuous_on_subset less.prems(1) segments_subset_convex_hull(2))
  2635         have "contour_integral  (linepath a b) f = - (contour_integral (linepath b d) f + (contour_integral (linepath d a) f))"
  2636              "contour_integral  (linepath b c) f = - (contour_integral (linepath c d) f + (contour_integral (linepath d b) f))"
  2637              "contour_integral  (linepath c a) f = - (contour_integral (linepath a d) f + contour_integral (linepath d c) f)"
  2638             using has_chain_integral_chain_integral3 [OF abd]
  2639                   has_chain_integral_chain_integral3 [OF bcd]
  2640                   has_chain_integral_chain_integral3 [OF cad]
  2641             by (simp_all add: algebra_simps add_eq_0_iff)
  2642         then have ?thesis
  2643           using cont_ad cont_bd cont_cd fy has_chain_integral_chain_integral3 contour_integral_reverse_linepath by fastforce
  2644       }
  2645       then show ?thesis
  2646         using fpi contour_integrable_on_def by blast
  2647     qed
  2648   qed
  2649 qed
  2650 
  2651 
  2652 subsection\<open>Cauchy's theorem for an open starlike set\<close>
  2653 
  2654 lemma starlike_convex_subset:
  2655   assumes S: "a \<in> S" "closed_segment b c \<subseteq> S" and subs: "\<And>x. x \<in> S \<Longrightarrow> closed_segment a x \<subseteq> S"
  2656     shows "convex hull {a,b,c} \<subseteq> S"
  2657       using S
  2658       apply (clarsimp simp add: convex_hull_insert [of "{b,c}" a] segment_convex_hull)
  2659       apply (meson subs convexD convex_closed_segment ends_in_segment(1) ends_in_segment(2) subsetCE)
  2660       done
  2661 
  2662 lemma triangle_contour_integrals_starlike_primitive:
  2663   assumes contf: "continuous_on S f"
  2664       and S: "a \<in> S" "open S"
  2665       and x: "x \<in> S"
  2666       and subs: "\<And>y. y \<in> S \<Longrightarrow> closed_segment a y \<subseteq> S"
  2667       and zer: "\<And>b c. closed_segment b c \<subseteq> S
  2668                    \<Longrightarrow> contour_integral (linepath a b) f + contour_integral (linepath b c) f +
  2669                        contour_integral (linepath c a) f = 0"
  2670     shows "((\<lambda>x. contour_integral(linepath a x) f) has_field_derivative f x) (at x)"
  2671 proof -
  2672   let ?pathint = "\<lambda>x y. contour_integral(linepath x y) f"
  2673   { fix e y
  2674     assume e: "0 < e" and bxe: "ball x e \<subseteq> S" and close: "cmod (y - x) < e"
  2675     have y: "y \<in> S"
  2676       using bxe close  by (force simp: dist_norm norm_minus_commute)
  2677     have cont_ayf: "continuous_on (closed_segment a y) f"
  2678       using contf continuous_on_subset subs y by blast
  2679     have xys: "closed_segment x y \<subseteq> S"
  2680       apply (rule order_trans [OF _ bxe])
  2681       using close
  2682       by (auto simp: dist_norm ball_def norm_minus_commute dest: segment_bound)
  2683     have "?pathint a y - ?pathint a x = ?pathint x y"
  2684       using zer [OF xys]  contour_integral_reverse_linepath [OF cont_ayf]  add_eq_0_iff by force
  2685   } note [simp] = this
  2686   { fix e::real
  2687     assume e: "0 < e"
  2688     have cont_atx: "continuous (at x) f"
  2689       using x S contf continuous_on_eq_continuous_at by blast
  2690     then obtain d1 where d1: "d1>0" and d1_less: "\<And>y. cmod (y - x) < d1 \<Longrightarrow> cmod (f y - f x) < e/2"
  2691       unfolding continuous_at Lim_at dist_norm  using e
  2692       by (drule_tac x="e/2" in spec) force
  2693     obtain d2 where d2: "d2>0" "ball x d2 \<subseteq> S" using  \<open>open S\<close> x
  2694       by (auto simp: open_contains_ball)
  2695     have dpos: "min d1 d2 > 0" using d1 d2 by simp
  2696     { fix y
  2697       assume yx: "y \<noteq> x" and close: "cmod (y - x) < min d1 d2"
  2698       have y: "y \<in> S"
  2699         using d2 close  by (force simp: dist_norm norm_minus_commute)
  2700       have "closed_segment x y \<subseteq> S"
  2701         using close d2  by (auto simp: dist_norm norm_minus_commute dest!: segment_bound(1))
  2702       then have fxy: "f contour_integrable_on linepath x y"
  2703         by (metis contour_integrable_continuous_linepath continuous_on_subset [OF contf])
  2704       then obtain i where i: "(f has_contour_integral i) (linepath x y)"
  2705         by (auto simp: contour_integrable_on_def)
  2706       then have "((\<lambda>w. f w - f x) has_contour_integral (i - f x * (y - x))) (linepath x y)"
  2707         by (rule has_contour_integral_diff [OF _ has_contour_integral_const_linepath])
  2708       then have "cmod (i - f x * (y - x)) \<le> e / 2 * cmod (y - x)"
  2709       proof (rule has_contour_integral_bound_linepath)
  2710         show "\<And>u. u \<in> closed_segment x y \<Longrightarrow> cmod (f u - f x) \<le> e / 2"
  2711           by (meson close d1_less le_less_trans less_imp_le min.strict_boundedE segment_bound1)
  2712       qed (use e in simp)
  2713       also have "\<dots> < e * cmod (y - x)"
  2714         by (simp add: e yx)
  2715       finally have "cmod (?pathint x y - f x * (y-x)) / cmod (y-x) < e"
  2716         using i yx  by (simp add: contour_integral_unique divide_less_eq)
  2717     }
  2718     then have "\<exists>d>0. \<forall>y. y \<noteq> x \<and> cmod (y-x) < d \<longrightarrow> cmod (?pathint x y - f x * (y-x)) / cmod (y-x) < e"
  2719       using dpos by blast
  2720   }
  2721   then have *: "(\<lambda>y. (?pathint x y - f x * (y - x)) /\<^sub>R cmod (y - x)) \<midarrow>x\<rightarrow> 0"
  2722     by (simp add: Lim_at dist_norm inverse_eq_divide)
  2723   show ?thesis
  2724     apply (simp add: has_field_derivative_def has_derivative_at2 bounded_linear_mult_right)
  2725     apply (rule Lim_transform [OF * Lim_eventually])
  2726     using \<open>open S\<close> x apply (force simp: dist_norm open_contains_ball inverse_eq_divide [symmetric] eventually_at)
  2727     done
  2728 qed
  2729 
  2730 (** Existence of a primitive.*)
  2731 
  2732 lemma holomorphic_starlike_primitive:
  2733   fixes f :: "complex \<Rightarrow> complex"
  2734   assumes contf: "continuous_on S f"
  2735       and S: "starlike S" and os: "open S"
  2736       and k: "finite k"
  2737       and fcd: "\<And>x. x \<in> S - k \<Longrightarrow> f field_differentiable at x"
  2738     shows "\<exists>g. \<forall>x \<in> S. (g has_field_derivative f x) (at x)"
  2739 proof -
  2740   obtain a where a: "a\<in>S" and a_cs: "\<And>x. x\<in>S \<Longrightarrow> closed_segment a x \<subseteq> S"
  2741     using S by (auto simp: starlike_def)
  2742   { fix x b c
  2743     assume "x \<in> S" "closed_segment b c \<subseteq> S"
  2744     then have abcs: "convex hull {a, b, c} \<subseteq> S"
  2745       by (simp add: a a_cs starlike_convex_subset)
  2746     then have "continuous_on (convex hull {a, b, c}) f"
  2747       by (simp add: continuous_on_subset [OF contf])
  2748     then have "(f has_contour_integral 0) (linepath a b +++ linepath b c +++ linepath c a)"
  2749       using abcs interior_subset by (force intro: fcd Cauchy_theorem_triangle_cofinite [OF _ k])
  2750   } note 0 = this
  2751   show ?thesis
  2752     apply (intro exI ballI)
  2753     apply (rule triangle_contour_integrals_starlike_primitive [OF contf a os], assumption)
  2754     apply (metis a_cs)
  2755     apply (metis has_chain_integral_chain_integral3 0)
  2756     done
  2757 qed
  2758 
  2759 corollary Cauchy_theorem_starlike:
  2760  "\<lbrakk>open S; starlike S; finite k; continuous_on S f;
  2761    \<And>x. x \<in> S - k \<Longrightarrow> f field_differentiable at x;
  2762    valid_path g; path_image g \<subseteq> S; pathfinish g = pathstart g\<rbrakk>
  2763    \<Longrightarrow> (f has_contour_integral 0)  g"
  2764   by (metis holomorphic_starlike_primitive Cauchy_theorem_primitive at_within_open)
  2765 
  2766 corollary Cauchy_theorem_starlike_simple:
  2767   "\<lbrakk>open S; starlike S; f holomorphic_on S; valid_path g; path_image g \<subseteq> S; pathfinish g = pathstart g\<rbrakk>
  2768    \<Longrightarrow> (f has_contour_integral 0) g"
  2769 apply (rule Cauchy_theorem_starlike [OF _ _ finite.emptyI])
  2770 apply (simp_all add: holomorphic_on_imp_continuous_on)
  2771 apply (metis at_within_open holomorphic_on_def)
  2772 done
  2773 
  2774 
  2775 subsection\<open>Cauchy's theorem for a convex set\<close>
  2776 
  2777 text\<open>For a convex set we can avoid assuming openness and boundary analyticity\<close>
  2778 
  2779 lemma triangle_contour_integrals_convex_primitive:
  2780   assumes contf: "continuous_on S f"
  2781       and S: "a \<in> S" "convex S"
  2782       and x: "x \<in> S"
  2783       and zer: "\<And>b c. \<lbrakk>b \<in> S; c \<in> S\<rbrakk>
  2784                    \<Longrightarrow> contour_integral (linepath a b) f + contour_integral (linepath b c) f +
  2785                        contour_integral (linepath c a) f = 0"
  2786     shows "((\<lambda>x. contour_integral(linepath a x) f) has_field_derivative f x) (at x within S)"
  2787 proof -
  2788   let ?pathint = "\<lambda>x y. contour_integral(linepath x y) f"
  2789   { fix y
  2790     assume y: "y \<in> S"
  2791     have cont_ayf: "continuous_on (closed_segment a y) f"
  2792       using S y  by (meson contf continuous_on_subset convex_contains_segment)
  2793     have xys: "closed_segment x y \<subseteq> S"  (*?*)
  2794       using convex_contains_segment S x y by auto
  2795     have "?pathint a y - ?pathint a x = ?pathint x y"
  2796       using zer [OF x y]  contour_integral_reverse_linepath [OF cont_ayf]  add_eq_0_iff by force
  2797   } note [simp] = this
  2798   { fix e::real
  2799     assume e: "0 < e"
  2800     have cont_atx: "continuous (at x within S) f"
  2801       using x S contf  by (simp add: continuous_on_eq_continuous_within)
  2802     then obtain d1 where d1: "d1>0" and d1_less: "\<And>y. \<lbrakk>y \<in> S; cmod (y - x) < d1\<rbrakk> \<Longrightarrow> cmod (f y - f x) < e/2"
  2803       unfolding continuous_within Lim_within dist_norm using e
  2804       by (drule_tac x="e/2" in spec) force
  2805     { fix y
  2806       assume yx: "y \<noteq> x" and close: "cmod (y - x) < d1" and y: "y \<in> S"
  2807       have fxy: "f contour_integrable_on linepath x y"
  2808         using convex_contains_segment S x y
  2809         by (blast intro!: contour_integrable_continuous_linepath continuous_on_subset [OF contf])
  2810       then obtain i where i: "(f has_contour_integral i) (linepath x y)"
  2811         by (auto simp: contour_integrable_on_def)
  2812       then have "((\<lambda>w. f w - f x) has_contour_integral (i - f x * (y - x))) (linepath x y)"
  2813         by (rule has_contour_integral_diff [OF _ has_contour_integral_const_linepath])
  2814       then have "cmod (i - f x * (y - x)) \<le> e / 2 * cmod (y - x)"
  2815       proof (rule has_contour_integral_bound_linepath)
  2816         show "\<And>u. u \<in> closed_segment x y \<Longrightarrow> cmod (f u - f x) \<le> e / 2"
  2817           by (meson assms(3) close convex_contains_segment d1_less le_less_trans less_imp_le segment_bound1 subset_iff x y)
  2818       qed (use e in simp)
  2819       also have "\<dots> < e * cmod (y - x)"
  2820         by (simp add: e yx)
  2821       finally have "cmod (?pathint x y - f x * (y-x)) / cmod (y-x) < e"
  2822         using i yx  by (simp add: contour_integral_unique divide_less_eq)
  2823     }
  2824     then have "\<exists>d>0. \<forall>y\<in>S. y \<noteq> x \<and> cmod (y-x) < d \<longrightarrow> cmod (?pathint x y - f x * (y-x)) / cmod (y-x) < e"
  2825       using d1 by blast
  2826   }
  2827   then have *: "((\<lambda>y. (contour_integral (linepath x y) f - f x * (y - x)) /\<^sub>R cmod (y - x)) \<longlongrightarrow> 0) (at x within S)"
  2828     by (simp add: Lim_within dist_norm inverse_eq_divide)
  2829   show ?thesis
  2830     apply (simp add: has_field_derivative_def has_derivative_within bounded_linear_mult_right)
  2831     apply (rule Lim_transform [OF * Lim_eventually])
  2832     using linordered_field_no_ub
  2833     apply (force simp: inverse_eq_divide [symmetric] eventually_at)
  2834     done
  2835 qed
  2836 
  2837 lemma contour_integral_convex_primitive:
  2838   assumes "convex S" "continuous_on S f" 
  2839           "\<And>a b c. \<lbrakk>a \<in> S; b \<in> S; c \<in> S\<rbrakk> \<Longrightarrow> (f has_contour_integral 0) (linepath a b +++ linepath b c +++ linepath c a)"
  2840   obtains g where "\<And>x. x \<in> S \<Longrightarrow> (g has_field_derivative f x) (at x within S)"
  2841 proof (cases "S={}")
  2842   case False
  2843   with assms that show ?thesis
  2844     by (blast intro: triangle_contour_integrals_convex_primitive has_chain_integral_chain_integral3)
  2845 qed auto
  2846 
  2847 lemma holomorphic_convex_primitive:
  2848   fixes f :: "complex \<Rightarrow> complex"
  2849   assumes "convex S" "finite K" and contf: "continuous_on S f" 
  2850     and fd: "\<And>x. x \<in> interior S - K \<Longrightarrow> f field_differentiable at x"
  2851   obtains g where "\<And>x. x \<in> S \<Longrightarrow> (g has_field_derivative f x) (at x within S)"
  2852 proof (rule contour_integral_convex_primitive [OF \<open>convex S\<close> contf Cauchy_theorem_triangle_cofinite])
  2853   have *: "convex hull {a, b, c} \<subseteq> S" if "a \<in> S" "b \<in> S" "c \<in> S" for a b c
  2854     by (simp add: \<open>convex S\<close> hull_minimal that)
  2855   show "continuous_on (convex hull {a, b, c}) f" if "a \<in> S" "b \<in> S" "c \<in> S" for a b c
  2856     by (meson "*" contf continuous_on_subset that)
  2857   show "f field_differentiable at x" if "a \<in> S" "b \<in> S" "c \<in> S" "x \<in> interior (convex hull {a, b, c}) - K" for a b c x
  2858     by (metis "*" DiffD1 DiffD2 DiffI fd interior_mono subsetCE that)
  2859 qed (use assms in \<open>force+\<close>)
  2860 
  2861 lemma holomorphic_convex_primitive':
  2862   fixes f :: "complex \<Rightarrow> complex"
  2863   assumes "convex S" and "open S" and "f holomorphic_on S"
  2864   obtains g where "\<And>x. x \<in> S \<Longrightarrow> (g has_field_derivative f x) (at x within S)"
  2865 proof (rule holomorphic_convex_primitive)
  2866   fix x assume "x \<in> interior S - {}"
  2867   with assms show "f field_differentiable at x"
  2868     by (auto intro!: holomorphic_on_imp_differentiable_at simp: interior_open)
  2869 qed (use assms in \<open>auto intro: holomorphic_on_imp_continuous_on\<close>)
  2870 
  2871 corollary Cauchy_theorem_convex:
  2872     "\<lbrakk>continuous_on S f; convex S; finite K;
  2873       \<And>x. x \<in> interior S - K \<Longrightarrow> f field_differentiable at x;
  2874       valid_path g; path_image g \<subseteq> S; pathfinish g = pathstart g\<rbrakk> 
  2875      \<Longrightarrow> (f has_contour_integral 0) g"
  2876   by (metis holomorphic_convex_primitive Cauchy_theorem_primitive)
  2877 
  2878 corollary Cauchy_theorem_convex_simple:
  2879     "\<lbrakk>f holomorphic_on S; convex S;
  2880      valid_path g; path_image g \<subseteq> S;
  2881      pathfinish g = pathstart g\<rbrakk> \<Longrightarrow> (f has_contour_integral 0) g"
  2882   apply (rule Cauchy_theorem_convex [where K = "{}"])
  2883   apply (simp_all add: holomorphic_on_imp_continuous_on)
  2884   using at_within_interior holomorphic_on_def interior_subset by fastforce
  2885 
  2886 
  2887 text\<open>In particular for a disc\<close>
  2888 corollary Cauchy_theorem_disc:
  2889     "\<lbrakk>finite K; continuous_on (cball a e) f;
  2890       \<And>x. x \<in> ball a e - K \<Longrightarrow> f field_differentiable at x;
  2891      valid_path g; path_image g \<subseteq> cball a e;
  2892      pathfinish g = pathstart g\<rbrakk> \<Longrightarrow> (f has_contour_integral 0) g"
  2893   by (auto intro: Cauchy_theorem_convex)
  2894 
  2895 corollary Cauchy_theorem_disc_simple:
  2896     "\<lbrakk>f holomorphic_on (ball a e); valid_path g; path_image g \<subseteq> ball a e;
  2897      pathfinish g = pathstart g\<rbrakk> \<Longrightarrow> (f has_contour_integral 0) g"
  2898 by (simp add: Cauchy_theorem_convex_simple)
  2899 
  2900 
  2901 subsection\<open>Generalize integrability to local primitives\<close>
  2902 
  2903 lemma contour_integral_local_primitive_lemma:
  2904   fixes f :: "complex\<Rightarrow>complex"
  2905   shows
  2906     "\<lbrakk>g piecewise_differentiable_on {a..b};
  2907       \<And>x. x \<in> s \<Longrightarrow> (f has_field_derivative f' x) (at x within s);
  2908       \<And>x. x \<in> {a..b} \<Longrightarrow> g x \<in> s\<rbrakk>
  2909      \<Longrightarrow> (\<lambda>x. f' (g x) * vector_derivative g (at x within {a..b}))
  2910             integrable_on {a..b}"
  2911   apply (cases "cbox a b = {}", force)
  2912   apply (simp add: integrable_on_def)
  2913   apply (rule exI)
  2914   apply (rule contour_integral_primitive_lemma, assumption+)
  2915   using atLeastAtMost_iff by blast
  2916 
  2917 lemma contour_integral_local_primitive_any:
  2918   fixes f :: "complex \<Rightarrow> complex"
  2919   assumes gpd: "g piecewise_differentiable_on {a..b}"
  2920       and dh: "\<And>x. x \<in> s
  2921                \<Longrightarrow> \<exists>d h. 0 < d \<and>
  2922                          (\<forall>y. norm(y - x) < d \<longrightarrow> (h has_field_derivative f y) (at y within s))"
  2923       and gs: "\<And>x. x \<in> {a..b} \<Longrightarrow> g x \<in> s"
  2924   shows "(\<lambda>x. f(g x) * vector_derivative g (at x)) integrable_on {a..b}"
  2925 proof -
  2926   { fix x
  2927     assume x: "a \<le> x" "x \<le> b"
  2928     obtain d h where d: "0 < d"
  2929                and h: "(\<And>y. norm(y - g x) < d \<Longrightarrow> (h has_field_derivative f y) (at y within s))"
  2930       using x gs dh by (metis atLeastAtMost_iff)
  2931     have "continuous_on {a..b} g" using gpd piecewise_differentiable_on_def by blast
  2932     then obtain e where e: "e>0" and lessd: "\<And>x'. x' \<in> {a..b} \<Longrightarrow> \<bar>x' - x\<bar> < e \<Longrightarrow> cmod (g x' - g x) < d"
  2933       using x d
  2934       apply (auto simp: dist_norm continuous_on_iff)
  2935       apply (drule_tac x=x in bspec)
  2936       using x apply simp
  2937       apply (drule_tac x=d in spec, auto)
  2938       done
  2939     have "\<exists>d>0. \<forall>u v. u \<le> x \<and> x \<le> v \<and> {u..v} \<subseteq> ball x d \<and> (u \<le> v \<longrightarrow> a \<le> u \<and> v \<le> b) \<longrightarrow>
  2940                           (\<lambda>x. f (g x) * vector_derivative g (at x)) integrable_on {u..v}"
  2941       apply (rule_tac x=e in exI)
  2942       using e
  2943       apply (simp add: integrable_on_localized_vector_derivative [symmetric], clarify)
  2944       apply (rule_tac f = h and s = "g ` {u..v}" in contour_integral_local_primitive_lemma)
  2945         apply (meson atLeastatMost_subset_iff gpd piecewise_differentiable_on_subset)
  2946        apply (force simp: ball_def dist_norm intro: lessd gs DERIV_subset [OF h], force)
  2947       done
  2948   } then
  2949   show ?thesis
  2950     by (force simp: intro!: integrable_on_little_subintervals [of a b, simplified])
  2951 qed
  2952 
  2953 lemma contour_integral_local_primitive:
  2954   fixes f :: "complex \<Rightarrow> complex"
  2955   assumes g: "valid_path g" "path_image g \<subseteq> s"
  2956       and dh: "\<And>x. x \<in> s
  2957                \<Longrightarrow> \<exists>d h. 0 < d \<and>
  2958                          (\<forall>y. norm(y - x) < d \<longrightarrow> (h has_field_derivative f y) (at y within s))"
  2959   shows "f contour_integrable_on g"
  2960   using g
  2961   apply (simp add: valid_path_def path_image_def contour_integrable_on_def has_contour_integral_def
  2962             has_integral_localized_vector_derivative integrable_on_def [symmetric])
  2963   using contour_integral_local_primitive_any [OF _ dh]
  2964   by (meson image_subset_iff piecewise_C1_imp_differentiable)
  2965 
  2966 
  2967 text\<open>In particular if a function is holomorphic\<close>
  2968 
  2969 lemma contour_integrable_holomorphic:
  2970   assumes contf: "continuous_on s f"
  2971       and os: "open s"
  2972       and k: "finite k"
  2973       and g: "valid_path g" "path_image g \<subseteq> s"
  2974       and fcd: "\<And>x. x \<in> s - k \<Longrightarrow> f field_differentiable at x"
  2975     shows "f contour_integrable_on g"
  2976 proof -
  2977   { fix z
  2978     assume z: "z \<in> s"
  2979     obtain d where "d>0" and d: "ball z d \<subseteq> s" using  \<open>open s\<close> z
  2980       by (auto simp: open_contains_ball)
  2981     then have contfb: "continuous_on (ball z d) f"
  2982       using contf continuous_on_subset by blast
  2983     obtain h where "\<forall>y\<in>ball z d. (h has_field_derivative f y) (at y within ball z d)"
  2984       by (metis holomorphic_convex_primitive [OF convex_ball k contfb fcd] d interior_subset Diff_iff set_mp)
  2985     then have "\<forall>y\<in>ball z d. (h has_field_derivative f y) (at y within s)"
  2986       by (metis open_ball at_within_open d os subsetCE)
  2987     then have "\<exists>h. (\<forall>y. cmod (y - z) < d \<longrightarrow> (h has_field_derivative f y) (at y within s))"
  2988       by (force simp: dist_norm norm_minus_commute)
  2989     then have "\<exists>d h. 0 < d \<and> (\<forall>y. cmod (y - z) < d \<longrightarrow> (h has_field_derivative f y) (at y within s))"
  2990       using \<open>0 < d\<close> by blast
  2991   }
  2992   then show ?thesis
  2993     by (rule contour_integral_local_primitive [OF g])
  2994 qed
  2995 
  2996 lemma contour_integrable_holomorphic_simple:
  2997   assumes fh: "f holomorphic_on S"
  2998       and os: "open S"
  2999       and g: "valid_path g" "path_image g \<subseteq> S"
  3000     shows "f contour_integrable_on g"
  3001   apply (rule contour_integrable_holomorphic [OF _ os Finite_Set.finite.emptyI g])
  3002   apply (simp add: fh holomorphic_on_imp_continuous_on)
  3003   using fh  by (simp add: field_differentiable_def holomorphic_on_open os)
  3004 
  3005 lemma continuous_on_inversediff:
  3006   fixes z:: "'a::real_normed_field" shows "z \<notin> S \<Longrightarrow> continuous_on S (\<lambda>w. 1 / (w - z))"
  3007   by (rule continuous_intros | force)+
  3008 
  3009 corollary contour_integrable_inversediff:
  3010     "\<lbrakk>valid_path g; z \<notin> path_image g\<rbrakk> \<Longrightarrow> (\<lambda>w. 1 / (w-z)) contour_integrable_on g"
  3011 apply (rule contour_integrable_holomorphic_simple [of _ "UNIV-{z}"])
  3012 apply (auto simp: holomorphic_on_open open_delete intro!: derivative_eq_intros)
  3013 done
  3014 
  3015 text\<open>Key fact that path integral is the same for a "nearby" path. This is the
  3016  main lemma for the homotopy form of Cauchy's theorem and is also useful
  3017  if we want "without loss of generality" to assume some nice properties of a
  3018  path (e.g. smoothness). It can also be used to define the integrals of
  3019  analytic functions over arbitrary continuous paths. This is just done for
  3020  winding numbers now.
  3021 \<close>
  3022 
  3023 text\<open>A technical definition to avoid duplication of similar proofs,
  3024      for paths joined at the ends versus looping paths\<close>
  3025 definition linked_paths :: "bool \<Rightarrow> (real \<Rightarrow> 'a) \<Rightarrow> (real \<Rightarrow> 'a::topological_space) \<Rightarrow> bool"
  3026   where "linked_paths atends g h ==
  3027         (if atends then pathstart h = pathstart g \<and> pathfinish h = pathfinish g
  3028                    else pathfinish g = pathstart g \<and> pathfinish h = pathstart h)"
  3029 
  3030 text\<open>This formulation covers two cases: @{term g} and @{term h} share their
  3031       start and end points; @{term g} and @{term h} both loop upon themselves.\<close>
  3032 lemma contour_integral_nearby:
  3033   assumes os: "open S" and p: "path p" "path_image p \<subseteq> S"
  3034   shows "\<exists>d. 0 < d \<and>
  3035             (\<forall>g h. valid_path g \<and> valid_path h \<and>
  3036                   (\<forall>t \<in> {0..1}. norm(g t - p t) < d \<and> norm(h t - p t) < d) \<and>
  3037                   linked_paths atends g h
  3038                   \<longrightarrow> path_image g \<subseteq> S \<and> path_image h \<subseteq> S \<and>
  3039                       (\<forall>f. f holomorphic_on S \<longrightarrow> contour_integral h f = contour_integral g f))"
  3040 proof -
  3041   have "\<forall>z. \<exists>e. z \<in> path_image p \<longrightarrow> 0 < e \<and> ball z e \<subseteq> S"
  3042     using open_contains_ball os p(2) by blast
  3043   then obtain ee where ee: "\<And>z. z \<in> path_image p \<Longrightarrow> 0 < ee z \<and> ball z (ee z) \<subseteq> S"
  3044     by metis
  3045   define cover where "cover = (\<lambda>z. ball z (ee z/3)) ` (path_image p)"
  3046   have "compact (path_image p)"
  3047     by (metis p(1) compact_path_image)
  3048   moreover have "path_image p \<subseteq> (\<Union>c\<in>path_image p. ball c (ee c / 3))"
  3049     using ee by auto
  3050   ultimately have "\<exists>D \<subseteq> cover. finite D \<and> path_image p \<subseteq> \<Union>D"
  3051     by (simp add: compact_eq_heine_borel cover_def)
  3052   then obtain D where D: "D \<subseteq> cover" "finite D" "path_image p \<subseteq> \<Union>D"
  3053     by blast
  3054   then obtain k where k: "k \<subseteq> {0..1}" "finite k" and D_eq: "D = ((\<lambda>z. ball z (ee z / 3)) \<circ> p) ` k"
  3055     apply (simp add: cover_def path_image_def image_comp)
  3056     apply (blast dest!: finite_subset_image [OF \<open>finite D\<close>])
  3057     done
  3058   then have kne: "k \<noteq> {}"
  3059     using D by auto
  3060   have pi: "\<And>i. i \<in> k \<Longrightarrow> p i \<in> path_image p"
  3061     using k  by (auto simp: path_image_def)
  3062   then have eepi: "\<And>i. i \<in> k \<Longrightarrow> 0 < ee((p i))"
  3063     by (metis ee)
  3064   define e where "e = Min((ee \<circ> p) ` k)"
  3065   have fin_eep: "finite ((ee \<circ> p) ` k)"
  3066     using k  by blast
  3067   have "0 < e"
  3068     using ee k  by (simp add: kne e_def Min_gr_iff [OF fin_eep] eepi)
  3069   have "uniformly_continuous_on {0..1} p"
  3070     using p  by (simp add: path_def compact_uniformly_continuous)
  3071   then obtain d::real where d: "d>0"
  3072           and de: "\<And>x x'. \<bar>x' - x\<bar> < d \<Longrightarrow> x\<in>{0..1} \<Longrightarrow> x'\<in>{0..1} \<Longrightarrow> cmod (p x' - p x) < e/3"
  3073     unfolding uniformly_continuous_on_def dist_norm real_norm_def
  3074     by (metis divide_pos_pos \<open>0 < e\<close> zero_less_numeral)
  3075   then obtain N::nat where N: "N>0" "inverse N < d"
  3076     using real_arch_inverse [of d]   by auto
  3077   show ?thesis
  3078   proof (intro exI conjI allI; clarify?)
  3079     show "e/3 > 0"
  3080       using \<open>0 < e\<close> by simp
  3081     fix g h
  3082     assume g: "valid_path g" and ghp: "\<forall>t\<in>{0..1}. cmod (g t - p t) < e / 3 \<and>  cmod (h t - p t) < e / 3"
  3083        and h: "valid_path h"
  3084        and joins: "linked_paths atends g h"
  3085     { fix t::real
  3086       assume t: "0 \<le> t" "t \<le> 1"
  3087       then obtain u where u: "u \<in> k" and ptu: "p t \<in> ball(p u) (ee(p u) / 3)"
  3088         using \<open>path_image p \<subseteq> \<Union>D\<close> D_eq by (force simp: path_image_def)
  3089       then have ele: "e \<le> ee (p u)" using fin_eep
  3090         by (simp add: e_def)
  3091       have "cmod (g t - p t) < e / 3" "cmod (h t - p t) < e / 3"
  3092         using ghp t by auto
  3093       with ele have "cmod (g t - p t) < ee (p u) / 3"
  3094                     "cmod (h t - p t) < ee (p u) / 3"
  3095         by linarith+
  3096       then have "g t \<in> ball(p u) (ee(p u))"  "h t \<in> ball(p u) (ee(p u))"
  3097         using norm_diff_triangle_ineq [of "g t" "p t" "p t" "p u"]
  3098               norm_diff_triangle_ineq [of "h t" "p t" "p t" "p u"] ptu eepi u
  3099         by (force simp: dist_norm ball_def norm_minus_commute)+
  3100       then have "g t \<in> S" "h t \<in> S" using ee u k
  3101         by (auto simp: path_image_def ball_def)
  3102     }
  3103     then have ghs: "path_image g \<subseteq> S" "path_image h \<subseteq> S"
  3104       by (auto simp: path_image_def)
  3105     moreover
  3106     { fix f
  3107       assume fhols: "f holomorphic_on S"
  3108       then have fpa: "f contour_integrable_on g"  "f contour_integrable_on h"
  3109         using g ghs h holomorphic_on_imp_continuous_on os contour_integrable_holomorphic_simple
  3110         by blast+
  3111       have contf: "continuous_on S f"
  3112         by (simp add: fhols holomorphic_on_imp_continuous_on)
  3113       { fix z
  3114         assume z: "z \<in> path_image p"
  3115         have "f holomorphic_on ball z (ee z)"
  3116           using fhols ee z holomorphic_on_subset by blast
  3117         then have "\<exists>ff. (\<forall>w \<in> ball z (ee z). (ff has_field_derivative f w) (at w))"
  3118           using holomorphic_convex_primitive [of "ball z (ee z)" "{}" f, simplified]
  3119           by (metis open_ball at_within_open holomorphic_on_def holomorphic_on_imp_continuous_on mem_ball)
  3120       }
  3121       then obtain ff where ff:
  3122             "\<And>z w. \<lbrakk>z \<in> path_image p; w \<in> ball z (ee z)\<rbrakk> \<Longrightarrow> (ff z has_field_derivative f w) (at w)"
  3123         by metis
  3124       { fix n
  3125         assume n: "n \<le> N"
  3126         then have "contour_integral(subpath 0 (n/N) h) f - contour_integral(subpath 0 (n/N) g) f =
  3127                    contour_integral(linepath (g(n/N)) (h(n/N))) f - contour_integral(linepath (g 0) (h 0)) f"
  3128         proof (induct n)
  3129           case 0 show ?case by simp
  3130         next
  3131           case (Suc n)
  3132           obtain t where t: "t \<in> k" and "p (n/N) \<in> ball(p t) (ee(p t) / 3)"
  3133             using \<open>path_image p \<subseteq> \<Union>D\<close> [THEN subsetD, where c="p (n/N)"] D_eq N Suc.prems
  3134             by (force simp: path_image_def)
  3135           then have ptu: "cmod (p t - p (n/N)) < ee (p t) / 3"
  3136             by (simp add: dist_norm)
  3137           have e3le: "e/3 \<le> ee (p t) / 3"  using fin_eep t
  3138             by (simp add: e_def)
  3139           { fix x
  3140             assume x: "n/N \<le> x" "x \<le> (1 + n)/N"
  3141             then have nN01: "0 \<le> n/N" "(1 + n)/N \<le> 1"
  3142               using Suc.prems by auto
  3143             then have x01: "0 \<le> x" "x \<le> 1"
  3144               using x by linarith+
  3145             have "cmod (p t - p x)  < ee (p t) / 3 + e/3"
  3146             proof (rule norm_diff_triangle_less [OF ptu de])
  3147               show "\<bar>real n / real N - x\<bar> < d"
  3148                 using x N by (auto simp: field_simps)
  3149             qed (use x01 Suc.prems in auto)
  3150             then have ptx: "cmod (p t - p x) < 2*ee (p t)/3"
  3151               using e3le eepi [OF t] by simp
  3152             have "cmod (p t - g x) < 2*ee (p t)/3 + e/3 "
  3153               apply (rule norm_diff_triangle_less [OF ptx])
  3154               using ghp x01 by (simp add: norm_minus_commute)
  3155             also have "\<dots> \<le> ee (p t)"
  3156               using e3le eepi [OF t] by simp
  3157             finally have gg: "cmod (p t - g x) < ee (p t)" .
  3158             have "cmod (p t - h x) < 2*ee (p t)/3 + e/3 "
  3159               apply (rule norm_diff_triangle_less [OF ptx])
  3160               using ghp x01 by (simp add: norm_minus_commute)
  3161             also have "\<dots> \<le> ee (p t)"
  3162               using e3le eepi [OF t] by simp
  3163             finally have "cmod (p t - g x) < ee (p t)"
  3164                          "cmod (p t - h x) < ee (p t)"
  3165               using gg by auto
  3166           } note ptgh_ee = this
  3167           have "closed_segment (g (real n / real N)) (h (real n / real N)) = path_image (linepath (h (n/N)) (g (n/N)))"
  3168             by (simp add: closed_segment_commute)
  3169           also have pi_hgn: "\<dots> \<subseteq> ball (p t) (ee (p t))"
  3170             using ptgh_ee [of "n/N"] Suc.prems
  3171             by (auto simp: field_simps dist_norm dest: segment_furthest_le [where y="p t"])
  3172           finally have gh_ns: "closed_segment (g (n/N)) (h (n/N)) \<subseteq> S"
  3173             using ee pi t by blast
  3174           have pi_ghn': "path_image (linepath (g ((1 + n) / N)) (h ((1 + n) / N))) \<subseteq> ball (p t) (ee (p t))"
  3175             using ptgh_ee [of "(1+n)/N"] Suc.prems
  3176             by (auto simp: field_simps dist_norm dest: segment_furthest_le [where y="p t"])
  3177           then have gh_n's: "closed_segment (g ((1 + n) / N)) (h ((1 + n) / N)) \<subseteq> S"
  3178             using \<open>N>0\<close> Suc.prems ee pi t
  3179             by (auto simp: Path_Connected.path_image_join field_simps)
  3180           have pi_subset_ball:
  3181                 "path_image (subpath (n/N) ((1+n) / N) g +++ linepath (g ((1+n) / N)) (h ((1+n) / N)) +++
  3182                              subpath ((1+n) / N) (n/N) h +++ linepath (h (n/N)) (g (n/N)))
  3183                  \<subseteq> ball (p t) (ee (p t))"
  3184             apply (intro subset_path_image_join pi_hgn pi_ghn')
  3185             using \<open>N>0\<close> Suc.prems
  3186             apply (auto simp: path_image_subpath dist_norm field_simps closed_segment_eq_real_ivl ptgh_ee)
  3187             done
  3188           have pi0: "(f has_contour_integral 0)
  3189                        (subpath (n/ N) ((Suc n)/N) g +++ linepath(g ((Suc n) / N)) (h((Suc n) / N)) +++
  3190                         subpath ((Suc n) / N) (n/N) h +++ linepath(h (n/N)) (g (n/N)))"
  3191             apply (rule Cauchy_theorem_primitive [of "ball(p t) (ee(p t))" "ff (p t)" "f"])
  3192             apply (metis ff open_ball at_within_open pi t)
  3193             using Suc.prems pi_subset_ball apply (simp_all add: valid_path_join valid_path_subpath g h)
  3194             done
  3195           have fpa1: "f contour_integrable_on subpath (real n / real N) (real (Suc n) / real N) g"
  3196             using Suc.prems by (simp add: contour_integrable_subpath g fpa)
  3197           have fpa2: "f contour_integrable_on linepath (g (real (Suc n) / real N)) (h (real (Suc n) / real N))"
  3198             using gh_n's
  3199             by (auto intro!: contour_integrable_continuous_linepath continuous_on_subset [OF contf])
  3200           have fpa3: "f contour_integrable_on linepath (h (real n / real N)) (g (real n / real N))"
  3201             using gh_ns
  3202             by (auto simp: closed_segment_commute intro!: contour_integrable_continuous_linepath continuous_on_subset [OF contf])
  3203           have eq0: "contour_integral (subpath (n/N) ((Suc n) / real N) g) f +
  3204                      contour_integral (linepath (g ((Suc n) / N)) (h ((Suc n) / N))) f +
  3205                      contour_integral (subpath ((Suc n) / N) (n/N) h) f +
  3206                      contour_integral (linepath (h (n/N)) (g (n/N))) f = 0"
  3207             using contour_integral_unique [OF pi0] Suc.prems
  3208             by (simp add: g h fpa valid_path_subpath contour_integrable_subpath
  3209                           fpa1 fpa2 fpa3 algebra_simps del: of_nat_Suc)
  3210           have *: "\<And>hn he hn' gn gd gn' hgn ghn gh0 ghn'.
  3211                     \<lbrakk>hn - gn = ghn - gh0;
  3212                      gd + ghn' + he + hgn = (0::complex);
  3213                      hn - he = hn'; gn + gd = gn'; hgn = -ghn\<rbrakk> \<Longrightarrow> hn' - gn' = ghn' - gh0"
  3214             by (auto simp: algebra_simps)
  3215           have "contour_integral (subpath 0 (n/N) h) f - contour_integral (subpath ((Suc n) / N) (n/N) h) f =
  3216                 contour_integral (subpath 0 (n/N) h) f + contour_integral (subpath (n/N) ((Suc n) / N) h) f"
  3217             unfolding reversepath_subpath [symmetric, of "((Suc n) / N)"]
  3218             using Suc.prems by (simp add: h fpa contour_integral_reversepath valid_path_subpath contour_integrable_subpath)
  3219           also have "\<dots> = contour_integral (subpath 0 ((Suc n) / N) h) f"
  3220             using Suc.prems by (simp add: contour_integral_subpath_combine h fpa)
  3221           finally have pi0_eq:
  3222                "contour_integral (subpath 0 (n/N) h) f - contour_integral (subpath ((Suc n) / N) (n/N) h) f =
  3223                 contour_integral (subpath 0 ((Suc n) / N) h) f" .
  3224           show ?case
  3225             apply (rule * [OF Suc.hyps eq0 pi0_eq])
  3226             using Suc.prems
  3227             apply (simp_all add: g h fpa contour_integral_subpath_combine
  3228                      contour_integral_reversepath [symmetric] contour_integrable_continuous_linepath
  3229                      continuous_on_subset [OF contf gh_ns])
  3230             done
  3231       qed
  3232       } note ind = this
  3233       have "contour_integral h f = contour_integral g f"
  3234         using ind [OF order_refl] N joins
  3235         by (simp add: linked_paths_def pathstart_def pathfinish_def split: if_split_asm)
  3236     }
  3237     ultimately
  3238     show "path_image g \<subseteq> S \<and> path_image h \<subseteq> S \<and> (\<forall>f. f holomorphic_on S \<longrightarrow> contour_integral h f = contour_integral g f)"
  3239       by metis
  3240   qed
  3241 qed
  3242 
  3243 
  3244 lemma
  3245   assumes "open S" "path p" "path_image p \<subseteq> S"
  3246     shows contour_integral_nearby_ends:
  3247       "\<exists>d. 0 < d \<and>
  3248               (\<forall>g h. valid_path g \<and> valid_path h \<and>
  3249                     (\<forall>t \<in> {0..1}. norm(g t - p t) < d \<and> norm(h t - p t) < d) \<and>
  3250                     pathstart h = pathstart g \<and> pathfinish h = pathfinish g
  3251                     \<longrightarrow> path_image g \<subseteq> S \<and>
  3252                         path_image h \<subseteq> S \<and>
  3253                         (\<forall>f. f holomorphic_on S
  3254                             \<longrightarrow> contour_integral h f = contour_integral g f))"
  3255     and contour_integral_nearby_loops:
  3256       "\<exists>d. 0 < d \<and>
  3257               (\<forall>g h. valid_path g \<and> valid_path h \<and>
  3258                     (\<forall>t \<in> {0..1}. norm(g t - p t) < d \<and> norm(h t - p t) < d) \<and>
  3259                     pathfinish g = pathstart g \<and> pathfinish h = pathstart h
  3260                     \<longrightarrow> path_image g \<subseteq> S \<and>
  3261                         path_image h \<subseteq> S \<and>
  3262                         (\<forall>f. f holomorphic_on S
  3263                             \<longrightarrow> contour_integral h f = contour_integral g f))"
  3264   using contour_integral_nearby [OF assms, where atends=True]
  3265   using contour_integral_nearby [OF assms, where atends=False]
  3266   unfolding linked_paths_def by simp_all
  3267 
  3268 lemma C1_differentiable_polynomial_function:
  3269   fixes p :: "real \<Rightarrow> 'a::euclidean_space"
  3270   shows "polynomial_function p \<Longrightarrow> p C1_differentiable_on S"
  3271   by (metis continuous_on_polymonial_function C1_differentiable_on_def  has_vector_derivative_polynomial_function)
  3272 
  3273 lemma valid_path_polynomial_function:
  3274   fixes p :: "real \<Rightarrow> 'a::euclidean_space"
  3275   shows "polynomial_function p \<Longrightarrow> valid_path p"
  3276 by (force simp: valid_path_def piecewise_C1_differentiable_on_def continuous_on_polymonial_function C1_differentiable_polynomial_function)
  3277 
  3278 lemma valid_path_subpath_trivial [simp]:
  3279     fixes g :: "real \<Rightarrow> 'a::euclidean_space"
  3280     shows "z \<noteq> g x \<Longrightarrow> valid_path (subpath x x g)"
  3281   by (simp add: subpath_def valid_path_polynomial_function)
  3282 
  3283 lemma contour_integral_bound_exists:
  3284 assumes S: "open S"
  3285     and g: "valid_path g"
  3286     and pag: "path_image g \<subseteq> S"
  3287   shows "\<exists>L. 0 < L \<and>
  3288              (\<forall>f B. f holomorphic_on S \<and> (\<forall>z \<in> S. norm(f z) \<le> B)
  3289                \<longrightarrow> norm(contour_integral g f) \<le> L*B)"
  3290 proof -
  3291   have "path g" using g
  3292     by (simp add: valid_path_imp_path)
  3293   then obtain d::real and p
  3294     where d: "0 < d"
  3295       and p: "polynomial_function p" "path_image p \<subseteq> S"
  3296       and pi: "\<And>f. f holomorphic_on S \<Longrightarrow> contour_integral g f = contour_integral p f"
  3297     using contour_integral_nearby_ends [OF S \<open>path g\<close> pag]
  3298     apply clarify
  3299     apply (drule_tac x=g in spec)
  3300     apply (simp only: assms)
  3301     apply (force simp: valid_path_polynomial_function dest: path_approx_polynomial_function)
  3302     done
  3303   then obtain p' where p': "polynomial_function p'"
  3304     "\<And>x. (p has_vector_derivative (p' x)) (at x)"
  3305     by (blast intro: has_vector_derivative_polynomial_function that)
  3306   then have "bounded(p' ` {0..1})"
  3307     using continuous_on_polymonial_function
  3308     by (force simp: intro!: compact_imp_bounded compact_continuous_image)
  3309   then obtain L where L: "L>0" and nop': "\<And>x. \<lbrakk>0 \<le> x; x \<le> 1\<rbrakk> \<Longrightarrow> norm (p' x) \<le> L"
  3310     by (force simp: bounded_pos)
  3311   { fix f B
  3312     assume f: "f holomorphic_on S" and B: "\<And>z. z\<in>S \<Longrightarrow> cmod (f z) \<le> B"
  3313     then have "f contour_integrable_on p \<and> valid_path p"
  3314       using p S
  3315       by (blast intro: valid_path_polynomial_function contour_integrable_holomorphic_simple holomorphic_on_imp_continuous_on)
  3316     moreover have "cmod (vector_derivative p (at x)) * cmod (f (p x)) \<le> L * B" if "0 \<le> x" "x \<le> 1" for x
  3317     proof (rule mult_mono)
  3318       show "cmod (vector_derivative p (at x)) \<le> L"
  3319         by (metis nop' p'(2) that vector_derivative_at)
  3320       show "cmod (f (p x)) \<le> B"
  3321         by (metis B atLeastAtMost_iff imageI p(2) path_defs(4) subset_eq that)
  3322     qed (use \<open>L>0\<close> in auto)
  3323     ultimately have "cmod (contour_integral g f) \<le> L * B"
  3324       apply (simp only: pi [OF f])
  3325       apply (simp only: contour_integral_integral)
  3326       apply (rule order_trans [OF integral_norm_bound_integral])
  3327          apply (auto simp: mult.commute integral_norm_bound_integral contour_integrable_on [symmetric] norm_mult)
  3328       done
  3329   } then
  3330   show ?thesis
  3331     by (force simp: L contour_integral_integral)
  3332 qed
  3333 
  3334 text\<open>We can treat even non-rectifiable paths as having a "length" for bounds on analytic functions in open sets.\<close>
  3335 
  3336 subsection\<open>Winding Numbers\<close>
  3337 
  3338 definition winding_number_prop :: "[real \<Rightarrow> complex, complex, real, real \<Rightarrow> complex, complex] \<Rightarrow> bool" where
  3339   "winding_number_prop \<gamma> z e p n \<equiv>
  3340       valid_path p \<and> z \<notin> path_image p \<and>
  3341       pathstart p = pathstart \<gamma> \<and>
  3342       pathfinish p = pathfinish \<gamma> \<and>
  3343       (\<forall>t \<in> {0..1}. norm(\<gamma> t - p t) < e) \<and>
  3344       contour_integral p (\<lambda>w. 1/(w - z)) = 2 * pi * \<i> * n"
  3345 
  3346 definition winding_number:: "[real \<Rightarrow> complex, complex] \<Rightarrow> complex" where
  3347   "winding_number \<gamma> z \<equiv> SOME n. \<forall>e > 0. \<exists>p. winding_number_prop \<gamma> z e p n"
  3348 
  3349 
  3350 lemma winding_number:
  3351   assumes "path \<gamma>" "z \<notin> path_image \<gamma>" "0 < e"
  3352     shows "\<exists>p. winding_number_prop \<gamma> z e p (winding_number \<gamma> z)"
  3353 proof -
  3354   have "path_image \<gamma> \<subseteq> UNIV - {z}"
  3355     using assms by blast
  3356   then obtain d
  3357     where d: "d>0"
  3358       and pi_eq: "\<And>h1 h2. valid_path h1 \<and> valid_path h2 \<and>
  3359                     (\<forall>t\<in>{0..1}. cmod (h1 t - \<gamma> t) < d \<and> cmod (h2 t - \<gamma> t) < d) \<and>
  3360                     pathstart h2 = pathstart h1 \<and> pathfinish h2 = pathfinish h1 \<longrightarrow>
  3361                       path_image h1 \<subseteq> UNIV - {z} \<and> path_image h2 \<subseteq> UNIV - {z} \<and>
  3362                       (\<forall>f. f holomorphic_on UNIV - {z} \<longrightarrow> contour_integral h2 f = contour_integral h1 f)"
  3363     using contour_integral_nearby_ends [of "UNIV - {z}" \<gamma>] assms by (auto simp: open_delete)
  3364   then obtain h where h: "polynomial_function h \<and> pathstart h = pathstart \<gamma> \<and> pathfinish h = pathfinish \<gamma> \<and>
  3365                           (\<forall>t \<in> {0..1}. norm(h t - \<gamma> t) < d/2)"
  3366     using path_approx_polynomial_function [OF \<open>path \<gamma>\<close>, of "d/2"] d by auto
  3367   define nn where "nn = 1/(2* pi*\<i>) * contour_integral h (\<lambda>w. 1/(w - z))"
  3368   have "\<exists>n. \<forall>e > 0. \<exists>p. winding_number_prop \<gamma> z e p n"
  3369     proof (rule_tac x=nn in exI, clarify)
  3370       fix e::real
  3371       assume e: "e>0"
  3372       obtain p where p: "polynomial_function p \<and>
  3373             pathstart p = pathstart \<gamma> \<and> pathfinish p = pathfinish \<gamma> \<and> (\<forall>t\<in>{0..1}. cmod (p t - \<gamma> t) < min e (d/2))"
  3374         using path_approx_polynomial_function [OF \<open>path \<gamma>\<close>, of "min e (d/2)"] d \<open>0<e\<close> by auto
  3375       have "(\<lambda>w. 1 / (w - z)) holomorphic_on UNIV - {z}"
  3376         by (auto simp: intro!: holomorphic_intros)
  3377       then show "\<exists>p. winding_number_prop \<gamma> z e p nn"
  3378         apply (rule_tac x=p in exI)
  3379         using pi_eq [of h p] h p d
  3380         apply (auto simp: valid_path_polynomial_function norm_minus_commute nn_def winding_number_prop_def)
  3381         done
  3382     qed
  3383   then show ?thesis
  3384     unfolding winding_number_def by (rule someI2_ex) (blast intro: \<open>0<e\<close>)
  3385 qed
  3386 
  3387 lemma winding_number_unique:
  3388   assumes \<gamma>: "path \<gamma>" "z \<notin> path_image \<gamma>"
  3389       and pi: "\<And>e. e>0 \<Longrightarrow> \<exists>p. winding_number_prop \<gamma> z e p n"
  3390    shows "winding_number \<gamma> z = n"
  3391 proof -
  3392   have "path_image \<gamma> \<subseteq> UNIV - {z}"
  3393     using assms by blast
  3394   then obtain e
  3395     where e: "e>0"
  3396       and pi_eq: "\<And>h1 h2 f. \<lbrakk>valid_path h1; valid_path h2;
  3397                     (\<forall>t\<in>{0..1}. cmod (h1 t - \<gamma> t) < e \<and> cmod (h2 t - \<gamma> t) < e);
  3398                     pathstart h2 = pathstart h1; pathfinish h2 = pathfinish h1; f holomorphic_on UNIV - {z}\<rbrakk> \<Longrightarrow>
  3399                     contour_integral h2 f = contour_integral h1 f"
  3400     using contour_integral_nearby_ends [of "UNIV - {z}" \<gamma>] assms  by (auto simp: open_delete)
  3401   obtain p where p: "winding_number_prop \<gamma> z e p n"
  3402     using pi [OF e] by blast
  3403   obtain q where q: "winding_number_prop \<gamma> z e q (winding_number \<gamma> z)"
  3404     using winding_number [OF \<gamma> e] by blast
  3405   have "2 * complex_of_real pi * \<i> * n = contour_integral p (\<lambda>w. 1 / (w - z))"
  3406     using p by (auto simp: winding_number_prop_def)
  3407   also have "\<dots> = contour_integral q (\<lambda>w. 1 / (w - z))"
  3408   proof (rule pi_eq)
  3409     show "(\<lambda>w. 1 / (w - z)) holomorphic_on UNIV - {z}"
  3410       by (auto intro!: holomorphic_intros)
  3411   qed (use p q in \<open>auto simp: winding_number_prop_def norm_minus_commute\<close>)
  3412   also have "\<dots> = 2 * complex_of_real pi * \<i> * winding_number \<gamma> z"
  3413     using q by (auto simp: winding_number_prop_def)
  3414   finally have "2 * complex_of_real pi * \<i> * n = 2 * complex_of_real pi * \<i> * winding_number \<gamma> z" .
  3415   then show ?thesis
  3416     by simp
  3417 qed
  3418 
  3419 (*NB not winding_number_prop here due to the loop in p*)
  3420 lemma winding_number_unique_loop:
  3421   assumes \<gamma>: "path \<gamma>" "z \<notin> path_image \<gamma>"
  3422       and loop: "pathfinish \<gamma> = pathstart \<gamma>"
  3423       and pi:
  3424         "\<And>e. e>0 \<Longrightarrow> \<exists>p. valid_path p \<and> z \<notin> path_image p \<and>
  3425                            pathfinish p = pathstart p \<and>
  3426                            (\<forall>t \<in> {0..1}. norm (\<gamma> t - p t) < e) \<and>
  3427                            contour_integral p (\<lambda>w. 1/(w - z)) = 2 * pi * \<i> * n"
  3428    shows "winding_number \<gamma> z = n"
  3429 proof -
  3430   have "path_image \<gamma> \<subseteq> UNIV - {z}"
  3431     using assms by blast
  3432   then obtain e
  3433     where e: "e>0"
  3434       and pi_eq: "\<And>h1 h2 f. \<lbrakk>valid_path h1; valid_path h2;
  3435                     (\<forall>t\<in>{0..1}. cmod (h1 t - \<gamma> t) < e \<and> cmod (h2 t - \<gamma> t) < e);
  3436                     pathfinish h1 = pathstart h1; pathfinish h2 = pathstart h2; f holomorphic_on UNIV - {z}\<rbrakk> \<Longrightarrow>
  3437                     contour_integral h2 f = contour_integral h1 f"
  3438     using contour_integral_nearby_loops [of "UNIV - {z}" \<gamma>] assms  by (auto simp: open_delete)
  3439   obtain p where p:
  3440      "valid_path p \<and> z \<notin> path_image p \<and> pathfinish p = pathstart p \<and>
  3441       (\<forall>t \<in> {0..1}. norm (\<gamma> t - p t) < e) \<and>
  3442       contour_integral p (\<lambda>w. 1/(w - z)) = 2 * pi * \<i> * n"
  3443     using pi [OF e] by blast
  3444   obtain q where q: "winding_number_prop \<gamma> z e q (winding_number \<gamma> z)"
  3445     using winding_number [OF \<gamma> e] by blast
  3446   have "2 * complex_of_real pi * \<i> * n = contour_integral p (\<lambda>w. 1 / (w - z))"
  3447     using p by auto
  3448   also have "\<dots> = contour_integral q (\<lambda>w. 1 / (w - z))"
  3449   proof (rule pi_eq)
  3450     show "(\<lambda>w. 1 / (w - z)) holomorphic_on UNIV - {z}"
  3451       by (auto intro!: holomorphic_intros)
  3452   qed (use p q loop in \<open>auto simp: winding_number_prop_def norm_minus_commute\<close>)
  3453   also have "\<dots> = 2 * complex_of_real pi * \<i> * winding_number \<gamma> z"
  3454     using q by (auto simp: winding_number_prop_def)
  3455   finally have "2 * complex_of_real pi * \<i> * n = 2 * complex_of_real pi * \<i> * winding_number \<gamma> z" .
  3456   then show ?thesis
  3457     by simp
  3458 qed
  3459 
  3460 lemma winding_number_valid_path:
  3461   assumes "valid_path \<gamma>" "z \<notin> path_image \<gamma>"
  3462   shows "winding_number \<gamma> z = 1/(2*pi*\<i>) * contour_integral \<gamma> (\<lambda>w. 1/(w - z))"
  3463   by (rule winding_number_unique)
  3464   (use assms in \<open>auto simp: valid_path_imp_path winding_number_prop_def\<close>)
  3465 
  3466 lemma has_contour_integral_winding_number:
  3467   assumes \<gamma>: "valid_path \<gamma>" "z \<notin> path_image \<gamma>"
  3468     shows "((\<lambda>w. 1/(w - z)) has_contour_integral (2*pi*\<i>*winding_number \<gamma> z)) \<gamma>"
  3469 by (simp add: winding_number_valid_path has_contour_integral_integral contour_integrable_inversediff assms)
  3470 
  3471 lemma winding_number_trivial [simp]: "z \<noteq> a \<Longrightarrow> winding_number(linepath a a) z = 0"
  3472   by (simp add: winding_number_valid_path)
  3473 
  3474 lemma winding_number_subpath_trivial [simp]: "z \<noteq> g x \<Longrightarrow> winding_number (subpath x x g) z = 0"
  3475   by (simp add: path_image_subpath winding_number_valid_path)
  3476 
  3477 lemma winding_number_join:
  3478   assumes \<gamma>1: "path \<gamma>1" "z \<notin> path_image \<gamma>1"
  3479       and \<gamma>2: "path \<gamma>2" "z \<notin> path_image \<gamma>2"
  3480       and "pathfinish \<gamma>1 = pathstart \<gamma>2"
  3481     shows "winding_number(\<gamma>1 +++ \<gamma>2) z = winding_number \<gamma>1 z + winding_number \<gamma>2 z"
  3482 proof (rule winding_number_unique)
  3483   show "\<exists>p. winding_number_prop (\<gamma>1 +++ \<gamma>2) z e p
  3484               (winding_number \<gamma>1 z + winding_number \<gamma>2 z)" if "e > 0" for e
  3485   proof -
  3486     obtain p1 where "winding_number_prop \<gamma>1 z e p1 (winding_number \<gamma>1 z)"
  3487       using \<open>0 < e\<close> \<gamma>1 winding_number by blast
  3488     moreover
  3489     obtain p2 where "winding_number_prop \<gamma>2 z e p2 (winding_number \<gamma>2 z)"
  3490       using \<open>0 < e\<close> \<gamma>2 winding_number by blast
  3491     ultimately
  3492     have "winding_number_prop (\<gamma>1+++\<gamma>2) z e (p1+++p2) (winding_number \<gamma>1 z + winding_number \<gamma>2 z)"
  3493       using assms
  3494       apply (simp add: winding_number_prop_def not_in_path_image_join contour_integrable_inversediff algebra_simps)
  3495       apply (auto simp: joinpaths_def)
  3496       done
  3497     then show ?thesis
  3498       by blast
  3499   qed
  3500 qed (use assms in \<open>auto simp: not_in_path_image_join\<close>)
  3501 
  3502 lemma winding_number_reversepath:
  3503   assumes "path \<gamma>" "z \<notin> path_image \<gamma>"
  3504     shows "winding_number(reversepath \<gamma>) z = - (winding_number \<gamma> z)"
  3505 proof (rule winding_number_unique)
  3506   show "\<exists>p. winding_number_prop (reversepath \<gamma>) z e p (- winding_number \<gamma> z)" if "e > 0" for e
  3507   proof -
  3508     obtain p where "winding_number_prop \<gamma> z e p (winding_number \<gamma> z)"
  3509       using \<open>0 < e\<close> assms winding_number by blast
  3510     then have "winding_number_prop (reversepath \<gamma>) z e (reversepath p) (- winding_number \<gamma> z)"
  3511       using assms
  3512       apply (simp add: winding_number_prop_def contour_integral_reversepath contour_integrable_inversediff valid_path_imp_reverse)
  3513       apply (auto simp: reversepath_def)
  3514       done
  3515     then show ?thesis
  3516       by blast
  3517   qed
  3518 qed (use assms in auto)
  3519 
  3520 lemma winding_number_shiftpath:
  3521   assumes \<gamma>: "path \<gamma>" "z \<notin> path_image \<gamma>"
  3522       and "pathfinish \<gamma> = pathstart \<gamma>" "a \<in> {0..1}"
  3523     shows "winding_number(shiftpath a \<gamma>) z = winding_number \<gamma> z"
  3524 proof (rule winding_number_unique_loop)
  3525   show "\<exists>p. valid_path p \<and> z \<notin> path_image p \<and> pathfinish p = pathstart p \<and>
  3526             (\<forall>t\<in>{0..1}. cmod (shiftpath a \<gamma> t - p t) < e) \<and>
  3527             contour_integral p (\<lambda>w. 1 / (w - z)) =
  3528             complex_of_real (2 * pi) * \<i> * winding_number \<gamma> z"
  3529     if "e > 0" for e
  3530   proof -
  3531     obtain p where "winding_number_prop \<gamma> z e p (winding_number \<gamma> z)"
  3532       using \<open>0 < e\<close> assms winding_number by blast
  3533     then show ?thesis
  3534       apply (rule_tac x="shiftpath a p" in exI)
  3535       using assms that
  3536       apply (auto simp: winding_number_prop_def path_image_shiftpath pathfinish_shiftpath pathstart_shiftpath contour_integral_shiftpath)
  3537       apply (simp add: shiftpath_def)
  3538       done
  3539   qed
  3540 qed (use assms in \<open>auto simp: path_shiftpath path_image_shiftpath pathfinish_shiftpath pathstart_shiftpath\<close>)
  3541 
  3542 lemma winding_number_split_linepath:
  3543   assumes "c \<in> closed_segment a b" "z \<notin> closed_segment a b"
  3544     shows "winding_number(linepath a b) z = winding_number(linepath a c) z + winding_number(linepath c b) z"
  3545 proof -
  3546   have "z \<notin> closed_segment a c" "z \<notin> closed_segment c b"
  3547     using assms  by (meson convex_contains_segment convex_segment ends_in_segment subsetCE)+
  3548   then show ?thesis
  3549     using assms
  3550     by (simp add: winding_number_valid_path contour_integral_split_linepath [symmetric] continuous_on_inversediff field_simps)
  3551 qed
  3552 
  3553 lemma winding_number_cong:
  3554    "(\<And>t. \<lbrakk>0 \<le> t; t \<le> 1\<rbrakk> \<Longrightarrow> p t = q t) \<Longrightarrow> winding_number p z = winding_number q z"
  3555   by (simp add: winding_number_def winding_number_prop_def pathstart_def pathfinish_def)
  3556 
  3557 lemma winding_number_offset: "winding_number p z = winding_number (\<lambda>w. p w - z) 0"
  3558   unfolding winding_number_def
  3559 proof (intro ext arg_cong [where f = Eps] arg_cong [where f = All] imp_cong refl, safe)
  3560   fix n e g
  3561   assume "0 < e" and g: "winding_number_prop p z e g n"
  3562   then show "\<exists>r. winding_number_prop (\<lambda>w. p w - z) 0 e r n"
  3563     by (rule_tac x="\<lambda>t. g t - z" in exI)
  3564        (force simp: winding_number_prop_def contour_integral_integral valid_path_def path_defs  
  3565                 vector_derivative_def has_vector_derivative_diff_const piecewise_C1_differentiable_diff C1_differentiable_imp_piecewise)
  3566 next
  3567   fix n e g
  3568   assume "0 < e" and g: "winding_number_prop (\<lambda>w. p w - z) 0 e g n"
  3569   then show "\<exists>r. winding_number_prop p z e r n"
  3570     apply (rule_tac x="\<lambda>t. g t + z" in exI)
  3571     apply (simp add: winding_number_prop_def contour_integral_integral valid_path_def path_defs 
  3572         piecewise_C1_differentiable_add vector_derivative_def has_vector_derivative_add_const C1_differentiable_imp_piecewise)
  3573     apply (force simp: algebra_simps)
  3574     done
  3575 qed
  3576 
  3577 subsubsection\<open>Some lemmas about negating a path\<close>
  3578 
  3579 lemma valid_path_negatepath: "valid_path \<gamma> \<Longrightarrow> valid_path (uminus \<circ> \<gamma>)"
  3580    unfolding o_def using piecewise_C1_differentiable_neg valid_path_def by blast
  3581 
  3582 lemma has_contour_integral_negatepath:
  3583   assumes \<gamma>: "valid_path \<gamma>" and cint: "((\<lambda>z. f (- z)) has_contour_integral - i) \<gamma>"
  3584   shows "(f has_contour_integral i) (uminus \<circ> \<gamma>)"
  3585 proof -
  3586   obtain S where cont: "continuous_on {0..1} \<gamma>" and "finite S" and diff: "\<gamma> C1_differentiable_on {0..1} - S"
  3587     using \<gamma> by (auto simp: valid_path_def piecewise_C1_differentiable_on_def)
  3588   have "((\<lambda>x. - (f (- \<gamma> x) * vector_derivative \<gamma> (at x within {0..1}))) has_integral i) {0..1}"
  3589     using cint by (auto simp: has_contour_integral_def dest: has_integral_neg)
  3590   then
  3591   have "((\<lambda>x. f (- \<gamma> x) * vector_derivative (uminus \<circ> \<gamma>) (at x within {0..1})) has_integral i) {0..1}"
  3592   proof (rule rev_iffD1 [OF _ has_integral_spike_eq])
  3593     show "negligible S"
  3594       by (simp add: \<open>finite S\<close> negligible_finite)
  3595     show "f (- \<gamma> x) * vector_derivative (uminus \<circ> \<gamma>) (at x within {0..1}) =
  3596          - (f (- \<gamma> x) * vector_derivative \<gamma> (at x within {0..1}))"
  3597       if "x \<in> {0..1} - S" for x
  3598     proof -
  3599       have "vector_derivative (uminus \<circ> \<gamma>) (at x within cbox 0 1) = - vector_derivative \<gamma> (at x within cbox 0 1)"
  3600       proof (rule vector_derivative_within_cbox)
  3601         show "(uminus \<circ> \<gamma> has_vector_derivative - vector_derivative \<gamma> (at x within cbox 0 1)) (at x within cbox 0 1)"
  3602           using that unfolding o_def
  3603           by (metis C1_differentiable_on_eq UNIV_I diff differentiable_subset has_vector_derivative_minus subsetI that vector_derivative_works)
  3604       qed (use that in auto)
  3605       then show ?thesis
  3606         by simp
  3607     qed
  3608   qed
  3609   then show ?thesis by (simp add: has_contour_integral_def)
  3610 qed
  3611 
  3612 lemma winding_number_negatepath:
  3613   assumes \<gamma>: "valid_path \<gamma>" and 0: "0 \<notin> path_image \<gamma>"
  3614   shows "winding_number(uminus \<circ> \<gamma>) 0 = winding_number \<gamma> 0"
  3615 proof -
  3616   have "(/) 1 contour_integrable_on \<gamma>"
  3617     using "0" \<gamma> contour_integrable_inversediff by fastforce
  3618   then have "((\<lambda>z. 1/z) has_contour_integral contour_integral \<gamma> ((/) 1)) \<gamma>"
  3619     by (rule has_contour_integral_integral)
  3620   then have "((\<lambda>z. 1 / - z) has_contour_integral - contour_integral \<gamma> ((/) 1)) \<gamma>"
  3621     using has_contour_integral_neg by auto
  3622   then show ?thesis
  3623     using assms
  3624     apply (simp add: winding_number_valid_path valid_path_negatepath image_def path_defs)
  3625     apply (simp add: contour_integral_unique has_contour_integral_negatepath)
  3626     done
  3627 qed
  3628 
  3629 lemma contour_integrable_negatepath:
  3630   assumes \<gamma>: "valid_path \<gamma>" and pi: "(\<lambda>z. f (- z)) contour_integrable_on \<gamma>"
  3631   shows "f contour_integrable_on (uminus \<circ> \<gamma>)"
  3632   by (metis \<gamma> add.inverse_inverse contour_integrable_on_def has_contour_integral_negatepath pi)
  3633 
  3634 (* A combined theorem deducing several things piecewise.*)
  3635 lemma winding_number_join_pos_combined:
  3636      "\<lbrakk>valid_path \<gamma>1; z \<notin> path_image \<gamma>1; 0 < Re(winding_number \<gamma>1 z);
  3637        valid_path \<gamma>2; z \<notin> path_image \<gamma>2; 0 < Re(winding_number \<gamma>2 z); pathfinish \<gamma>1 = pathstart \<gamma>2\<rbrakk>
  3638       \<Longrightarrow> valid_path(\<gamma>1 +++ \<gamma>2) \<and> z \<notin> path_image(\<gamma>1 +++ \<gamma>2) \<and> 0 < Re(winding_number(\<gamma>1 +++ \<gamma>2) z)"
  3639   by (simp add: valid_path_join path_image_join winding_number_join valid_path_imp_path)
  3640 
  3641 
  3642 subsubsection\<open>Useful sufficient conditions for the winding number to be positive\<close>
  3643 
  3644 lemma Re_winding_number:
  3645     "\<lbrakk>valid_path \<gamma>; z \<notin> path_image \<gamma>\<rbrakk>
  3646      \<Longrightarrow> Re(winding_number \<gamma> z) = Im(contour_integral \<gamma> (\<lambda>w. 1/(w - z))) / (2*pi)"
  3647 by (simp add: winding_number_valid_path field_simps Re_divide power2_eq_square)
  3648 
  3649 lemma winding_number_pos_le:
  3650   assumes \<gamma>: "valid_path \<gamma>" "z \<notin> path_image \<gamma>"
  3651       and ge: "\<And>x. \<lbrakk>0 < x; x < 1\<rbrakk> \<Longrightarrow> 0 \<le> Im (vector_derivative \<gamma> (at x) * cnj(\<gamma> x - z))"
  3652     shows "0 \<le> Re(winding_number \<gamma> z)"
  3653 proof -
  3654   have ge0: "0 \<le> Im (vector_derivative \<gamma> (at x) / (\<gamma> x - z))" if x: "0 < x" "x < 1" for x
  3655     using ge by (simp add: Complex.Im_divide algebra_simps x)
  3656   let ?vd = "\<lambda>x. 1 / (\<gamma> x - z) * vector_derivative \<gamma> (at x)"
  3657   let ?int = "\<lambda>z. contour_integral \<gamma> (\<lambda>w. 1 / (w - z))"
  3658   have hi: "(?vd has_integral ?int z) (cbox 0 1)"
  3659     unfolding box_real
  3660     apply (subst has_contour_integral [symmetric])
  3661     using \<gamma> by (simp add: contour_integrable_inversediff has_contour_integral_integral)
  3662   have "0 \<le> Im (?int z)"
  3663   proof (rule has_integral_component_nonneg [of \<i>, simplified])
  3664     show "\<And>x. x \<in> cbox 0 1 \<Longrightarrow> 0 \<le> Im (if 0 < x \<and> x < 1 then ?vd x else 0)"
  3665       by (force simp: ge0)
  3666     show "((\<lambda>x. if 0 < x \<and> x < 1 then ?vd x else 0) has_integral ?int z) (cbox 0 1)"
  3667       by (rule has_integral_spike_interior [OF hi]) simp
  3668   qed 
  3669   then show ?thesis
  3670     by (simp add: Re_winding_number [OF \<gamma>] field_simps)
  3671 qed
  3672 
  3673 lemma winding_number_pos_lt_lemma:
  3674   assumes \<gamma>: "valid_path \<gamma>" "z \<notin> path_image \<gamma>"
  3675       and e: "0 < e"
  3676       and ge: "\<And>x. \<lbrakk>0 < x; x < 1\<rbrakk> \<Longrightarrow> e \<le> Im (vector_derivative \<gamma> (at x) / (\<gamma> x - z))"
  3677     shows "0 < Re(winding_number \<gamma> z)"
  3678 proof -
  3679   let ?vd = "\<lambda>x. 1 / (\<gamma> x - z) * vector_derivative \<gamma> (at x)"
  3680   let ?int = "\<lambda>z. contour_integral \<gamma> (\<lambda>w. 1 / (w - z))"
  3681   have hi: "(?vd has_integral ?int z) (cbox 0 1)"
  3682     unfolding box_real 
  3683     apply (subst has_contour_integral [symmetric])
  3684     using \<gamma> by (simp add: contour_integrable_inversediff has_contour_integral_integral)
  3685   have "e \<le> Im (contour_integral \<gamma> (\<lambda>w. 1 / (w - z)))"
  3686   proof (rule has_integral_component_le [of \<i> "\<lambda>x. \<i>*e" "\<i>*e" "{0..1}", simplified])
  3687     show "((\<lambda>x. if 0 < x \<and> x < 1 then ?vd x else \<i> * complex_of_real e) has_integral ?int z) {0..1}"
  3688       by (rule has_integral_spike_interior [OF hi, simplified box_real]) (use e in simp)
  3689     show "\<And>x. 0 \<le> x \<and> x \<le> 1 \<Longrightarrow>
  3690               e \<le> Im (if 0 < x \<and> x < 1 then ?vd x else \<i> * complex_of_real e)"
  3691       by (simp add: ge)
  3692   qed (use has_integral_const_real [of _ 0 1] in auto)
  3693   with e show ?thesis
  3694     by (simp add: Re_winding_number [OF \<gamma>] field_simps)
  3695 qed
  3696 
  3697 lemma winding_number_pos_lt:
  3698   assumes \<gamma>: "valid_path \<gamma>" "z \<notin> path_image \<gamma>"
  3699       and e: "0 < e"
  3700       and ge: "\<And>x. \<lbrakk>0 < x; x < 1\<rbrakk> \<Longrightarrow> e \<le> Im (vector_derivative \<gamma> (at x) * cnj(\<gamma> x - z))"
  3701     shows "0 < Re (winding_number \<gamma> z)"
  3702 proof -
  3703   have bm: "bounded ((\<lambda>w. w - z) ` (path_image \<gamma>))"
  3704     using bounded_translation [of _ "-z"] \<gamma> by (simp add: bounded_valid_path_image)
  3705   then obtain B where B: "B > 0" and Bno: "\<And>x. x \<in> (\<lambda>w. w - z) ` (path_image \<gamma>) \<Longrightarrow> norm x \<le> B"
  3706     using bounded_pos [THEN iffD1, OF bm] by blast
  3707   { fix x::real  assume x: "0 < x" "x < 1"
  3708     then have B2: "cmod (\<gamma> x - z)^2 \<le> B^2" using Bno [of "\<gamma> x - z"]
  3709       by (simp add: path_image_def power2_eq_square mult_mono')
  3710     with x have "\<gamma> x \<noteq> z" using \<gamma>
  3711       using path_image_def by fastforce
  3712     then have "e / B\<^sup>2 \<le> Im (vector_derivative \<gamma> (at x) * cnj (\<gamma> x - z)) / (cmod (\<gamma> x - z))\<^sup>2"
  3713       using B ge [OF x] B2 e
  3714       apply (rule_tac y="e / (cmod (\<gamma> x - z))\<^sup>2" in order_trans)
  3715       apply (auto simp: divide_left_mono divide_right_mono)
  3716       done
  3717     then have "e / B\<^sup>2 \<le> Im (vector_derivative \<gamma> (at x) / (\<gamma> x - z))"
  3718       by (simp add: complex_div_cnj [of _ "\<gamma> x - z" for x] del: complex_cnj_diff times_complex.sel)
  3719   } note * = this
  3720   show ?thesis
  3721     using e B by (simp add: * winding_number_pos_lt_lemma [OF \<gamma>, of "e/B^2"])
  3722 qed
  3723 
  3724 subsection\<open>The winding number is an integer\<close>
  3725 
  3726 text\<open>Proof from the book Complex Analysis by Lars V. Ahlfors, Chapter 4, section 2.1,
  3727      Also on page 134 of Serge Lang's book with the name title, etc.\<close>
  3728 
  3729 lemma exp_fg:
  3730   fixes z::complex
  3731   assumes g: "(g has_vector_derivative g') (at x within s)"
  3732       and f: "(f has_vector_derivative (g' / (g x - z))) (at x within s)"
  3733       and z: "g x \<noteq> z"
  3734     shows "((\<lambda>x. exp(-f x) * (g x - z)) has_vector_derivative 0) (at x within s)"
  3735 proof -
  3736   have *: "(exp \<circ> (\<lambda>x. (- f x)) has_vector_derivative - (g' / (g x - z)) * exp (- f x)) (at x within s)"
  3737     using assms unfolding has_vector_derivative_def scaleR_conv_of_real
  3738     by (auto intro!: derivative_eq_intros)
  3739   show ?thesis
  3740     apply (rule has_vector_derivative_eq_rhs)
  3741     using z
  3742     apply (auto intro!: derivative_eq_intros * [unfolded o_def] g)
  3743     done
  3744 qed
  3745 
  3746 lemma winding_number_exp_integral:
  3747   fixes z::complex
  3748   assumes \<gamma>: "\<gamma> piecewise_C1_differentiable_on {a..b}"
  3749       and ab: "a \<le> b"
  3750       and z: "z \<notin> \<gamma> ` {a..b}"
  3751     shows "(\<lambda>x. vector_derivative \<gamma> (at x) / (\<gamma> x - z)) integrable_on {a..b}"
  3752           (is "?thesis1")
  3753           "exp (- (integral {a..b} (\<lambda>x. vector_derivative \<gamma> (at x) / (\<gamma> x - z)))) * (\<gamma> b - z) = \<gamma> a - z"
  3754           (is "?thesis2")
  3755 proof -
  3756   let ?D\<gamma> = "\<lambda>x. vector_derivative \<gamma> (at x)"
  3757   have [simp]: "\<And>x. a \<le> x \<Longrightarrow> x \<le> b \<Longrightarrow> \<gamma> x \<noteq> z"
  3758     using z by force
  3759   have cong: "continuous_on {a..b} \<gamma>"
  3760     using \<gamma> by (simp add: piecewise_C1_differentiable_on_def)
  3761   obtain k where fink: "finite k" and g_C1_diff: "\<gamma> C1_differentiable_on ({a..b} - k)"
  3762     using \<gamma> by (force simp: piecewise_C1_differentiable_on_def)
  3763   have \<circ>: "open ({a<..<b} - k)"
  3764     using \<open>finite k\<close> by (simp add: finite_imp_closed open_Diff)
  3765   moreover have "{a<..<b} - k \<subseteq> {a..b} - k"
  3766     by force
  3767   ultimately have g_diff_at: "\<And>x. \<lbrakk>x \<notin> k; x \<in> {a<..<b}\<rbrakk> \<Longrightarrow> \<gamma> differentiable at x"
  3768     by (metis Diff_iff differentiable_on_subset C1_diff_imp_diff [OF g_C1_diff] differentiable_on_def at_within_open)
  3769   { fix w
  3770     assume "w \<noteq> z"
  3771     have "continuous_on (ball w (cmod (w - z))) (\<lambda>w. 1 / (w - z))"
  3772       by (auto simp: dist_norm intro!: continuous_intros)
  3773     moreover have "\<And>x. cmod (w - x) < cmod (w - z) \<Longrightarrow> \<exists>f'. ((\<lambda>w. 1 / (w - z)) has_field_derivative f') (at x)"
  3774       by (auto simp: intro!: derivative_eq_intros)
  3775     ultimately have "\<exists>h. \<forall>y. norm(y - w) < norm(w - z) \<longrightarrow> (h has_field_derivative 1/(y - z)) (at y)"
  3776       using holomorphic_convex_primitive [of "ball w (norm(w - z))" "{}" "\<lambda>w. 1/(w - z)"]
  3777       by (force simp: field_differentiable_def Ball_def dist_norm at_within_open_NO_MATCH norm_minus_commute)
  3778   }
  3779   then obtain h where h: "\<And>w y. w \<noteq> z \<Longrightarrow> norm(y - w) < norm(w - z) \<Longrightarrow> (h w has_field_derivative 1/(y - z)) (at y)"
  3780     by meson
  3781   have exy: "\<exists>y. ((\<lambda>x. inverse (\<gamma> x - z) * ?D\<gamma> x) has_integral y) {a..b}"
  3782     unfolding integrable_on_def [symmetric]
  3783   proof (rule contour_integral_local_primitive_any [OF piecewise_C1_imp_differentiable [OF \<gamma>]])
  3784     show "\<exists>d h. 0 < d \<and>
  3785                (\<forall>y. cmod (y - w) < d \<longrightarrow> (h has_field_derivative inverse (y - z))(at y within - {z}))" 
  3786           if "w \<in> - {z}" for w
  3787       apply (rule_tac x="norm(w - z)" in exI)
  3788       using that inverse_eq_divide has_field_derivative_at_within h
  3789       by (metis Compl_insert DiffD2 insertCI right_minus_eq zero_less_norm_iff)
  3790   qed simp
  3791   have vg_int: "(\<lambda>x. ?D\<gamma> x / (\<gamma> x - z)) integrable_on {a..b}"
  3792     unfolding box_real [symmetric] divide_inverse_commute
  3793     by (auto intro!: exy integrable_subinterval simp add: integrable_on_def ab)
  3794   with ab show ?thesis1
  3795     by (simp add: divide_inverse_commute integral_def integrable_on_def)
  3796   { fix t
  3797     assume t: "t \<in> {a..b}"
  3798     have cball: "continuous_on (ball (\<gamma> t) (dist (\<gamma> t) z)) (\<lambda>x. inverse (x - z))"
  3799         using z by (auto intro!: continuous_intros simp: dist_norm)
  3800     have icd: "\<And>x. cmod (\<gamma> t - x) < cmod (\<gamma> t - z) \<Longrightarrow> (\<lambda>w. inverse (w - z)) field_differentiable at x"
  3801       unfolding field_differentiable_def by (force simp: intro!: derivative_eq_intros)
  3802     obtain h where h: "\<And>x. cmod (\<gamma> t - x) < cmod (\<gamma> t - z) \<Longrightarrow>
  3803                        (h has_field_derivative inverse (x - z)) (at x within {y. cmod (\<gamma> t - y) < cmod (\<gamma> t - z)})"
  3804       using holomorphic_convex_primitive [where f = "\<lambda>w. inverse(w - z)", OF convex_ball finite.emptyI cball icd]
  3805       by simp (auto simp: ball_def dist_norm that)
  3806     { fix x D
  3807       assume x: "x \<notin> k" "a < x" "x < b"
  3808       then have "x \<in> interior ({a..b} - k)"
  3809         using open_subset_interior [OF \<circ>] by fastforce
  3810       then have con: "isCont ?D\<gamma> x"
  3811         using g_C1_diff x by (auto simp: C1_differentiable_on_eq intro: continuous_on_interior)
  3812       then have con_vd: "continuous (at x within {a..b}) (\<lambda>x. ?D\<gamma> x)"
  3813         by (rule continuous_at_imp_continuous_within)
  3814       have gdx: "\<gamma> differentiable at x"
  3815         using x by (simp add: g_diff_at)
  3816       have "\<And>d. \<lbrakk>x \<notin> k; a < x; x < b;
  3817           (\<gamma> has_vector_derivative d) (at x); a \<le> t; t \<le> b\<rbrakk>
  3818          \<Longrightarrow> ((\<lambda>x. integral {a..x}
  3819                      (\<lambda>x. ?D\<gamma> x /
  3820                            (\<gamma> x - z))) has_vector_derivative
  3821               d / (\<gamma> x - z))
  3822               (at x within {a..b})"
  3823         apply (rule has_vector_derivative_eq_rhs)
  3824          apply (rule integral_has_vector_derivative_continuous_at [where S = "{}", simplified])
  3825         apply (rule con_vd continuous_intros cong vg_int | simp add: continuous_at_imp_continuous_within has_vector_derivative_continuous vector_derivative_at)+
  3826         done
  3827       then have "((\<lambda>c. exp (- integral {a..c} (\<lambda>x. ?D\<gamma> x / (\<gamma> x - z))) * (\<gamma> c - z)) has_derivative (\<lambda>h. 0))
  3828           (at x within {a..b})"
  3829         using x gdx t
  3830         apply (clarsimp simp add: differentiable_iff_scaleR)
  3831         apply (rule exp_fg [unfolded has_vector_derivative_def, simplified], blast intro: has_derivative_at_withinI)
  3832         apply (simp_all add: has_vector_derivative_def [symmetric])
  3833         done
  3834       } note * = this
  3835     have "exp (- (integral {a..t} (\<lambda>x. ?D\<gamma> x / (\<gamma> x - z)))) * (\<gamma> t - z) =\<gamma> a - z"
  3836       apply (rule has_derivative_zero_unique_strong_interval [of "{a,b} \<union> k" a b])
  3837       using t
  3838       apply (auto intro!: * continuous_intros fink cong indefinite_integral_continuous_1 [OF vg_int]  simp add: ab)+
  3839       done
  3840    }
  3841   with ab show ?thesis2
  3842     by (simp add: divide_inverse_commute integral_def)
  3843 qed
  3844 
  3845 corollary winding_number_exp_2pi:
  3846     "\<lbrakk>path p; z \<notin> path_image p\<rbrakk>
  3847      \<Longrightarrow> pathfinish p - z = exp (2 * pi * \<i> * winding_number p z) * (pathstart p - z)"
  3848 using winding_number [of p z 1] unfolding valid_path_def path_image_def pathstart_def pathfinish_def winding_number_prop_def
  3849   by (force dest: winding_number_exp_integral(2) [of _ 0 1 z] simp: field_simps contour_integral_integral exp_minus)
  3850 
  3851 
  3852 subsection\<open>The version with complex integers and equality\<close>
  3853 
  3854 lemma integer_winding_number_eq:
  3855   assumes \<gamma>: "path \<gamma>" and z: "z \<notin> path_image \<gamma>"
  3856   shows "winding_number \<gamma> z \<in> \<int> \<longleftrightarrow> pathfinish \<gamma> = pathstart \<gamma>"
  3857 proof -
  3858   obtain p where p: "valid_path p" "z \<notin> path_image p"
  3859                     "pathstart p = pathstart \<gamma>" "pathfinish p = pathfinish \<gamma>"
  3860            and eq: "contour_integral p (\<lambda>w. 1 / (w - z)) = complex_of_real (2 * pi) * \<i> * winding_number \<gamma> z"
  3861     using winding_number [OF assms, of 1] unfolding winding_number_prop_def by auto
  3862   then have wneq: "winding_number \<gamma> z = winding_number p z"
  3863       using eq winding_number_valid_path by force
  3864   have iff: "(winding_number \<gamma> z \<in> \<int>) \<longleftrightarrow> (exp (contour_integral p (\<lambda>w. 1 / (w - z))) = 1)"
  3865     using eq by (simp add: exp_eq_1 complex_is_Int_iff)
  3866   have "exp (contour_integral p (\<lambda>w. 1 / (w - z))) = (\<gamma> 1 - z) / (\<gamma> 0 - z)"
  3867     using p winding_number_exp_integral(2) [of p 0 1 z]
  3868     apply (simp add: valid_path_def path_defs contour_integral_integral exp_minus divide_simps)
  3869     by (metis path_image_def pathstart_def pathstart_in_path_image)
  3870   then have "winding_number p z \<in> \<int> \<longleftrightarrow> pathfinish p = pathstart p"
  3871     using p wneq iff by (auto simp: path_defs)
  3872   then show ?thesis using p eq
  3873     by (auto simp: winding_number_valid_path)
  3874 qed
  3875 
  3876 theorem integer_winding_number:
  3877   "\<lbrakk>path \<gamma>; pathfinish \<gamma> = pathstart \<gamma>; z \<notin> path_image \<gamma>\<rbrakk> \<Longrightarrow> winding_number \<gamma> z \<in> \<int>"
  3878 by (metis integer_winding_number_eq)
  3879 
  3880 
  3881 text\<open>If the winding number's magnitude is at least one, then the path must contain points in every direction.*)
  3882    We can thus bound the winding number of a path that doesn't intersect a given ray. \<close>
  3883 
  3884 lemma winding_number_pos_meets:
  3885   fixes z::complex
  3886   assumes \<gamma>: "valid_path \<gamma>" and z: "z \<notin> path_image \<gamma>" and 1: "Re (winding_number \<gamma> z) \<ge> 1"
  3887       and w: "w \<noteq> z"
  3888   shows "\<exists>a::real. 0 < a \<and> z + a*(w - z) \<in> path_image \<gamma>"
  3889 proof -
  3890   have [simp]: "\<And>x. 0 \<le> x \<Longrightarrow> x \<le> 1 \<Longrightarrow> \<gamma> x \<noteq> z"
  3891     using z by (auto simp: path_image_def)
  3892   have [simp]: "z \<notin> \<gamma> ` {0..1}"
  3893     using path_image_def z by auto
  3894   have gpd: "\<gamma> piecewise_C1_differentiable_on {0..1}"
  3895     using \<gamma> valid_path_def by blast
  3896   define r where "r = (w - z) / (\<gamma> 0 - z)"
  3897   have [simp]: "r \<noteq> 0"
  3898     using w z by (auto simp: r_def)
  3899   have cont: "continuous_on {0..1}
  3900      (\<lambda>x. Im (integral {0..x} (\<lambda>x. vector_derivative \<gamma> (at x) / (\<gamma> x - z))))"
  3901     by (intro continuous_intros indefinite_integral_continuous_1 winding_number_exp_integral [OF gpd]; simp)
  3902   have "Arg r \<le> 2*pi"
  3903     by (simp add: Arg less_eq_real_def)
  3904   also have "\<dots> \<le> Im (integral {0..1} (\<lambda>x. vector_derivative \<gamma> (at x) / (\<gamma> x - z)))"
  3905     using 1
  3906     apply (simp add: winding_number_valid_path [OF \<gamma> z] contour_integral_integral)
  3907     apply (simp add: Complex.Re_divide field_simps power2_eq_square)
  3908     done
  3909   finally have "Arg r \<le> Im (integral {0..1} (\<lambda>x. vector_derivative \<gamma> (at x) / (\<gamma> x - z)))" .
  3910   then have "\<exists>t. t \<in> {0..1} \<and> Im(integral {0..t} (\<lambda>x. vector_derivative \<gamma> (at x)/(\<gamma> x - z))) = Arg r"
  3911     by (simp add: Arg_ge_0 cont IVT')
  3912   then obtain t where t:     "t \<in> {0..1}"
  3913                   and eqArg: "Im (integral {0..t} (\<lambda>x. vector_derivative \<gamma> (at x)/(\<gamma> x - z))) = Arg r"
  3914     by blast
  3915   define i where "i = integral {0..t} (\<lambda>x. vector_derivative \<gamma> (at x) / (\<gamma> x - z))"
  3916   have iArg: "Arg r = Im i"
  3917     using eqArg by (simp add: i_def)
  3918   have gpdt: "\<gamma> piecewise_C1_differentiable_on {0..t}"
  3919     by (metis atLeastAtMost_iff atLeastatMost_subset_iff order_refl piecewise_C1_differentiable_on_subset gpd t)
  3920   have "exp (- i) * (\<gamma> t - z) = \<gamma> 0 - z"
  3921     unfolding i_def
  3922     apply (rule winding_number_exp_integral [OF gpdt])
  3923     using t z unfolding path_image_def by force+
  3924   then have *: "\<gamma> t - z = exp i * (\<gamma> 0 - z)"
  3925     by (simp add: exp_minus field_simps)
  3926   then have "(w - z) = r * (\<gamma> 0 - z)"
  3927     by (simp add: r_def)
  3928   then have "z + complex_of_real (exp (Re i)) * (w - z) / complex_of_real (cmod r) = \<gamma> t"
  3929     apply simp
  3930     apply (subst Complex_Transcendental.Arg_eq [of r])
  3931     apply (simp add: iArg)
  3932     using * apply (simp add: exp_eq_polar field_simps)
  3933     done
  3934   with t show ?thesis
  3935     by (rule_tac x="exp(Re i) / norm r" in exI) (auto simp: path_image_def)
  3936 qed
  3937 
  3938 lemma winding_number_big_meets:
  3939   fixes z::complex
  3940   assumes \<gamma>: "valid_path \<gamma>" and z: "z \<notin> path_image \<gamma>" and "\<bar>Re (winding_number \<gamma> z)\<bar> \<ge> 1"
  3941       and w: "w \<noteq> z"
  3942   shows "\<exists>a::real. 0 < a \<and> z + a*(w - z) \<in> path_image \<gamma>"
  3943 proof -
  3944   { assume "Re (winding_number \<gamma> z) \<le> - 1"
  3945     then have "Re (winding_number (reversepath \<gamma>) z) \<ge> 1"
  3946       by (simp add: \<gamma> valid_path_imp_path winding_number_reversepath z)
  3947     moreover have "valid_path (reversepath \<gamma>)"
  3948       using \<gamma> valid_path_imp_reverse by auto
  3949     moreover have "z \<notin> path_image (reversepath \<gamma>)"
  3950       by (simp add: z)
  3951     ultimately have "\<exists>a::real. 0 < a \<and> z + a*(w - z) \<in> path_image (reversepath \<gamma>)"
  3952       using winding_number_pos_meets w by blast
  3953     then have ?thesis
  3954       by simp
  3955   }
  3956   then show ?thesis
  3957     using assms
  3958     by (simp add: abs_if winding_number_pos_meets split: if_split_asm)
  3959 qed
  3960 
  3961 lemma winding_number_less_1:
  3962   fixes z::complex
  3963   shows
  3964   "\<lbrakk>valid_path \<gamma>; z \<notin> path_image \<gamma>; w \<noteq> z;
  3965     \<And>a::real. 0 < a \<Longrightarrow> z + a*(w - z) \<notin> path_image \<gamma>\<rbrakk>
  3966    \<Longrightarrow> Re(winding_number \<gamma> z) < 1"
  3967    by (auto simp: not_less dest: winding_number_big_meets)
  3968 
  3969 text\<open>One way of proving that WN=1 for a loop.\<close>
  3970 lemma winding_number_eq_1:
  3971   fixes z::complex
  3972   assumes \<gamma>: "valid_path \<gamma>" and z: "z \<notin> path_image \<gamma>" and loop: "pathfinish \<gamma> = pathstart \<gamma>"
  3973       and 0: "0 < Re(winding_number \<gamma> z)" and 2: "Re(winding_number \<gamma> z) < 2"
  3974   shows "winding_number \<gamma> z = 1"
  3975 proof -
  3976   have "winding_number \<gamma> z \<in> Ints"
  3977     by (simp add: \<gamma> integer_winding_number loop valid_path_imp_path z)
  3978   then show ?thesis
  3979     using 0 2 by (auto simp: Ints_def)
  3980 qed
  3981 
  3982 
  3983 subsection\<open>Continuity of winding number and invariance on connected sets\<close>
  3984 
  3985 lemma continuous_at_winding_number:
  3986   fixes z::complex
  3987   assumes \<gamma>: "path \<gamma>" and z: "z \<notin> path_image \<gamma>"
  3988   shows "continuous (at z) (winding_number \<gamma>)"
  3989 proof -
  3990   obtain e where "e>0" and cbg: "cball z e \<subseteq> - path_image \<gamma>"
  3991     using open_contains_cball [of "- path_image \<gamma>"]  z
  3992     by (force simp: closed_def [symmetric] closed_path_image [OF \<gamma>])
  3993   then have ppag: "path_image \<gamma> \<subseteq> - cball z (e/2)"
  3994     by (force simp: cball_def dist_norm)
  3995   have oc: "open (- cball z (e / 2))"
  3996     by (simp add: closed_def [symmetric])
  3997   obtain d where "d>0" and pi_eq:
  3998     "\<And>h1 h2. \<lbrakk>valid_path h1; valid_path h2;
  3999               (\<forall>t\<in>{0..1}. cmod (h1 t - \<gamma> t) < d \<and> cmod (h2 t - \<gamma> t) < d);
  4000               pathstart h2 = pathstart h1; pathfinish h2 = pathfinish h1\<rbrakk>
  4001              \<Longrightarrow>
  4002                path_image h1 \<subseteq> - cball z (e / 2) \<and>
  4003                path_image h2 \<subseteq> - cball z (e / 2) \<and>
  4004                (\<forall>f. f holomorphic_on - cball z (e / 2) \<longrightarrow> contour_integral h2 f = contour_integral h1 f)"
  4005     using contour_integral_nearby_ends [OF oc \<gamma> ppag] by metis
  4006   obtain p where p: "valid_path p" "z \<notin> path_image p"
  4007                     "pathstart p = pathstart \<gamma> \<and> pathfinish p = pathfinish \<gamma>"
  4008               and pg: "\<And>t. t\<in>{0..1} \<Longrightarrow> cmod (\<gamma> t - p t) < min d e / 2"
  4009               and pi: "contour_integral p (\<lambda>x. 1 / (x - z)) = complex_of_real (2 * pi) * \<i> * winding_number \<gamma> z"
  4010     using winding_number [OF \<gamma> z, of "min d e / 2"] \<open>d>0\<close> \<open>e>0\<close> by (auto simp: winding_number_prop_def)
  4011   { fix w
  4012     assume d2: "cmod (w - z) < d/2" and e2: "cmod (w - z) < e/2"
  4013     then have wnotp: "w \<notin> path_image p"
  4014       using cbg \<open>d>0\<close> \<open>e>0\<close>
  4015       apply (simp add: path_image_def cball_def dist_norm, clarify)
  4016       apply (frule pg)
  4017       apply (drule_tac c="\<gamma> x" in subsetD)
  4018       apply (auto simp: less_eq_real_def norm_minus_commute norm_triangle_half_l)
  4019       done
  4020     have wnotg: "w \<notin> path_image \<gamma>"
  4021       using cbg e2 \<open>e>0\<close> by (force simp: dist_norm norm_minus_commute)
  4022     { fix k::real
  4023       assume k: "k>0"
  4024       then obtain q where q: "valid_path q" "w \<notin> path_image q"
  4025                              "pathstart q = pathstart \<gamma> \<and> pathfinish q = pathfinish \<gamma>"
  4026                     and qg: "\<And>t. t \<in> {0..1} \<Longrightarrow> cmod (\<gamma> t - q t) < min k (min d e) / 2"
  4027                     and qi: "contour_integral q (\<lambda>u. 1 / (u - w)) = complex_of_real (2 * pi) * \<i> * winding_number \<gamma> w"
  4028         using winding_number [OF \<gamma> wnotg, of "min k (min d e) / 2"] \<open>d>0\<close> \<open>e>0\<close> k
  4029         by (force simp: min_divide_distrib_right winding_number_prop_def)
  4030       have "contour_integral p (\<lambda>u. 1 / (u - w)) = contour_integral q (\<lambda>u. 1 / (u - w))"
  4031         apply (rule pi_eq [OF \<open>valid_path q\<close> \<open>valid_path p\<close>, THEN conjunct2, THEN conjunct2, rule_format])
  4032         apply (frule pg)
  4033         apply (frule qg)
  4034         using p q \<open>d>0\<close> e2
  4035         apply (auto simp: dist_norm norm_minus_commute intro!: holomorphic_intros)
  4036         done
  4037       then have "contour_integral p (\<lambda>x. 1 / (x - w)) = complex_of_real (2 * pi) * \<i> * winding_number \<gamma> w"
  4038         by (simp add: pi qi)
  4039     } note pip = this
  4040     have "path p"
  4041       using p by (simp add: valid_path_imp_path)
  4042     then have "winding_number p w = winding_number \<gamma> w"
  4043       apply (rule winding_number_unique [OF _ wnotp])
  4044       apply (rule_tac x=p in exI)
  4045       apply (simp add: p wnotp min_divide_distrib_right pip winding_number_prop_def)
  4046       done
  4047   } note wnwn = this
  4048   obtain pe where "pe>0" and cbp: "cball z (3 / 4 * pe) \<subseteq> - path_image p"
  4049     using p open_contains_cball [of "- path_image p"]
  4050     by (force simp: closed_def [symmetric] closed_path_image [OF valid_path_imp_path])
  4051   obtain L
  4052     where "L>0"
  4053       and L: "\<And>f B. \<lbrakk>f holomorphic_on - cball z (3 / 4 * pe);
  4054                       \<forall>z \<in> - cball z (3 / 4 * pe). cmod (f z) \<le> B\<rbrakk> \<Longrightarrow>
  4055                       cmod (contour_integral p f) \<le> L * B"
  4056     using contour_integral_bound_exists [of "- cball z (3/4*pe)" p] cbp \<open>valid_path p\<close> by force
  4057   { fix e::real and w::complex
  4058     assume e: "0 < e" and w: "cmod (w - z) < pe/4" "cmod (w - z) < e * pe\<^sup>2 / (8 * L)"
  4059     then have [simp]: "w \<notin> path_image p"
  4060       using cbp p(2) \<open>0 < pe\<close>
  4061       by (force simp: dist_norm norm_minus_commute path_image_def cball_def)
  4062     have [simp]: "contour_integral p (\<lambda>x. 1/(x - w)) - contour_integral p (\<lambda>x. 1/(x - z)) =
  4063                   contour_integral p (\<lambda>x. 1/(x - w) - 1/(x - z))"
  4064       by (simp add: p contour_integrable_inversediff contour_integral_diff)
  4065     { fix x
  4066       assume pe: "3/4 * pe < cmod (z - x)"
  4067       have "cmod (w - x) < pe/4 + cmod (z - x)"
  4068         by (meson add_less_cancel_right norm_diff_triangle_le order_refl order_trans_rules(21) w(1))
  4069       then have wx: "cmod (w - x) < 4/3 * cmod (z - x)" using pe by simp
  4070       have "cmod (z - x) \<le> cmod (z - w) + cmod (w - x)"
  4071         using norm_diff_triangle_le by blast
  4072       also have "\<dots> < pe/4 + cmod (w - x)"
  4073         using w by (simp add: norm_minus_commute)
  4074       finally have "pe/2 < cmod (w - x)"
  4075         using pe by auto
  4076       then have "(pe/2)^2 < cmod (w - x) ^ 2"
  4077         apply (rule power_strict_mono)
  4078         using \<open>pe>0\<close> by auto
  4079       then have pe2: "pe^2 < 4 * cmod (w - x) ^ 2"
  4080         by (simp add: power_divide)
  4081       have "8 * L * cmod (w - z) < e * pe\<^sup>2"
  4082         using w \<open>L>0\<close> by (simp add: field_simps)
  4083       also have "\<dots> < e * 4 * cmod (w - x) * cmod (w - x)"
  4084         using pe2 \<open>e>0\<close> by (simp add: power2_eq_square)
  4085       also have "\<dots> < e * 4 * cmod (w - x) * (4/3 * cmod (z - x))"
  4086         using wx
  4087         apply (rule mult_strict_left_mono)
  4088         using pe2 e not_less_iff_gr_or_eq by fastforce
  4089       finally have "L * cmod (w - z) < 2/3 * e * cmod (w - x) * cmod (z - x)"
  4090         by simp
  4091       also have "\<dots> \<le> e * cmod (w - x) * cmod (z - x)"
  4092          using e by simp
  4093       finally have Lwz: "L * cmod (w - z) < e * cmod (w - x) * cmod (z - x)" .
  4094       have "L * cmod (1 / (x - w) - 1 / (x - z)) \<le> e"
  4095         apply (cases "x=z \<or> x=w")
  4096         using pe \<open>pe>0\<close> w \<open>L>0\<close>
  4097         apply (force simp: norm_minus_commute)
  4098         using wx w(2) \<open>L>0\<close> pe pe2 Lwz
  4099         apply (auto simp: divide_simps mult_less_0_iff norm_minus_commute norm_divide norm_mult power2_eq_square)
  4100         done
  4101     } note L_cmod_le = this
  4102     have *: "cmod (contour_integral p (\<lambda>x. 1 / (x - w) - 1 / (x - z))) \<le> L * (e * pe\<^sup>2 / L / 4 * (inverse (pe / 2))\<^sup>2)"
  4103       apply (rule L)
  4104       using \<open>pe>0\<close> w
  4105       apply (force simp: dist_norm norm_minus_commute intro!: holomorphic_intros)
  4106       using \<open>pe>0\<close> w \<open>L>0\<close>
  4107       apply (auto simp: cball_def dist_norm field_simps L_cmod_le  simp del: less_divide_eq_numeral1 le_divide_eq_numeral1)
  4108       done
  4109     have "cmod (contour_integral p (\<lambda>x. 1 / (x - w)) - contour_integral p (\<lambda>x. 1 / (x - z))) < 2*e"
  4110       apply simp
  4111       apply (rule le_less_trans [OF *])
  4112       using \<open>L>0\<close> e
  4113       apply (force simp: field_simps)
  4114       done
  4115     then have "cmod (winding_number p w - winding_number p z) < e"
  4116       using pi_ge_two e
  4117       by (force simp: winding_number_valid_path p field_simps norm_divide norm_mult intro: less_le_trans)
  4118   } note cmod_wn_diff = this
  4119   then have "isCont (winding_number p) z"
  4120     apply (simp add: continuous_at_eps_delta, clarify)
  4121     apply (rule_tac x="min (pe/4) (e/2*pe^2/L/4)" in exI)
  4122     using \<open>pe>0\<close> \<open>L>0\<close>
  4123     apply (simp add: dist_norm cmod_wn_diff)
  4124     done
  4125   then show ?thesis
  4126     apply (rule continuous_transform_within [where d = "min d e / 2"])
  4127     apply (auto simp: \<open>d>0\<close> \<open>e>0\<close> dist_norm wnwn)
  4128     done
  4129 qed
  4130 
  4131 corollary continuous_on_winding_number:
  4132     "path \<gamma> \<Longrightarrow> continuous_on (- path_image \<gamma>) (\<lambda>w. winding_number \<gamma> w)"
  4133   by (simp add: continuous_at_imp_continuous_on continuous_at_winding_number)
  4134 
  4135 
  4136 subsection\<open>The winding number is constant on a connected region\<close>
  4137 
  4138 lemma winding_number_constant:
  4139   assumes \<gamma>: "path \<gamma>" and loop: "pathfinish \<gamma> = pathstart \<gamma>" and cs: "connected S" and sg: "S \<inter> path_image \<gamma> = {}"
  4140   shows "winding_number \<gamma> constant_on S"
  4141 proof -
  4142   have *: "1 \<le> cmod (winding_number \<gamma> y - winding_number \<gamma> z)"
  4143       if ne: "winding_number \<gamma> y \<noteq> winding_number \<gamma> z" and "y \<in> S" "z \<in> S" for y z
  4144   proof -
  4145     have "winding_number \<gamma> y \<in> \<int>"  "winding_number \<gamma> z \<in>  \<int>"
  4146       using that integer_winding_number [OF \<gamma> loop] sg \<open>y \<in> S\<close> by auto
  4147     with ne show ?thesis
  4148       by (auto simp: Ints_def reorient: of_int_diff)
  4149   qed
  4150   have cont: "continuous_on S (\<lambda>w. winding_number \<gamma> w)"
  4151     using continuous_on_winding_number [OF \<gamma>] sg
  4152     by (meson continuous_on_subset disjoint_eq_subset_Compl)
  4153   show ?thesis
  4154     using "*" zero_less_one
  4155     by (blast intro: continuous_discrete_range_constant [OF cs cont])
  4156 qed
  4157 
  4158 lemma winding_number_eq:
  4159      "\<lbrakk>path \<gamma>; pathfinish \<gamma> = pathstart \<gamma>; w \<in> S; z \<in> S; connected S; S \<inter> path_image \<gamma> = {}\<rbrakk>
  4160       \<Longrightarrow> winding_number \<gamma> w = winding_number \<gamma> z"
  4161   using winding_number_constant by (metis constant_on_def) 
  4162 
  4163 lemma open_winding_number_levelsets:
  4164   assumes \<gamma>: "path \<gamma>" and loop: "pathfinish \<gamma> = pathstart \<gamma>"
  4165     shows "open {z. z \<notin> path_image \<gamma> \<and> winding_number \<gamma> z = k}"
  4166 proof -
  4167   have opn: "open (- path_image \<gamma>)"
  4168     by (simp add: closed_path_image \<gamma> open_Compl)
  4169   { fix z assume z: "z \<notin> path_image \<gamma>" and k: "k = winding_number \<gamma> z"
  4170     obtain e where e: "e>0" "ball z e \<subseteq> - path_image \<gamma>"
  4171       using open_contains_ball [of "- path_image \<gamma>"] opn z
  4172       by blast
  4173     have "\<exists>e>0. \<forall>y. dist y z < e \<longrightarrow> y \<notin> path_image \<gamma> \<and> winding_number \<gamma> y = winding_number \<gamma> z"
  4174       apply (rule_tac x=e in exI)
  4175       using e apply (simp add: dist_norm ball_def norm_minus_commute)
  4176       apply (auto simp: dist_norm norm_minus_commute intro!: winding_number_eq [OF assms, where S = "ball z e"])
  4177       done
  4178   } then
  4179   show ?thesis
  4180     by (auto simp: open_dist)
  4181 qed
  4182 
  4183 subsection\<open>Winding number is zero "outside" a curve, in various senses\<close>
  4184 
  4185 proposition winding_number_zero_in_outside:
  4186   assumes \<gamma>: "path \<gamma>" and loop: "pathfinish \<gamma> = pathstart \<gamma>" and z: "z \<in> outside (path_image \<gamma>)"
  4187     shows "winding_number \<gamma> z = 0"
  4188 proof -
  4189   obtain B::real where "0 < B" and B: "path_image \<gamma> \<subseteq> ball 0 B"
  4190     using bounded_subset_ballD [OF bounded_path_image [OF \<gamma>]] by auto
  4191   obtain w::complex where w: "w \<notin> ball 0 (B + 1)"
  4192     by (metis abs_of_nonneg le_less less_irrefl mem_ball_0 norm_of_real)
  4193   have "- ball 0 (B + 1) \<subseteq> outside (path_image \<gamma>)"
  4194     apply (rule outside_subset_convex)
  4195     using B subset_ball by auto
  4196   then have wout: "w \<in> outside (path_image \<gamma>)"
  4197     using w by blast
  4198   moreover have "winding_number \<gamma> constant_on outside (path_image \<gamma>)"
  4199     using winding_number_constant [OF \<gamma> loop, of "outside(path_image \<gamma>)"] connected_outside
  4200     by (metis DIM_complex bounded_path_image dual_order.refl \<gamma> outside_no_overlap)
  4201   ultimately have "winding_number \<gamma> z = winding_number \<gamma> w"
  4202     by (metis (no_types, hide_lams) constant_on_def z)
  4203   also have "\<dots> = 0"
  4204   proof -
  4205     have wnot: "w \<notin> path_image \<gamma>"  using wout by (simp add: outside_def)
  4206     { fix e::real assume "0<e"
  4207       obtain p where p: "polynomial_function p" "pathstart p = pathstart \<gamma>" "pathfinish p = pathfinish \<gamma>"
  4208                  and pg1: "(\<And>t. \<lbrakk>0 \<le> t; t \<le> 1\<rbrakk> \<Longrightarrow> cmod (p t - \<gamma> t) < 1)"
  4209                  and pge: "(\<And>t. \<lbrakk>0 \<le> t; t \<le> 1\<rbrakk> \<Longrightarrow> cmod (p t - \<gamma> t) < e)"
  4210         using path_approx_polynomial_function [OF \<gamma>, of "min 1 e"] \<open>e>0\<close> by force
  4211       have pip: "path_image p \<subseteq> ball 0 (B + 1)"
  4212         using B
  4213         apply (clarsimp simp add: path_image_def dist_norm ball_def)
  4214         apply (frule (1) pg1)
  4215         apply (fastforce dest: norm_add_less)
  4216         done
  4217       then have "w \<notin> path_image p"  using w by blast
  4218       then have "\<exists>p. valid_path p \<and> w \<notin> path_image p \<and>
  4219                      pathstart p = pathstart \<gamma> \<and> pathfinish p = pathfinish \<gamma> \<and>
  4220                      (\<forall>t\<in>{0..1}. cmod (\<gamma> t - p t) < e) \<and> contour_integral p (\<lambda>wa. 1 / (wa - w)) = 0"
  4221         apply (rule_tac x=p in exI)
  4222         apply (simp add: p valid_path_polynomial_function)
  4223         apply (intro conjI)
  4224         using pge apply (simp add: norm_minus_commute)
  4225         apply (rule contour_integral_unique [OF Cauchy_theorem_convex_simple [OF _ convex_ball [of 0 "B+1"]]])
  4226         apply (rule holomorphic_intros | simp add: dist_norm)+
  4227         using mem_ball_0 w apply blast
  4228         using p apply (simp_all add: valid_path_polynomial_function loop pip)
  4229         done
  4230     }
  4231     then show ?thesis
  4232       by (auto intro: winding_number_unique [OF \<gamma>] simp add: winding_number_prop_def wnot)
  4233   qed
  4234   finally show ?thesis .
  4235 qed
  4236 
  4237 corollary winding_number_zero_const: "a \<noteq> z \<Longrightarrow> winding_number (\<lambda>t. a) z = 0"
  4238   by (rule winding_number_zero_in_outside)
  4239      (auto simp: pathfinish_def pathstart_def path_polynomial_function)
  4240 
  4241 corollary winding_number_zero_outside:
  4242     "\<lbrakk>path \<gamma>; convex s; pathfinish \<gamma> = pathstart \<gamma>; z \<notin> s; path_image \<gamma> \<subseteq> s\<rbrakk> \<Longrightarrow> winding_number \<gamma> z = 0"
  4243   by (meson convex_in_outside outside_mono subsetCE winding_number_zero_in_outside)
  4244 
  4245 lemma winding_number_zero_at_infinity:
  4246   assumes \<gamma>: "path \<gamma>" and loop: "pathfinish \<gamma> = pathstart \<gamma>"
  4247     shows "\<exists>B. \<forall>z. B \<le> norm z \<longrightarrow> winding_number \<gamma> z = 0"
  4248 proof -
  4249   obtain B::real where "0 < B" and B: "path_image \<gamma> \<subseteq> ball 0 B"
  4250     using bounded_subset_ballD [OF bounded_path_image [OF \<gamma>]] by auto
  4251   then show ?thesis
  4252     apply (rule_tac x="B+1" in exI, clarify)
  4253     apply (rule winding_number_zero_outside [OF \<gamma> convex_cball [of 0 B] loop])
  4254     apply (meson less_add_one mem_cball_0 not_le order_trans)
  4255     using ball_subset_cball by blast
  4256 qed
  4257 
  4258 lemma winding_number_zero_point:
  4259     "\<lbrakk>path \<gamma>; convex s; pathfinish \<gamma> = pathstart \<gamma>; open s; path_image \<gamma> \<subseteq> s\<rbrakk>
  4260      \<Longrightarrow> \<exists>z. z \<in> s \<and> winding_number \<gamma> z = 0"
  4261   using outside_compact_in_open [of "path_image \<gamma>" s] path_image_nonempty winding_number_zero_in_outside
  4262   by (fastforce simp add: compact_path_image)
  4263 
  4264 
  4265 text\<open>If a path winds round a set, it winds rounds its inside.\<close>
  4266 lemma winding_number_around_inside:
  4267   assumes \<gamma>: "path \<gamma>" and loop: "pathfinish \<gamma> = pathstart \<gamma>"
  4268       and cls: "closed s" and cos: "connected s" and s_disj: "s \<inter> path_image \<gamma> = {}"
  4269       and z: "z \<in> s" and wn_nz: "winding_number \<gamma> z \<noteq> 0" and w: "w \<in> s \<union> inside s"
  4270     shows "winding_number \<gamma> w = winding_number \<gamma> z"
  4271 proof -
  4272   have ssb: "s \<subseteq> inside(path_image \<gamma>)"
  4273   proof
  4274     fix x :: complex
  4275     assume "x \<in> s"
  4276     hence "x \<notin> path_image \<gamma>"
  4277       by (meson disjoint_iff_not_equal s_disj)
  4278     thus "x \<in> inside (path_image \<gamma>)"
  4279       using \<open>x \<in> s\<close> by (metis (no_types) ComplI UnE cos \<gamma> loop s_disj union_with_outside winding_number_eq winding_number_zero_in_outside wn_nz z)
  4280 qed
  4281   show ?thesis
  4282     apply (rule winding_number_eq [OF \<gamma> loop w])
  4283     using z apply blast
  4284     apply (simp add: cls connected_with_inside cos)
  4285     apply (simp add: Int_Un_distrib2 s_disj, safe)
  4286     by (meson ssb inside_inside_compact_connected [OF cls, of "path_image \<gamma>"] compact_path_image connected_path_image contra_subsetD disjoint_iff_not_equal \<gamma> inside_no_overlap)
  4287  qed
  4288 
  4289 
  4290 text\<open>Bounding a WN by 1/2 for a path and point in opposite halfspaces.\<close>
  4291 lemma winding_number_subpath_continuous:
  4292   assumes \<gamma>: "valid_path \<gamma>" and z: "z \<notin> path_image \<gamma>"
  4293     shows "continuous_on {0..1} (\<lambda>x. winding_number(subpath 0 x \<gamma>) z)"
  4294 proof -
  4295   have *: "integral {0..x} (\<lambda>t. vector_derivative \<gamma> (at t) / (\<gamma> t - z)) / (2 * of_real pi * \<i>) =
  4296          winding_number (subpath 0 x \<gamma>) z"
  4297          if x: "0 \<le> x" "x \<le> 1" for x
  4298   proof -
  4299     have "integral {0..x} (\<lambda>t. vector_derivative \<gamma> (at t) / (\<gamma> t - z)) / (2 * of_real pi * \<i>) =
  4300           1 / (2*pi*\<i>) * contour_integral (subpath 0 x \<gamma>) (\<lambda>w. 1/(w - z))"
  4301       using assms x
  4302       apply (simp add: contour_integral_subcontour_integral [OF contour_integrable_inversediff])
  4303       done
  4304     also have "\<dots> = winding_number (subpath 0 x \<gamma>) z"
  4305       apply (subst winding_number_valid_path)
  4306       using assms x
  4307       apply (simp_all add: path_image_subpath valid_path_subpath)
  4308       by (force simp: path_image_def)
  4309     finally show ?thesis .
  4310   qed
  4311   show ?thesis
  4312     apply (rule continuous_on_eq
  4313                  [where f = "\<lambda>x. 1 / (2*pi*\<i>) *
  4314                                  integral {0..x} (\<lambda>t. 1/(\<gamma> t - z) * vector_derivative \<gamma> (at t))"])
  4315     apply (rule continuous_intros)+
  4316     apply (rule indefinite_integral_continuous_1)
  4317     apply (rule contour_integrable_inversediff [OF assms, unfolded contour_integrable_on])
  4318       using assms
  4319     apply (simp add: *)
  4320     done
  4321 qed
  4322 
  4323 lemma winding_number_ivt_pos:
  4324     assumes \<gamma>: "valid_path \<gamma>" and z: "z \<notin> path_image \<gamma>" and "0 \<le> w" "w \<le> Re(winding_number \<gamma> z)"
  4325       shows "\<exists>t \<in> {0..1}. Re(winding_number(subpath 0 t \<gamma>) z) = w"
  4326   apply (rule ivt_increasing_component_on_1 [of 0 1, where ?k = "1::complex", simplified complex_inner_1_right], simp)
  4327   apply (rule winding_number_subpath_continuous [OF \<gamma> z])
  4328   using assms
  4329   apply (auto simp: path_image_def image_def)
  4330   done
  4331 
  4332 lemma winding_number_ivt_neg:
  4333     assumes \<gamma>: "valid_path \<gamma>" and z: "z \<notin> path_image \<gamma>" and "Re(winding_number \<gamma> z) \<le> w" "w \<le> 0"
  4334       shows "\<exists>t \<in> {0..1}. Re(winding_number(subpath 0 t \<gamma>) z) = w"
  4335   apply (rule ivt_decreasing_component_on_1 [of 0 1, where ?k = "1::complex", simplified complex_inner_1_right], simp)
  4336   apply (rule winding_number_subpath_continuous [OF \<gamma> z])
  4337   using assms
  4338   apply (auto simp: path_image_def image_def)
  4339   done
  4340 
  4341 lemma winding_number_ivt_abs:
  4342     assumes \<gamma>: "valid_path \<gamma>" and z: "z \<notin> path_image \<gamma>" and "0 \<le> w" "w \<le> \<bar>Re(winding_number \<gamma> z)\<bar>"
  4343       shows "\<exists>t \<in> {0..1}. \<bar>Re (winding_number (subpath 0 t \<gamma>) z)\<bar> = w"
  4344   using assms winding_number_ivt_pos [of \<gamma> z w] winding_number_ivt_neg [of \<gamma> z "-w"]
  4345   by force
  4346 
  4347 lemma winding_number_lt_half_lemma:
  4348   assumes \<gamma>: "valid_path \<gamma>" and z: "z \<notin> path_image \<gamma>" and az: "a \<bullet> z \<le> b" and pag: "path_image \<gamma> \<subseteq> {w. a \<bullet> w > b}"
  4349     shows "Re(winding_number \<gamma> z) < 1/2"
  4350 proof -
  4351   { assume "Re(winding_number \<gamma> z) \<ge> 1/2"
  4352     then obtain t::real where t: "0 \<le> t" "t \<le> 1" and sub12: "Re (winding_number (subpath 0 t \<gamma>) z) = 1/2"
  4353       using winding_number_ivt_pos [OF \<gamma> z, of "1/2"] by auto
  4354     have gt: "\<gamma> t - z = - (of_real (exp (- (2 * pi * Im (winding_number (subpath 0 t \<gamma>) z)))) * (\<gamma> 0 - z))"
  4355       using winding_number_exp_2pi [of "subpath 0 t \<gamma>" z]
  4356       apply (simp add: t \<gamma> valid_path_imp_path)
  4357       using closed_segment_eq_real_ivl path_image_def t z by (fastforce simp: path_image_subpath Euler sub12)
  4358     have "b < a \<bullet> \<gamma> 0"
  4359     proof -
  4360       have "\<gamma> 0 \<in> {c. b < a \<bullet> c}"
  4361         by (metis (no_types) pag atLeastAtMost_iff image_subset_iff order_refl path_image_def zero_le_one)
  4362       thus ?thesis
  4363         by blast
  4364     qed
  4365     moreover have "b < a \<bullet> \<gamma> t"
  4366     proof -
  4367       have "\<gamma> t \<in> {c. b < a \<bullet> c}"
  4368         by (metis (no_types) pag atLeastAtMost_iff image_subset_iff path_image_def t)
  4369       thus ?thesis
  4370         by blast
  4371     qed
  4372     ultimately have "0 < a \<bullet> (\<gamma> 0 - z)" "0 < a \<bullet> (\<gamma> t - z)" using az
  4373       by (simp add: inner_diff_right)+
  4374     then have False
  4375       by (simp add: gt inner_mult_right mult_less_0_iff)
  4376   }
  4377   then show ?thesis by force
  4378 qed
  4379 
  4380 lemma winding_number_lt_half:
  4381   assumes "valid_path \<gamma>" "a \<bullet> z \<le> b" "path_image \<gamma> \<subseteq> {w. a \<bullet> w > b}"
  4382     shows "\<bar>Re (winding_number \<gamma> z)\<bar> < 1/2"
  4383 proof -
  4384   have "z \<notin> path_image \<gamma>" using assms by auto
  4385   with assms show ?thesis
  4386     apply (simp add: winding_number_lt_half_lemma abs_if del: less_divide_eq_numeral1)
  4387     apply (metis complex_inner_1_right winding_number_lt_half_lemma [OF valid_path_imp_reverse, of \<gamma> z a b]
  4388                  winding_number_reversepath valid_path_imp_path inner_minus_left path_image_reversepath)
  4389     done
  4390 qed
  4391 
  4392 lemma winding_number_le_half:
  4393   assumes \<gamma>: "valid_path \<gamma>" and z: "z \<notin> path_image \<gamma>"
  4394       and anz: "a \<noteq> 0" and azb: "a \<bullet> z \<le> b" and pag: "path_image \<gamma> \<subseteq> {w. a \<bullet> w \<ge> b}"
  4395     shows "\<bar>Re (winding_number \<gamma> z)\<bar> \<le> 1/2"
  4396 proof -
  4397   { assume wnz_12: "\<bar>Re (winding_number \<gamma> z)\<bar> > 1/2"
  4398     have "isCont (winding_number \<gamma>) z"
  4399       by (metis continuous_at_winding_number valid_path_imp_path \<gamma> z)
  4400     then obtain d where "d>0" and d: "\<And>x'. dist x' z < d \<Longrightarrow> dist (winding_number \<gamma> x') (winding_number \<gamma> z) < \<bar>Re(winding_number \<gamma> z)\<bar> - 1/2"
  4401       using continuous_at_eps_delta wnz_12 diff_gt_0_iff_gt by blast
  4402     define z' where "z' = z - (d / (2 * cmod a)) *\<^sub>R a"
  4403     have *: "a \<bullet> z' \<le> b - d / 3 * cmod a"
  4404       unfolding z'_def inner_mult_right' divide_inverse
  4405       apply (simp add: divide_simps algebra_simps dot_square_norm power2_eq_square anz)
  4406       apply (metis \<open>0 < d\<close> add_increasing azb less_eq_real_def mult_nonneg_nonneg mult_right_mono norm_ge_zero norm_numeral)
  4407       done
  4408     have "cmod (winding_number \<gamma> z' - winding_number \<gamma> z) < \<bar>Re (winding_number \<gamma> z)\<bar> - 1/2"
  4409       using d [of z'] anz \<open>d>0\<close> by (simp add: dist_norm z'_def)
  4410     then have "1/2 < \<bar>Re (winding_number \<gamma> z)\<bar> - cmod (winding_number \<gamma> z' - winding_number \<gamma> z)"
  4411       by simp
  4412     then have "1/2 < \<bar>Re (winding_number \<gamma> z)\<bar> - \<bar>Re (winding_number \<gamma> z') - Re (winding_number \<gamma> z)\<bar>"
  4413       using abs_Re_le_cmod [of "winding_number \<gamma> z' - winding_number \<gamma> z"] by simp
  4414     then have wnz_12': "\<bar>Re (winding_number \<gamma> z')\<bar> > 1/2"
  4415       by linarith
  4416     moreover have "\<bar>Re (winding_number \<gamma> z')\<bar> < 1/2"
  4417       apply (rule winding_number_lt_half [OF \<gamma> *])
  4418       using azb \<open>d>0\<close> pag
  4419       apply (auto simp: add_strict_increasing anz divide_simps algebra_simps dest!: subsetD)
  4420       done
  4421     ultimately have False
  4422       by simp
  4423   }
  4424   then show ?thesis by force
  4425 qed
  4426 
  4427 lemma winding_number_lt_half_linepath: "z \<notin> closed_segment a b \<Longrightarrow> \<bar>Re (winding_number (linepath a b) z)\<bar> < 1/2"
  4428   using separating_hyperplane_closed_point [of "closed_segment a b" z]
  4429   apply auto
  4430   apply (simp add: closed_segment_def)
  4431   apply (drule less_imp_le)
  4432   apply (frule winding_number_lt_half [OF valid_path_linepath [of a b]])
  4433   apply (auto simp: segment)
  4434   done
  4435 
  4436 
  4437 text\<open> Positivity of WN for a linepath.\<close>
  4438 lemma winding_number_linepath_pos_lt:
  4439     assumes "0 < Im ((b - a) * cnj (b - z))"
  4440       shows "0 < Re(winding_number(linepath a b) z)"
  4441 proof -
  4442   have z: "z \<notin> path_image (linepath a b)"
  4443     using assms
  4444     by (simp add: closed_segment_def) (force simp: algebra_simps)
  4445   show ?thesis
  4446     apply (rule winding_number_pos_lt [OF valid_path_linepath z assms])
  4447     apply (simp add: linepath_def algebra_simps)
  4448     done
  4449 qed
  4450 
  4451 
  4452 subsection\<open>Cauchy's integral formula, again for a convex enclosing set\<close>
  4453 
  4454 lemma Cauchy_integral_formula_weak:
  4455     assumes s: "convex s" and "finite k" and conf: "continuous_on s f"
  4456         and fcd: "(\<And>x. x \<in> interior s - k \<Longrightarrow> f field_differentiable at x)"
  4457         and z: "z \<in> interior s - k" and vpg: "valid_path \<gamma>"
  4458         and pasz: "path_image \<gamma> \<subseteq> s - {z}" and loop: "pathfinish \<gamma> = pathstart \<gamma>"
  4459       shows "((\<lambda>w. f w / (w - z)) has_contour_integral (2*pi * \<i> * winding_number \<gamma> z * f z)) \<gamma>"
  4460 proof -
  4461   obtain f' where f': "(f has_field_derivative f') (at z)"
  4462     using fcd [OF z] by (auto simp: field_differentiable_def)
  4463   have pas: "path_image \<gamma> \<subseteq> s" and znotin: "z \<notin> path_image \<gamma>" using pasz by blast+
  4464   have c: "continuous (at x within s) (\<lambda>w. if w = z then f' else (f w - f z) / (w - z))" if "x \<in> s" for x
  4465   proof (cases "x = z")
  4466     case True then show ?thesis
  4467       apply (simp add: continuous_within)
  4468       apply (rule Lim_transform_away_within [of _ "z+1" _ "\<lambda>w::complex. (f w - f z)/(w - z)"])
  4469       using has_field_derivative_at_within has_field_derivative_iff f'
  4470       apply (fastforce simp add:)+
  4471       done
  4472   next
  4473     case False
  4474     then have dxz: "dist x z > 0" by auto
  4475     have cf: "continuous (at x within s) f"
  4476       using conf continuous_on_eq_continuous_within that by blast
  4477     have "continuous (at x within s) (\<lambda>w. (f w - f z) / (w - z))"
  4478       by (rule cf continuous_intros | simp add: False)+
  4479     then show ?thesis
  4480       apply (rule continuous_transform_within [OF _ dxz that, of "\<lambda>w::complex. (f w - f z)/(w - z)"])
  4481       apply (force simp: dist_commute)
  4482       done
  4483   qed
  4484   have fink': "finite (insert z k)" using \<open>finite k\<close> by blast
  4485   have *: "((\<lambda>w. if w = z then f' else (f w - f z) / (w - z)) has_contour_integral 0) \<gamma>"
  4486     apply (rule Cauchy_theorem_convex [OF _ s fink' _ vpg pas loop])
  4487     using c apply (force simp: continuous_on_eq_continuous_within)
  4488     apply (rename_tac w)
  4489     apply (rule_tac d="dist w z" and f = "\<lambda>w. (f w - f z)/(w - z)" in field_differentiable_transform_within)
  4490     apply (simp_all add: dist_pos_lt dist_commute)
  4491     apply (metis less_irrefl)
  4492     apply (rule derivative_intros fcd | simp)+
  4493     done
  4494   show ?thesis
  4495     apply (rule has_contour_integral_eq)
  4496     using znotin has_contour_integral_add [OF has_contour_integral_lmul [OF has_contour_integral_winding_number [OF vpg znotin], of "f z"] *]
  4497     apply (auto simp: mult_ac divide_simps)
  4498     done
  4499 qed
  4500 
  4501 theorem Cauchy_integral_formula_convex_simple:
  4502     "\<lbrakk>convex s; f holomorphic_on s; z \<in> interior s; valid_path \<gamma>; path_image \<gamma> \<subseteq> s - {z};
  4503       pathfinish \<gamma> = pathstart \<gamma>\<rbrakk>
  4504      \<Longrightarrow> ((\<lambda>w. f w / (w - z)) has_contour_integral (2*pi * \<i> * winding_number \<gamma> z * f z)) \<gamma>"
  4505   apply (rule Cauchy_integral_formula_weak [where k = "{}"])
  4506   using holomorphic_on_imp_continuous_on
  4507   by auto (metis at_within_interior holomorphic_on_def interiorE subsetCE)
  4508 
  4509 
  4510 subsection\<open>Homotopy forms of Cauchy's theorem\<close>
  4511 
  4512 proposition Cauchy_theorem_homotopic:
  4513     assumes hom: "if atends then homotopic_paths s g h else homotopic_loops s g h"
  4514         and "open s" and f: "f holomorphic_on s"
  4515         and vpg: "valid_path g" and vph: "valid_path h"
  4516     shows "contour_integral g f = contour_integral h f"
  4517 proof -
  4518   have pathsf: "linked_paths atends g h"
  4519     using hom  by (auto simp: linked_paths_def homotopic_paths_imp_pathstart homotopic_paths_imp_pathfinish homotopic_loops_imp_loop)
  4520   obtain k :: "real \<times> real \<Rightarrow> complex"
  4521     where contk: "continuous_on ({0..1} \<times> {0..1}) k"
  4522       and ks: "k ` ({0..1} \<times> {0..1}) \<subseteq> s"
  4523       and k [simp]: "\<forall>x. k (0, x) = g x" "\<forall>x. k (1, x) = h x"
  4524       and ksf: "\<forall>t\<in>{0..1}. linked_paths atends g (\<lambda>x. k (t, x))"
  4525       using hom pathsf by (auto simp: linked_paths_def homotopic_paths_def homotopic_loops_def homotopic_with_def split: if_split_asm)
  4526   have ucontk: "uniformly_continuous_on ({0..1} \<times> {0..1}) k"
  4527     by (blast intro: compact_Times compact_uniformly_continuous [OF contk])
  4528   { fix t::real assume t: "t \<in> {0..1}"
  4529     have pak: "path (k \<circ> (\<lambda>u. (t, u)))"
  4530       unfolding path_def
  4531       apply (rule continuous_intros continuous_on_subset [OF contk])+
  4532       using t by force
  4533     have pik: "path_image (k \<circ> Pair t) \<subseteq> s"
  4534       using ks t by (auto simp: path_image_def)
  4535     obtain e where "e>0" and e:
  4536          "\<And>g h. \<lbrakk>valid_path g; valid_path h;
  4537                   \<forall>u\<in>{0..1}. cmod (g u - (k \<circ> Pair t) u) < e \<and> cmod (h u - (k \<circ> Pair t) u) < e;
  4538                   linked_paths atends g h\<rbrakk>
  4539                  \<Longrightarrow> contour_integral h f = contour_integral g f"
  4540       using contour_integral_nearby [OF \<open>open s\<close> pak pik, of atends] f by metis
  4541     obtain d where "d>0" and d:
  4542         "\<And>x x'. \<lbrakk>x \<in> {0..1} \<times> {0..1}; x' \<in> {0..1} \<times> {0..1}; norm (x'-x) < d\<rbrakk> \<Longrightarrow> norm (k x' - k x) < e/4"
  4543       by (rule uniformly_continuous_onE [OF ucontk, of "e/4"]) (auto simp: dist_norm \<open>e>0\<close>)
  4544     { fix t1 t2
  4545       assume t1: "0 \<le> t1" "t1 \<le> 1" and t2: "0 \<le> t2" "t2 \<le> 1" and ltd: "\<bar>t1 - t\<bar> < d" "\<bar>t2 - t\<bar> < d"
  4546       have no2: "\<And>g1 k1 kt. \<lbrakk>norm(g1 - k1) < e/4; norm(k1 - kt) < e/4\<rbrakk> \<Longrightarrow> norm(g1 - kt) < e"
  4547         using \<open>e > 0\<close>
  4548         apply (rule_tac y = k1 in norm_triangle_half_l)
  4549         apply (auto simp: norm_minus_commute intro: order_less_trans)
  4550         done
  4551       have "\<exists>d>0. \<forall>g1 g2. valid_path g1 \<and> valid_path g2 \<and>
  4552                           (\<forall>u\<in>{0..1}. cmod (g1 u - k (t1, u)) < d \<and> cmod (g2 u - k (t2, u)) < d) \<and>
  4553                           linked_paths atends g1 g2 \<longrightarrow>
  4554                           contour_integral g2 f = contour_integral g1 f"
  4555         apply (rule_tac x="e/4" in exI)
  4556         using t t1 t2 ltd \<open>e > 0\<close>
  4557         apply (auto intro!: e simp: d no2 simp del: less_divide_eq_numeral1)
  4558         done
  4559     }
  4560     then have "\<exists>e. 0 < e \<and>
  4561               (\<forall>t1 t2. t1 \<in> {0..1} \<and> t2 \<in> {0..1} \<and> \<bar>t1 - t\<bar> < e \<and> \<bar>t2 - t\<bar> < e
  4562                 \<longrightarrow> (\<exists>d. 0 < d \<and>
  4563                      (\<forall>g1 g2. valid_path g1 \<and> valid_path g2 \<and>
  4564                        (\<forall>u \<in> {0..1}.
  4565                           norm(g1 u - k((t1,u))) < d \<and> norm(g2 u - k((t2,u))) < d) \<and>
  4566                           linked_paths atends g1 g2
  4567                           \<longrightarrow> contour_integral g2 f = contour_integral g1 f)))"
  4568       by (rule_tac x=d in exI) (simp add: \<open>d > 0\<close>)
  4569   }
  4570   then obtain ee where ee:
  4571        "\<And>t. t \<in> {0..1} \<Longrightarrow> ee t > 0 \<and>
  4572           (\<forall>t1 t2. t1 \<in> {0..1} \<longrightarrow> t2 \<in> {0..1} \<longrightarrow> \<bar>t1 - t\<bar> < ee t \<longrightarrow> \<bar>t2 - t\<bar> < ee t
  4573             \<longrightarrow> (\<exists>d. 0 < d \<and>
  4574                  (\<forall>g1 g2. valid_path g1 \<and> valid_path g2 \<and>
  4575                    (\<forall>u \<in> {0..1}.
  4576                       norm(g1 u - k((t1,u))) < d \<and> norm(g2 u - k((t2,u))) < d) \<and>
  4577                       linked_paths atends g1 g2
  4578                       \<longrightarrow> contour_integral g2 f = contour_integral g1 f)))"
  4579     by metis
  4580   note ee_rule = ee [THEN conjunct2, rule_format]
  4581   define C where "C = (\<lambda>t. ball t (ee t / 3)) ` {0..1}"
  4582   obtain C' where C': "C' \<subseteq> C" "finite C'" and C'01: "{0..1} \<subseteq> \<Union>C'"
  4583   proof (rule compactE [OF compact_interval])
  4584     show "{0..1} \<subseteq> \<Union>C"
  4585       using ee [THEN conjunct1] by (auto simp: C_def dist_norm)
  4586   qed (use C_def in auto)
  4587   define kk where "kk = {t \<in> {0..1}. ball t (ee t / 3) \<in> C'}"
  4588   have kk01: "kk \<subseteq> {0..1}" by (auto simp: kk_def)
  4589   define e where "e = Min (ee ` kk)"
  4590   have C'_eq: "C' = (\<lambda>t. ball t (ee t / 3)) ` kk"
  4591     using C' by (auto simp: kk_def C_def)
  4592   have ee_pos[simp]: "\<And>t. t \<in> {0..1} \<Longrightarrow> ee t > 0"
  4593     by (simp add: kk_def ee)
  4594   moreover have "finite kk"
  4595     using \<open>finite C'\<close> kk01 by (force simp: C'_eq inj_on_def ball_eq_ball_iff dest: ee_pos finite_imageD)
  4596   moreover have "kk \<noteq> {}" using \<open>{0..1} \<subseteq> \<Union>C'\<close> C'_eq by force
  4597   ultimately have "e > 0"
  4598     using finite_less_Inf_iff [of "ee ` kk" 0] kk01 by (force simp: e_def)
  4599   then obtain N::nat where "N > 0" and N: "1/N < e/3"
  4600     by (meson divide_pos_pos nat_approx_posE zero_less_Suc zero_less_numeral)
  4601   have e_le_ee: "\<And>i. i \<in> kk \<Longrightarrow> e \<le> ee i"
  4602     using \<open>finite kk\<close> by (simp add: e_def Min_le_iff [of "ee ` kk"])
  4603   have plus: "\<exists>t \<in> kk. x \<in> ball t (ee t / 3)" if "x \<in> {0..1}" for x
  4604     using C' subsetD [OF C'01 that]  unfolding C'_eq by blast
  4605   have [OF order_refl]:
  4606       "\<exists>d. 0 < d \<and> (\<forall>j. valid_path j \<and> (\<forall>u \<in> {0..1}. norm(j u - k (n/N, u)) < d) \<and> linked_paths atends g j
  4607                         \<longrightarrow> contour_integral j f = contour_integral g f)"
  4608        if "n \<le> N" for n
  4609   using that
  4610   proof (induct n)
  4611     case 0 show ?case using ee_rule [of 0 0 0]
  4612       apply clarsimp
  4613       apply (rule_tac x=d in exI, safe)
  4614       by (metis diff_self vpg norm_zero)
  4615   next
  4616     case (Suc n)
  4617     then have N01: "n/N \<in> {0..1}" "(Suc n)/N \<in> {0..1}"  by auto
  4618     then obtain t where t: "t \<in> kk" "n/N \<in> ball t (ee t / 3)"
  4619       using plus [of "n/N"] by blast
  4620     then have nN_less: "\<bar>n/N - t\<bar> < ee t"
  4621       by (simp add: dist_norm del: less_divide_eq_numeral1)
  4622     have n'N_less: "\<bar>real (Suc n) / real N - t\<bar> < ee t"
  4623       using t N \<open>N > 0\<close> e_le_ee [of t]
  4624       by (simp add: dist_norm add_divide_distrib abs_diff_less_iff del: less_divide_eq_numeral1) (simp add: field_simps)
  4625     have t01: "t \<in> {0..1}" using \<open>kk \<subseteq> {0..1}\<close> \<open>t \<in> kk\<close> by blast
  4626     obtain d1 where "d1 > 0" and d1:
  4627         "\<And>g1 g2. \<lbrakk>valid_path g1; valid_path g2;
  4628                    \<forall>u\<in>{0..1}. cmod (g1 u - k (n/N, u)) < d1 \<and> cmod (g2 u - k ((Suc n) / N, u)) < d1;
  4629                    linked_paths atends g1 g2\<rbrakk>
  4630                    \<Longrightarrow> contour_integral g2 f = contour_integral g1 f"
  4631       using ee [THEN conjunct2, rule_format, OF t01 N01 nN_less n'N_less] by fastforce
  4632     have "n \<le> N" using Suc.prems by auto
  4633     with Suc.hyps
  4634     obtain d2 where "d2 > 0"
  4635       and d2: "\<And>j. \<lbrakk>valid_path j; \<forall>u\<in>{0..1}. cmod (j u - k (n/N, u)) < d2; linked_paths atends g j\<rbrakk>
  4636                      \<Longrightarrow> contour_integral j f = contour_integral g f"
  4637         by auto
  4638     have "continuous_on {0..1} (k \<circ> (\<lambda>u. (n/N, u)))"
  4639       apply (rule continuous_intros continuous_on_subset [OF contk])+
  4640       using N01 by auto
  4641     then have pkn: "path (\<lambda>u. k (n/N, u))"
  4642       by (simp add: path_def)
  4643     have min12: "min d1 d2 > 0" by (simp add: \<open>0 < d1\<close> \<open>0 < d2\<close>)
  4644     obtain p where "polynomial_function p"
  4645         and psf: "pathstart p = pathstart (\<lambda>u. k (n/N, u))"
  4646                  "pathfinish p = pathfinish (\<lambda>u. k (n/N, u))"
  4647         and pk_le:  "\<And>t. t\<in>{0..1} \<Longrightarrow> cmod (p t - k (n/N, t)) < min d1 d2"
  4648       using path_approx_polynomial_function [OF pkn min12] by blast
  4649     then have vpp: "valid_path p" using valid_path_polynomial_function by blast
  4650     have lpa: "linked_paths atends g p"
  4651       by (metis (mono_tags, lifting) N01(1) ksf linked_paths_def pathfinish_def pathstart_def psf)
  4652     show ?case
  4653     proof (intro exI; safe)
  4654       fix j
  4655       assume "valid_path j" "linked_paths atends g j"
  4656         and "\<forall>u\<in>{0..1}. cmod (j u - k (real (Suc n) / real N, u)) < min d1 d2"
  4657       then have "contour_integral j f = contour_integral p f"
  4658         using pk_le N01(1) ksf by (force intro!: vpp d1 simp add: linked_paths_def psf)
  4659       also have "... = contour_integral g f"
  4660         using pk_le by (force intro!: vpp d2 lpa)
  4661       finally show "contour_integral j f = contour_integral g f" .
  4662     qed (simp add: \<open>0 < d1\<close> \<open>0 < d2\<close>)
  4663   qed
  4664   then obtain d where "0 < d"
  4665                        "\<And>j. valid_path j \<and> (\<forall>u \<in> {0..1}. norm(j u - k (1,u)) < d) \<and> linked_paths atends g j
  4666                             \<Longrightarrow> contour_integral j f = contour_integral g f"
  4667     using \<open>N>0\<close> by auto
  4668   then have "linked_paths atends g h \<Longrightarrow> contour_integral h f = contour_integral g f"
  4669     using \<open>N>0\<close> vph by fastforce
  4670   then show ?thesis
  4671     by (simp add: pathsf)
  4672 qed
  4673 
  4674 proposition Cauchy_theorem_homotopic_paths:
  4675     assumes hom: "homotopic_paths s g h"
  4676         and "open s" and f: "f holomorphic_on s"
  4677         and vpg: "valid_path g" and vph: "valid_path h"
  4678     shows "contour_integral g f = contour_integral h f"
  4679   using Cauchy_theorem_homotopic [of True s g h] assms by simp
  4680 
  4681 proposition Cauchy_theorem_homotopic_loops:
  4682     assumes hom: "homotopic_loops s g h"
  4683         and "open s" and f: "f holomorphic_on s"
  4684         and vpg: "valid_path g" and vph: "valid_path h"
  4685     shows "contour_integral g f = contour_integral h f"
  4686   using Cauchy_theorem_homotopic [of False s g h] assms by simp
  4687 
  4688 lemma has_contour_integral_newpath:
  4689     "\<lbrakk>(f has_contour_integral y) h; f contour_integrable_on g; contour_integral g f = contour_integral h f\<rbrakk>
  4690      \<Longrightarrow> (f has_contour_integral y) g"
  4691   using has_contour_integral_integral contour_integral_unique by auto
  4692 
  4693 lemma Cauchy_theorem_null_homotopic:
  4694      "\<lbrakk>f holomorphic_on s; open s; valid_path g; homotopic_loops s g (linepath a a)\<rbrakk> \<Longrightarrow> (f has_contour_integral 0) g"
  4695   apply (rule has_contour_integral_newpath [where h = "linepath a a"], simp)
  4696   using contour_integrable_holomorphic_simple
  4697     apply (blast dest: holomorphic_on_imp_continuous_on homotopic_loops_imp_subset)
  4698   by (simp add: Cauchy_theorem_homotopic_loops)
  4699 
  4700 
  4701 
  4702 subsection\<open>More winding number properties\<close>
  4703 
  4704 text\<open>including the fact that it's +-1 inside a simple closed curve.\<close>
  4705 
  4706 lemma winding_number_homotopic_paths:
  4707     assumes "homotopic_paths (-{z}) g h"
  4708       shows "winding_number g z = winding_number h z"
  4709 proof -
  4710   have "path g" "path h" using homotopic_paths_imp_path [OF assms] by auto
  4711   moreover have pag: "z \<notin> path_image g" and pah: "z \<notin> path_image h"
  4712     using homotopic_paths_imp_subset [OF assms] by auto
  4713   ultimately obtain d e where "d > 0" "e > 0"
  4714       and d: "\<And>p. \<lbrakk>path p; pathstart p = pathstart g; pathfinish p = pathfinish g; \<forall>t\<in>{0..1}. norm (p t - g t) < d\<rbrakk>
  4715             \<Longrightarrow> homotopic_paths (-{z}) g p"
  4716       and e: "\<And>q. \<lbrakk>path q; pathstart q = pathstart h; pathfinish q = pathfinish h; \<forall>t\<in>{0..1}. norm (q t - h t) < e\<rbrakk>
  4717             \<Longrightarrow> homotopic_paths (-{z}) h q"
  4718     using homotopic_nearby_paths [of g "-{z}"] homotopic_nearby_paths [of h "-{z}"] by force
  4719   obtain p where p:
  4720        "valid_path p" "z \<notin> path_image p"
  4721        "pathstart p = pathstart g" "pathfinish p = pathfinish g"
  4722        and gp_less:"\<forall>t\<in>{0..1}. cmod (g t - p t) < d"
  4723        and pap: "contour_integral p (\<lambda>w. 1 / (w - z)) = complex_of_real (2 * pi) * \<i> * winding_number g z"
  4724     using winding_number [OF \<open>path g\<close> pag \<open>0 < d\<close>] unfolding winding_number_prop_def by blast
  4725   obtain q where q:
  4726        "valid_path q" "z \<notin> path_image q"
  4727        "pathstart q = pathstart h" "pathfinish q = pathfinish h"
  4728        and hq_less: "\<forall>t\<in>{0..1}. cmod (h t - q t) < e"
  4729        and paq:  "contour_integral q (\<lambda>w. 1 / (w - z)) = complex_of_real (2 * pi) * \<i> * winding_number h z"
  4730     using winding_number [OF \<open>path h\<close> pah \<open>0 < e\<close>] unfolding winding_number_prop_def by blast
  4731   have "homotopic_paths (- {z}) g p"
  4732     by (simp add: d p valid_path_imp_path norm_minus_commute gp_less)
  4733   moreover have "homotopic_paths (- {z}) h q"
  4734     by (simp add: e q valid_path_imp_path norm_minus_commute hq_less)
  4735   ultimately have "homotopic_paths (- {z}) p q"
  4736     by (blast intro: homotopic_paths_trans homotopic_paths_sym assms)
  4737   then have "contour_integral p (\<lambda>w. 1/(w - z)) = contour_integral q (\<lambda>w. 1/(w - z))"
  4738     by (rule Cauchy_theorem_homotopic_paths) (auto intro!: holomorphic_intros simp: p q)
  4739   then show ?thesis
  4740     by (simp add: pap paq)
  4741 qed
  4742 
  4743 lemma winding_number_homotopic_loops:
  4744     assumes "homotopic_loops (-{z}) g h"
  4745       shows "winding_number g z = winding_number h z"
  4746 proof -
  4747   have "path g" "path h" using homotopic_loops_imp_path [OF assms] by auto
  4748   moreover have pag: "z \<notin> path_image g" and pah: "z \<notin> path_image h"
  4749     using homotopic_loops_imp_subset [OF assms] by auto
  4750   moreover have gloop: "pathfinish g = pathstart g" and hloop: "pathfinish h = pathstart h"
  4751     using homotopic_loops_imp_loop [OF assms] by auto
  4752   ultimately obtain d e where "d > 0" "e > 0"
  4753       and d: "\<And>p. \<lbrakk>path p; pathfinish p = pathstart p; \<forall>t\<in>{0..1}. norm (p t - g t) < d\<rbrakk>
  4754             \<Longrightarrow> homotopic_loops (-{z}) g p"
  4755       and e: "\<And>q. \<lbrakk>path q; pathfinish q = pathstart q; \<forall>t\<in>{0..1}. norm (q t - h t) < e\<rbrakk>
  4756             \<Longrightarrow> homotopic_loops (-{z}) h q"
  4757     using homotopic_nearby_loops [of g "-{z}"] homotopic_nearby_loops [of h "-{z}"] by force
  4758   obtain p where p:
  4759        "valid_path p" "z \<notin> path_image p"
  4760        "pathstart p = pathstart g" "pathfinish p = pathfinish g"
  4761        and gp_less:"\<forall>t\<in>{0..1}. cmod (g t - p t) < d"
  4762        and pap: "contour_integral p (\<lambda>w. 1 / (w - z)) = complex_of_real (2 * pi) * \<i> * winding_number g z"
  4763     using winding_number [OF \<open>path g\<close> pag \<open>0 < d\<close>] unfolding winding_number_prop_def by blast
  4764   obtain q where q:
  4765        "valid_path q" "z \<notin> path_image q"
  4766        "pathstart q = pathstart h" "pathfinish q = pathfinish h"
  4767        and hq_less: "\<forall>t\<in>{0..1}. cmod (h t - q t) < e"
  4768        and paq:  "contour_integral q (\<lambda>w. 1 / (w - z)) = complex_of_real (2 * pi) * \<i> * winding_number h z"
  4769     using winding_number [OF \<open>path h\<close> pah \<open>0 < e\<close>] unfolding winding_number_prop_def by blast
  4770   have gp: "homotopic_loops (- {z}) g p"
  4771     by (simp add: gloop d gp_less norm_minus_commute p valid_path_imp_path)
  4772   have hq: "homotopic_loops (- {z}) h q"
  4773     by (simp add: e hloop hq_less norm_minus_commute q valid_path_imp_path)
  4774   have "contour_integral p (\<lambda>w. 1/(w - z)) = contour_integral q (\<lambda>w. 1/(w - z))"
  4775   proof (rule Cauchy_theorem_homotopic_loops)
  4776     show "homotopic_loops (- {z}) p q"
  4777       by (blast intro: homotopic_loops_trans homotopic_loops_sym gp hq assms)
  4778   qed (auto intro!: holomorphic_intros simp: p q)
  4779   then show ?thesis
  4780     by (simp add: pap paq)
  4781 qed
  4782 
  4783 lemma winding_number_paths_linear_eq:
  4784   "\<lbrakk>path g; path h; pathstart h = pathstart g; pathfinish h = pathfinish g;
  4785     \<And>t. t \<in> {0..1} \<Longrightarrow> z \<notin> closed_segment (g t) (h t)\<rbrakk>
  4786         \<Longrightarrow> winding_number h z = winding_number g z"
  4787   by (blast intro: sym homotopic_paths_linear winding_number_homotopic_paths)
  4788 
  4789 lemma winding_number_loops_linear_eq:
  4790   "\<lbrakk>path g; path h; pathfinish g = pathstart g; pathfinish h = pathstart h;
  4791     \<And>t. t \<in> {0..1} \<Longrightarrow> z \<notin> closed_segment (g t) (h t)\<rbrakk>
  4792         \<Longrightarrow> winding_number h z = winding_number g z"
  4793   by (blast intro: sym homotopic_loops_linear winding_number_homotopic_loops)
  4794 
  4795 lemma winding_number_nearby_paths_eq:
  4796      "\<lbrakk>path g; path h; pathstart h = pathstart g; pathfinish h = pathfinish g;
  4797       \<And>t. t \<in> {0..1} \<Longrightarrow> norm(h t - g t) < norm(g t - z)\<rbrakk>
  4798       \<Longrightarrow> winding_number h z = winding_number g z"
  4799   by (metis segment_bound(2) norm_minus_commute not_le winding_number_paths_linear_eq)
  4800 
  4801 lemma winding_number_nearby_loops_eq:
  4802      "\<lbrakk>path g; path h; pathfinish g = pathstart g; pathfinish h = pathstart h;
  4803       \<And>t. t \<in> {0..1} \<Longrightarrow> norm(h t - g t) < norm(g t - z)\<rbrakk>
  4804       \<Longrightarrow> winding_number h z = winding_number g z"
  4805   by (metis segment_bound(2) norm_minus_commute not_le winding_number_loops_linear_eq)
  4806 
  4807 
  4808 proposition winding_number_subpath_combine:
  4809     "\<lbrakk>path g; z \<notin> path_image g;
  4810       u \<in> {0..1}; v \<in> {0..1}; w \<in> {0..1}\<rbrakk>
  4811       \<Longrightarrow> winding_number (subpath u v g) z + winding_number (subpath v w g) z =
  4812           winding_number (subpath u w g) z"
  4813 apply (rule trans [OF winding_number_join [THEN sym]
  4814                       winding_number_homotopic_paths [OF homotopic_join_subpaths]])
  4815 apply (auto dest: path_image_subpath_subset)
  4816 done
  4817 
  4818 
  4819 subsection\<open>Partial circle path\<close>
  4820 
  4821 definition part_circlepath :: "[complex, real, real, real, real] \<Rightarrow> complex"
  4822   where "part_circlepath z r s t \<equiv> \<lambda>x. z + of_real r * exp (\<i> * of_real (linepath s t x))"
  4823 
  4824 lemma pathstart_part_circlepath [simp]:
  4825      "pathstart(part_circlepath z r s t) = z + r*exp(\<i> * s)"
  4826 by (metis part_circlepath_def pathstart_def pathstart_linepath)
  4827 
  4828 lemma pathfinish_part_circlepath [simp]:
  4829      "pathfinish(part_circlepath z r s t) = z + r*exp(\<i>*t)"
  4830 by (metis part_circlepath_def pathfinish_def pathfinish_linepath)
  4831 
  4832 proposition has_vector_derivative_part_circlepath [derivative_intros]:
  4833     "((part_circlepath z r s t) has_vector_derivative
  4834       (\<i> * r * (of_real t - of_real s) * exp(\<i> * linepath s t x)))
  4835      (at x within X)"
  4836   apply (simp add: part_circlepath_def linepath_def scaleR_conv_of_real)
  4837   apply (rule has_vector_derivative_real_complex)
  4838   apply (rule derivative_eq_intros | simp)+
  4839   done
  4840 
  4841 corollary vector_derivative_part_circlepath:
  4842     "vector_derivative (part_circlepath z r s t) (at x) =
  4843        \<i> * r * (of_real t - of_real s) * exp(\<i> * linepath s t x)"
  4844   using has_vector_derivative_part_circlepath vector_derivative_at by blast
  4845 
  4846 corollary vector_derivative_part_circlepath01:
  4847     "\<lbrakk>0 \<le> x; x \<le> 1\<rbrakk>
  4848      \<Longrightarrow> vector_derivative (part_circlepath z r s t) (at x within {0..1}) =
  4849           \<i> * r * (of_real t - of_real s) * exp(\<i> * linepath s t x)"
  4850   using has_vector_derivative_part_circlepath
  4851   by (auto simp: vector_derivative_at_within_ivl)
  4852 
  4853 lemma valid_path_part_circlepath [simp]: "valid_path (part_circlepath z r s t)"
  4854   apply (simp add: valid_path_def)
  4855   apply (rule C1_differentiable_imp_piecewise)
  4856   apply (auto simp: C1_differentiable_on_eq vector_derivative_works vector_derivative_part_circlepath has_vector_derivative_part_circlepath
  4857               intro!: continuous_intros)
  4858   done
  4859 
  4860 lemma path_part_circlepath [simp]: "path (part_circlepath z r s t)"
  4861   by (simp add: valid_path_imp_path)
  4862 
  4863 proposition path_image_part_circlepath:
  4864   assumes "s \<le> t"
  4865     shows "path_image (part_circlepath z r s t) = {z + r * exp(\<i> * of_real x) | x. s \<le> x \<and> x \<le> t}"
  4866 proof -
  4867   { fix z::real
  4868     assume "0 \<le> z" "z \<le> 1"
  4869     with \<open>s \<le> t\<close> have "\<exists>x. (exp (\<i> * linepath s t z) = exp (\<i> * of_real x)) \<and> s \<le> x \<and> x \<le> t"
  4870       apply (rule_tac x="(1 - z) * s + z * t" in exI)
  4871       apply (simp add: linepath_def scaleR_conv_of_real algebra_simps)
  4872       apply (rule conjI)
  4873       using mult_right_mono apply blast
  4874       using affine_ineq  by (metis "mult.commute")
  4875   }
  4876   moreover
  4877   { fix z
  4878     assume "s \<le> z" "z \<le> t"
  4879     then have "z + of_real r * exp (\<i> * of_real z) \<in> (\<lambda>x. z + of_real r * exp (\<i> * linepath s t x)) ` {0..1}"
  4880       apply (rule_tac x="(z - s)/(t - s)" in image_eqI)
  4881       apply (simp add: linepath_def scaleR_conv_of_real divide_simps exp_eq)
  4882       apply (auto simp: algebra_simps divide_simps)
  4883       done
  4884   }
  4885   ultimately show ?thesis
  4886     by (fastforce simp add: path_image_def part_circlepath_def)
  4887 qed
  4888 
  4889 corollary path_image_part_circlepath_subset:
  4890     "\<lbrakk>s \<le> t; 0 \<le> r\<rbrakk> \<Longrightarrow> path_image(part_circlepath z r s t) \<subseteq> sphere z r"
  4891 by (auto simp: path_image_part_circlepath sphere_def dist_norm algebra_simps norm_mult)
  4892 
  4893 proposition in_path_image_part_circlepath:
  4894   assumes "w \<in> path_image(part_circlepath z r s t)" "s \<le> t" "0 \<le> r"
  4895     shows "norm(w - z) = r"
  4896 proof -
  4897   have "w \<in> {c. dist z c = r}"
  4898     by (metis (no_types) path_image_part_circlepath_subset sphere_def subset_eq assms)
  4899   thus ?thesis
  4900     by (simp add: dist_norm norm_minus_commute)
  4901 qed
  4902 
  4903 proposition finite_bounded_log: "finite {z::complex. norm z \<le> b \<and> exp z = w}"
  4904 proof (cases "w = 0")
  4905   case True then show ?thesis by auto
  4906 next
  4907   case False
  4908   have *: "finite {x. cmod (complex_of_real (2 * real_of_int x * pi) * \<i>) \<le> b + cmod (Ln w)}"
  4909     apply (simp add: norm_mult finite_int_iff_bounded_le)
  4910     apply (rule_tac x="\<lfloor>(b + cmod (Ln w)) / (2*pi)\<rfloor>" in exI)
  4911     apply (auto simp: divide_simps le_floor_iff)
  4912     done
  4913   have [simp]: "\<And>P f. {z. P z \<and> (\<exists>n. z = f n)} = f ` {n. P (f n)}"
  4914     by blast
  4915   show ?thesis
  4916     apply (subst exp_Ln [OF False, symmetric])
  4917     apply (simp add: exp_eq)
  4918     using norm_add_leD apply (fastforce intro: finite_subset [OF _ *])
  4919     done
  4920 qed
  4921 
  4922 lemma finite_bounded_log2:
  4923   fixes a::complex
  4924     assumes "a \<noteq> 0"
  4925     shows "finite {z. norm z \<le> b \<and> exp(a*z) = w}"
  4926 proof -
  4927   have *: "finite ((\<lambda>z. z / a) ` {z. cmod z \<le> b * cmod a \<and> exp z = w})"
  4928     by (rule finite_imageI [OF finite_bounded_log])
  4929   show ?thesis
  4930     by (rule finite_subset [OF _ *]) (force simp: assms norm_mult)
  4931 qed
  4932 
  4933 proposition has_contour_integral_bound_part_circlepath_strong:
  4934   assumes fi: "(f has_contour_integral i) (part_circlepath z r s t)"
  4935       and "finite k" and le: "0 \<le> B" "0 < r" "s \<le> t"
  4936       and B: "\<And>x. x \<in> path_image(part_circlepath z r s t) - k \<Longrightarrow> norm(f x) \<le> B"
  4937     shows "cmod i \<le> B * r * (t - s)"
  4938 proof -
  4939   consider "s = t" | "s < t" using \<open>s \<le> t\<close> by linarith
  4940   then show ?thesis
  4941   proof cases
  4942     case 1 with fi [unfolded has_contour_integral]
  4943     have "i = 0"  by (simp add: vector_derivative_part_circlepath)
  4944     with assms show ?thesis by simp
  4945   next
  4946     case 2
  4947     have [simp]: "\<bar>r\<bar> = r" using \<open>r > 0\<close> by linarith
  4948     have [simp]: "cmod (complex_of_real t - complex_of_real s) = t-s"
  4949       by (metis "2" abs_of_pos diff_gt_0_iff_gt norm_of_real of_real_diff)
  4950     have "finite (part_circlepath z r s t -` {y} \<inter> {0..1})" if "y \<in> k" for y
  4951     proof -
  4952       define w where "w = (y - z)/of_real r / exp(\<i> * of_real s)"
  4953       have fin: "finite (of_real -` {z. cmod z \<le> 1 \<and> exp (\<i> * complex_of_real (t - s) * z) = w})"
  4954         apply (rule finite_vimageI [OF finite_bounded_log2])
  4955         using \<open>s < t\<close> apply (auto simp: inj_of_real)
  4956         done
  4957       show ?thesis
  4958         apply (simp add: part_circlepath_def linepath_def vimage_def)
  4959         apply (rule finite_subset [OF _ fin])
  4960         using le
  4961         apply (auto simp: w_def algebra_simps scaleR_conv_of_real exp_add exp_diff)
  4962         done
  4963     qed
  4964     then have fin01: "finite ((part_circlepath z r s t) -` k \<inter> {0..1})"
  4965       by (rule finite_finite_vimage_IntI [OF \<open>finite k\<close>])
  4966     have **: "((\<lambda>x. if (part_circlepath z r s t x) \<in> k then 0
  4967                     else f(part_circlepath z r s t x) *
  4968                        vector_derivative (part_circlepath z r s t) (at x)) has_integral i)  {0..1}"
  4969       by (rule has_integral_spike [OF negligible_finite [OF fin01]])  (use fi has_contour_integral in auto)
  4970     have *: "\<And>x. \<lbrakk>0 \<le> x; x \<le> 1; part_circlepath z r s t x \<notin> k\<rbrakk> \<Longrightarrow> cmod (f (part_circlepath z r s t x)) \<le> B"
  4971       by (auto intro!: B [unfolded path_image_def image_def, simplified])
  4972     show ?thesis
  4973       apply (rule has_integral_bound [where 'a=real, simplified, OF _ **, simplified])
  4974       using assms apply force
  4975       apply (simp add: norm_mult vector_derivative_part_circlepath)
  4976       using le * "2" \<open>r > 0\<close> by auto
  4977   qed
  4978 qed
  4979 
  4980 corollary has_contour_integral_bound_part_circlepath:
  4981       "\<lbrakk>(f has_contour_integral i) (part_circlepath z r s t);
  4982         0 \<le> B; 0 < r; s \<le> t;
  4983         \<And>x. x \<in> path_image(part_circlepath z r s t) \<Longrightarrow> norm(f x) \<le> B\<rbrakk>
  4984        \<Longrightarrow> norm i \<le> B*r*(t - s)"
  4985   by (auto intro: has_contour_integral_bound_part_circlepath_strong)
  4986 
  4987 proposition contour_integrable_continuous_part_circlepath:
  4988      "continuous_on (path_image (part_circlepath z r s t)) f
  4989       \<Longrightarrow> f contour_integrable_on (part_circlepath z r s t)"
  4990   apply (simp add: contour_integrable_on has_contour_integral_def vector_derivative_part_circlepath path_image_def)
  4991   apply (rule integrable_continuous_real)
  4992   apply (fast intro: path_part_circlepath [unfolded path_def] continuous_intros continuous_on_compose2 [where g=f, OF _ _ order_refl])
  4993   done
  4994 
  4995 proposition winding_number_part_circlepath_pos_less:
  4996   assumes "s < t" and no: "norm(w - z) < r"
  4997     shows "0 < Re (winding_number(part_circlepath z r s t) w)"
  4998 proof -
  4999   have "0 < r" by (meson no norm_not_less_zero not_le order.strict_trans2)
  5000   note valid_path_part_circlepath
  5001   moreover have " w \<notin> path_image (part_circlepath z r s t)"
  5002     using assms by (auto simp: path_image_def image_def part_circlepath_def norm_mult linepath_def)
  5003   moreover have "0 < r * (t - s) * (r - cmod (w - z))"
  5004     using assms by (metis \<open>0 < r\<close> diff_gt_0_iff_gt mult_pos_pos)
  5005   ultimately show ?thesis
  5006     apply (rule winding_number_pos_lt [where e = "r*(t - s)*(r - norm(w - z))"])
  5007     apply (simp add: vector_derivative_part_circlepath right_diff_distrib [symmetric] mult_ac)
  5008     apply (rule mult_left_mono)+
  5009     using Re_Im_le_cmod [of "w-z" "linepath s t x" for x]
  5010     apply (simp add: exp_Euler cos_of_real sin_of_real part_circlepath_def algebra_simps cos_squared_eq [unfolded power2_eq_square])
  5011     using assms \<open>0 < r\<close> by auto
  5012 qed
  5013 
  5014 proposition simple_path_part_circlepath:
  5015     "simple_path(part_circlepath z r s t) \<longleftrightarrow> (r \<noteq> 0 \<and> s \<noteq> t \<and> \<bar>s - t\<bar> \<le> 2*pi)"
  5016 proof (cases "r = 0 \<or> s = t")
  5017   case True
  5018   then show ?thesis
  5019     unfolding part_circlepath_def simple_path_def
  5020     by (rule disjE) (force intro: bexI [where x = "1/4"] bexI [where x = "1/3"])+
  5021 next
  5022   case False then have "r \<noteq> 0" "s \<noteq> t" by auto
  5023   have *: "\<And>x y z s t. \<i>*((1 - x) * s + x * t) = \<i>*(((1 - y) * s + y * t)) + z  \<longleftrightarrow> \<i>*(x - y) * (t - s) = z"
  5024     by (simp add: algebra_simps)
  5025   have abs01: "\<And>x y::real. 0 \<le> x \<and> x \<le> 1 \<and> 0 \<le> y \<and> y \<le> 1
  5026                       \<Longrightarrow> (x = y \<or> x = 0 \<and> y = 1 \<or> x = 1 \<and> y = 0 \<longleftrightarrow> \<bar>x - y\<bar> \<in> {0,1})"
  5027     by auto
  5028   have **: "\<And>x y. (\<exists>n. (complex_of_real x - of_real y) * (of_real t - of_real s) = 2 * (of_int n * of_real pi)) \<longleftrightarrow>
  5029                   (\<exists>n. \<bar>x - y\<bar> * (t - s) = 2 * (of_int n * pi))"
  5030     by (force simp: algebra_simps abs_if dest: arg_cong [where f=Re] arg_cong [where f=complex_of_real]
  5031                     intro: exI [where x = "-n" for n])
  5032   have 1: "\<bar>s - t\<bar> \<le> 2 * pi"
  5033     if "\<And>x. 0 \<le> x \<and> x \<le> 1 \<Longrightarrow> (\<exists>n. x * (t - s) = 2 * (real_of_int n * pi)) \<longrightarrow> x = 0 \<or> x = 1"
  5034   proof (rule ccontr)
  5035     assume "\<not> \<bar>s - t\<bar> \<le> 2 * pi"
  5036     then have *: "\<And>n. t - s \<noteq> of_int n * \<bar>s - t\<bar>"
  5037       using False that [of "2*pi / \<bar>t - s\<bar>"] by (simp add: abs_minus_commute divide_simps)
  5038     show False
  5039       using * [of 1] * [of "-1"] by auto
  5040   qed
  5041   have 2: "\<bar>s - t\<bar> = \<bar>2 * (real_of_int n * pi) / x\<bar>" if "x \<noteq> 0" "x * (t - s) = 2 * (real_of_int n * pi)" for x n
  5042   proof -
  5043     have "t-s = 2 * (real_of_int n * pi)/x"
  5044       using that by (simp add: field_simps)
  5045     then show ?thesis by (metis abs_minus_commute)
  5046   qed
  5047   have abs_away: "\<And>P. (\<forall>x\<in>{0..1}. \<forall>y\<in>{0..1}. P \<bar>x - y\<bar>) \<longleftrightarrow> (\<forall>x::real. 0 \<le> x \<and> x \<le> 1 \<longrightarrow> P x)"
  5048     by force
  5049   show ?thesis using False
  5050     apply (simp add: simple_path_def)
  5051     apply (simp add: part_circlepath_def linepath_def exp_eq  * ** abs01  del: Set.insert_iff)
  5052     apply (subst abs_away)
  5053     apply (auto simp: 1)
  5054     apply (rule ccontr)
  5055     apply (auto simp: 2 divide_simps abs_mult dest: of_int_leD)
  5056     done
  5057 qed
  5058 
  5059 proposition arc_part_circlepath:
  5060   assumes "r \<noteq> 0" "s \<noteq> t" "\<bar>s - t\<bar> < 2*pi"
  5061     shows "arc (part_circlepath z r s t)"
  5062 proof -
  5063   have *: "x = y" if eq: "\<i> * (linepath s t x) = \<i> * (linepath s t y) + 2 * of_int n * complex_of_real pi * \<i>"
  5064     and x: "x \<in> {0..1}" and y: "y \<in> {0..1}" for x y n
  5065   proof (rule ccontr)
  5066     assume "x \<noteq> y"
  5067     have "(linepath s t x) = (linepath s t y) + 2 * of_int n * complex_of_real pi"
  5068       by (metis add_divide_eq_iff complex_i_not_zero mult.commute nonzero_mult_div_cancel_left eq)
  5069     then have "s*y + t*x = s*x + (t*y + of_int n * (pi * 2))"
  5070       by (force simp: algebra_simps linepath_def dest: arg_cong [where f=Re])
  5071     with \<open>x \<noteq> y\<close> have st: "s-t = (of_int n * (pi * 2) / (y-x))"
  5072       by (force simp: field_simps)
  5073     have "\<bar>real_of_int n\<bar> < \<bar>y - x\<bar>"
  5074       using assms \<open>x \<noteq> y\<close> by (simp add: st abs_mult field_simps)
  5075     then show False
  5076       using assms x y st by (auto dest: of_int_lessD)
  5077   qed
  5078   show ?thesis
  5079     using assms
  5080     apply (simp add: arc_def)
  5081     apply (simp add: part_circlepath_def inj_on_def exp_eq)
  5082     apply (blast intro: *)
  5083     done
  5084 qed
  5085 
  5086 
  5087 subsection\<open>Special case of one complete circle\<close>
  5088 
  5089 definition circlepath :: "[complex, real, real] \<Rightarrow> complex"
  5090   where "circlepath z r \<equiv> part_circlepath z r 0 (2*pi)"
  5091 
  5092 lemma circlepath: "circlepath z r = (\<lambda>x. z + r * exp(2 * of_real pi * \<i> * of_real x))"
  5093   by (simp add: circlepath_def part_circlepath_def linepath_def algebra_simps)
  5094 
  5095 lemma pathstart_circlepath [simp]: "pathstart (circlepath z r) = z + r"
  5096   by (simp add: circlepath_def)
  5097 
  5098 lemma pathfinish_circlepath [simp]: "pathfinish (circlepath z r) = z + r"
  5099   by (simp add: circlepath_def) (metis exp_two_pi_i mult.commute)
  5100 
  5101 lemma circlepath_minus: "circlepath z (-r) x = circlepath z r (x + 1/2)"
  5102 proof -
  5103   have "z + of_real r * exp (2 * pi * \<i> * (x + 1/2)) =
  5104         z + of_real r * exp (2 * pi * \<i> * x + pi * \<i>)"
  5105     by (simp add: divide_simps) (simp add: algebra_simps)
  5106   also have "\<dots> = z - r * exp (2 * pi * \<i> * x)"
  5107     by (simp add: exp_add)
  5108   finally show ?thesis
  5109     by (simp add: circlepath path_image_def sphere_def dist_norm)
  5110 qed
  5111 
  5112 lemma circlepath_add1: "circlepath z r (x+1) = circlepath z r x"
  5113   using circlepath_minus [of z r "x+1/2"] circlepath_minus [of z "-r" x]
  5114   by (simp add: add.commute)
  5115 
  5116 lemma circlepath_add_half: "circlepath z r (x + 1/2) = circlepath z r (x - 1/2)"
  5117   using circlepath_add1 [of z r "x-1/2"]
  5118   by (simp add: add.commute)
  5119 
  5120 lemma path_image_circlepath_minus_subset:
  5121      "path_image (circlepath z (-r)) \<subseteq> path_image (circlepath z r)"
  5122   apply (simp add: path_image_def image_def circlepath_minus, clarify)
  5123   apply (case_tac "xa \<le> 1/2", force)
  5124   apply (force simp: circlepath_add_half)+
  5125   done
  5126 
  5127 lemma path_image_circlepath_minus: "path_image (circlepath z (-r)) = path_image (circlepath z r)"
  5128   using path_image_circlepath_minus_subset by fastforce
  5129 
  5130 proposition has_vector_derivative_circlepath [derivative_intros]:
  5131  "((circlepath z r) has_vector_derivative (2 * pi * \<i> * r * exp (2 * of_real pi * \<i> * of_real x)))
  5132    (at x within X)"
  5133   apply (simp add: circlepath_def scaleR_conv_of_real)
  5134   apply (rule derivative_eq_intros)
  5135   apply (simp add: algebra_simps)
  5136   done
  5137 
  5138 corollary vector_derivative_circlepath:
  5139    "vector_derivative (circlepath z r) (at x) =
  5140     2 * pi * \<i> * r * exp(2 * of_real pi * \<i> * x)"
  5141 using has_vector_derivative_circlepath vector_derivative_at by blast
  5142 
  5143 corollary vector_derivative_circlepath01:
  5144     "\<lbrakk>0 \<le> x; x \<le> 1\<rbrakk>
  5145      \<Longrightarrow> vector_derivative (circlepath z r) (at x within {0..1}) =
  5146           2 * pi * \<i> * r * exp(2 * of_real pi * \<i> * x)"
  5147   using has_vector_derivative_circlepath
  5148   by (auto simp: vector_derivative_at_within_ivl)
  5149 
  5150 lemma valid_path_circlepath [simp]: "valid_path (circlepath z r)"
  5151   by (simp add: circlepath_def)
  5152 
  5153 lemma path_circlepath [simp]: "path (circlepath z r)"
  5154   by (simp add: valid_path_imp_path)
  5155 
  5156 lemma path_image_circlepath_nonneg:
  5157   assumes "0 \<le> r" shows "path_image (circlepath z r) = sphere z r"
  5158 proof -
  5159   have *: "x \<in> (\<lambda>u. z + (cmod (x - z)) * exp (\<i> * (of_real u * (of_real pi * 2)))) ` {0..1}" for x
  5160   proof (cases "x = z")
  5161     case True then show ?thesis by force
  5162   next
  5163     case False
  5164     define w where "w = x - z"
  5165     then have "w \<noteq> 0" by (simp add: False)
  5166     have **: "\<And>t. \<lbrakk>Re w = cos t * cmod w; Im w = sin t * cmod w\<rbrakk> \<Longrightarrow> w = of_real (cmod w) * exp (\<i> * t)"
  5167       using cis_conv_exp complex_eq_iff by auto
  5168     show ?thesis
  5169       apply (rule sincos_total_2pi [of "Re(w/of_real(norm w))" "Im(w/of_real(norm w))"])
  5170       apply (simp add: divide_simps \<open>w \<noteq> 0\<close> cmod_power2 [symmetric])
  5171       apply (rule_tac x="t / (2*pi)" in image_eqI)
  5172       apply (simp add: divide_simps \<open>w \<noteq> 0\<close>)
  5173       using False **
  5174       apply (auto simp: w_def)
  5175       done
  5176   qed
  5177   show ?thesis
  5178     unfolding circlepath path_image_def sphere_def dist_norm
  5179     by (force simp: assms algebra_simps norm_mult norm_minus_commute intro: *)
  5180 qed
  5181 
  5182 proposition path_image_circlepath [simp]:
  5183     "path_image (circlepath z r) = sphere z \<bar>r\<bar>"
  5184   using path_image_circlepath_minus
  5185   by (force simp: path_image_circlepath_nonneg abs_if)
  5186 
  5187 lemma has_contour_integral_bound_circlepath_strong:
  5188       "\<lbrakk>(f has_contour_integral i) (circlepath z r);
  5189         finite k; 0 \<le> B; 0 < r;
  5190         \<And>x. \<lbrakk>norm(x - z) = r; x \<notin> k\<rbrakk> \<Longrightarrow> norm(f x) \<le> B\<rbrakk>
  5191         \<Longrightarrow> norm i \<le> B*(2*pi*r)"
  5192   unfolding circlepath_def
  5193   by (auto simp: algebra_simps in_path_image_part_circlepath dest!: has_contour_integral_bound_part_circlepath_strong)
  5194 
  5195 corollary has_contour_integral_bound_circlepath:
  5196       "\<lbrakk>(f has_contour_integral i) (circlepath z r);
  5197         0 \<le> B; 0 < r; \<And>x. norm(x - z) = r \<Longrightarrow> norm(f x) \<le> B\<rbrakk>
  5198         \<Longrightarrow> norm i \<le> B*(2*pi*r)"
  5199   by (auto intro: has_contour_integral_bound_circlepath_strong)
  5200 
  5201 proposition contour_integrable_continuous_circlepath:
  5202     "continuous_on (path_image (circlepath z r)) f
  5203      \<Longrightarrow> f contour_integrable_on (circlepath z r)"
  5204   by (simp add: circlepath_def contour_integrable_continuous_part_circlepath)
  5205 
  5206 lemma simple_path_circlepath: "simple_path(circlepath z r) \<longleftrightarrow> (r \<noteq> 0)"
  5207   by (simp add: circlepath_def simple_path_part_circlepath)
  5208 
  5209 lemma notin_path_image_circlepath [simp]: "cmod (w - z) < r \<Longrightarrow> w \<notin> path_image (circlepath z r)"
  5210   by (simp add: sphere_def dist_norm norm_minus_commute)
  5211 
  5212 proposition contour_integral_circlepath:
  5213   assumes "r > 0"
  5214   shows "contour_integral (circlepath z r) (\<lambda>w. 1 / (w - z)) = 2 * complex_of_real pi * \<i>"
  5215 proof (rule contour_integral_unique)
  5216   show "((\<lambda>w. 1 / (w - z)) has_contour_integral 2 * complex_of_real pi * \<i>) (circlepath z r)"
  5217     unfolding has_contour_integral_def using assms
  5218     apply (subst has_integral_cong)
  5219      apply (simp add: vector_derivative_circlepath01)
  5220     using has_integral_const_real [of _ 0 1] apply (force simp: circlepath)
  5221     done
  5222 qed
  5223 
  5224 lemma winding_number_circlepath_centre: "0 < r \<Longrightarrow> winding_number (circlepath z r) z = 1"
  5225   apply (rule winding_number_unique_loop)
  5226   apply (simp_all add: sphere_def valid_path_imp_path)
  5227   apply (rule_tac x="circlepath z r" in exI)
  5228   apply (simp add: sphere_def contour_integral_circlepath)
  5229   done
  5230 
  5231 proposition winding_number_circlepath:
  5232   assumes "norm(w - z) < r" shows "winding_number(circlepath z r) w = 1"
  5233 proof (cases "w = z")
  5234   case True then show ?thesis
  5235     using assms winding_number_circlepath_centre by auto
  5236 next
  5237   case False
  5238   have [simp]: "r > 0"
  5239     using assms le_less_trans norm_ge_zero by blast
  5240   define r' where "r' = norm(w - z)"
  5241   have "r' < r"
  5242     by (simp add: assms r'_def)
  5243   have disjo: "cball z r' \<inter> sphere z r = {}"
  5244     using \<open>r' < r\<close> by (force simp: cball_def sphere_def)
  5245   have "winding_number(circlepath z r) w = winding_number(circlepath z r) z"
  5246   proof (rule winding_number_around_inside [where s = "cball z r'"])
  5247     show "winding_number (circlepath z r) z \<noteq> 0"
  5248       by (simp add: winding_number_circlepath_centre)
  5249     show "cball z r' \<inter> path_image (circlepath z r) = {}"
  5250       by (simp add: disjo less_eq_real_def)
  5251   qed (auto simp: r'_def dist_norm norm_minus_commute)
  5252   also have "\<dots> = 1"
  5253     by (simp add: winding_number_circlepath_centre)
  5254   finally show ?thesis .
  5255 qed
  5256 
  5257 
  5258 text\<open> Hence the Cauchy formula for points inside a circle.\<close>
  5259 
  5260 theorem Cauchy_integral_circlepath:
  5261   assumes contf: "continuous_on (cball z r) f" and holf: "f holomorphic_on (ball z r)" and wz: "norm(w - z) < r"
  5262   shows "((\<lambda>u. f u/(u - w)) has_contour_integral (2 * of_real pi * \<i> * f w))
  5263          (circlepath z r)"
  5264 proof -
  5265   have "r > 0"
  5266     using assms le_less_trans norm_ge_zero by blast
  5267   have "((\<lambda>u. f u / (u - w)) has_contour_integral (2 * pi) * \<i> * winding_number (circlepath z r) w * f w)
  5268         (circlepath z r)"
  5269   proof (rule Cauchy_integral_formula_weak [where s = "cball z r" and k = "{}"])
  5270     show "\<And>x. x \<in> interior (cball z r) - {} \<Longrightarrow>
  5271          f field_differentiable at x"
  5272       using holf holomorphic_on_imp_differentiable_at by auto
  5273     have "w \<notin> sphere z r"
  5274       by simp (metis dist_commute dist_norm not_le order_refl wz)
  5275     then show "path_image (circlepath z r) \<subseteq> cball z r - {w}"
  5276       using \<open>r > 0\<close> by (auto simp add: cball_def sphere_def)
  5277   qed (use wz in \<open>simp_all add: dist_norm norm_minus_commute contf\<close>)
  5278   then show ?thesis
  5279     by (simp add: winding_number_circlepath assms)
  5280 qed
  5281 
  5282 corollary Cauchy_integral_circlepath_simple:
  5283   assumes "f holomorphic_on cball z r" "norm(w - z) < r"
  5284   shows "((\<lambda>u. f u/(u - w)) has_contour_integral (2 * of_real pi * \<i> * f w))
  5285          (circlepath z r)"
  5286 using assms by (force simp: holomorphic_on_imp_continuous_on holomorphic_on_subset Cauchy_integral_circlepath)
  5287 
  5288 
  5289 lemma no_bounded_connected_component_imp_winding_number_zero:
  5290   assumes g: "path g" "path_image g \<subseteq> s" "pathfinish g = pathstart g" "z \<notin> s"
  5291       and nb: "\<And>z. bounded (connected_component_set (- s) z) \<longrightarrow> z \<in> s"
  5292   shows "winding_number g z = 0"
  5293 apply (rule winding_number_zero_in_outside)
  5294 apply (simp_all add: assms)
  5295 by (metis nb [of z] \<open>path_image g \<subseteq> s\<close> \<open>z \<notin> s\<close> contra_subsetD mem_Collect_eq outside outside_mono)
  5296 
  5297 lemma no_bounded_path_component_imp_winding_number_zero:
  5298   assumes g: "path g" "path_image g \<subseteq> s" "pathfinish g = pathstart g" "z \<notin> s"
  5299       and nb: "\<And>z. bounded (path_component_set (- s) z) \<longrightarrow> z \<in> s"
  5300   shows "winding_number g z = 0"
  5301 apply (rule no_bounded_connected_component_imp_winding_number_zero [OF g])
  5302 by (simp add: bounded_subset nb path_component_subset_connected_component)
  5303 
  5304 
  5305 subsection\<open> Uniform convergence of path integral\<close>
  5306 
  5307 text\<open>Uniform convergence when the derivative of the path is bounded, and in particular for the special case of a circle.\<close>
  5308 
  5309 proposition contour_integral_uniform_limit:
  5310   assumes ev_fint: "eventually (\<lambda>n::'a. (f n) contour_integrable_on \<gamma>) F"
  5311       and ul_f: "uniform_limit (path_image \<gamma>) f l F"
  5312       and noleB: "\<And>t. t \<in> {0..1} \<Longrightarrow> norm (vector_derivative \<gamma> (at t)) \<le> B"
  5313       and \<gamma>: "valid_path \<gamma>"
  5314       and [simp]: "~ (trivial_limit F)"
  5315   shows "l contour_integrable_on \<gamma>" "((\<lambda>n. contour_integral \<gamma> (f n)) \<longlongrightarrow> contour_integral \<gamma> l) F"
  5316 proof -
  5317   have "0 \<le> B" by (meson noleB [of 0] atLeastAtMost_iff norm_ge_zero order_refl order_trans zero_le_one)
  5318   { fix e::real
  5319     assume "0 < e"
  5320     then have "0 < e / (\<bar>B\<bar> + 1)" by simp
  5321     then have "\<forall>\<^sub>F n in F. \<forall>x\<in>path_image \<gamma>. cmod (f n x - l x) < e / (\<bar>B\<bar> + 1)"
  5322       using ul_f [unfolded uniform_limit_iff dist_norm] by auto
  5323     with ev_fint
  5324     obtain a where fga: "\<And>x. x \<in> {0..1} \<Longrightarrow> cmod (f a (\<gamma> x) - l (\<gamma> x)) < e / (\<bar>B\<bar> + 1)"
  5325                and inta: "(\<lambda>t. f a (\<gamma> t) * vector_derivative \<gamma> (at t)) integrable_on {0..1}"
  5326       using eventually_happens [OF eventually_conj]
  5327       by (fastforce simp: contour_integrable_on path_image_def)
  5328     have Ble: "B * e / (\<bar>B\<bar> + 1) \<le> e"
  5329       using \<open>0 \<le> B\<close>  \<open>0 < e\<close> by (simp add: divide_simps)
  5330     have "\<exists>h. (\<forall>x\<in>{0..1}. cmod (l (\<gamma> x) * vector_derivative \<gamma> (at x) - h x) \<le> e) \<and> h integrable_on {0..1}"
  5331     proof (intro exI conjI ballI)
  5332       show "cmod (l (\<gamma> x) * vector_derivative \<gamma> (at x) - f a (\<gamma> x) * vector_derivative \<gamma> (at x)) \<le> e" 
  5333         if "x \<in> {0..1}" for x
  5334         apply (rule order_trans [OF _ Ble])
  5335         using noleB [OF that] fga [OF that] \<open>0 \<le> B\<close> \<open>0 < e\<close>
  5336         apply (simp add: norm_mult left_diff_distrib [symmetric] norm_minus_commute divide_simps)
  5337         apply (fastforce simp: mult_ac dest: mult_mono [OF less_imp_le])
  5338         done
  5339     qed (rule inta)
  5340   }
  5341   then show lintg: "l contour_integrable_on \<gamma>"
  5342     unfolding contour_integrable_on by (metis (mono_tags, lifting)integrable_uniform_limit_real) 
  5343   { fix e::real
  5344     define B' where "B' = B + 1"
  5345     have B': "B' > 0" "B' > B" using  \<open>0 \<le> B\<close> by (auto simp: B'_def)
  5346     assume "0 < e"
  5347     then have ev_no': "\<forall>\<^sub>F n in F. \<forall>x\<in>path_image \<gamma>. 2 * cmod (f n x - l x) < e / B'"
  5348       using ul_f [unfolded uniform_limit_iff dist_norm, rule_format, of "e / B' / 2"] B' 
  5349         by (simp add: field_simps)
  5350     have ie: "integral {0..1::real} (\<lambda>x. e / 2) < e" using \<open>0 < e\<close> by simp
  5351     have *: "cmod (f x (\<gamma> t) * vector_derivative \<gamma> (at t) - l (\<gamma> t) * vector_derivative \<gamma> (at t)) \<le> e / 2"
  5352              if t: "t\<in>{0..1}" and leB': "2 * cmod (f x (\<gamma> t) - l (\<gamma> t)) < e / B'" for x t
  5353     proof -
  5354       have "2 * cmod (f x (\<gamma> t) - l (\<gamma> t)) * cmod (vector_derivative \<gamma> (at t)) \<le> e * (B/ B')"
  5355         using mult_mono [OF less_imp_le [OF leB'] noleB] B' \<open>0 < e\<close> t by auto
  5356       also have "\<dots> < e"
  5357         by (simp add: B' \<open>0 < e\<close> mult_imp_div_pos_less)
  5358       finally have "2 * cmod (f x (\<gamma> t) - l (\<gamma> t)) * cmod (vector_derivative \<gamma> (at t)) < e" .
  5359       then show ?thesis
  5360         by (simp add: left_diff_distrib [symmetric] norm_mult)
  5361     qed
  5362     have le_e: "\<And>x. \<lbrakk>\<forall>xa\<in>{0..1}. 2 * cmod (f x (\<gamma> xa) - l (\<gamma> xa)) < e / B'; f x contour_integrable_on \<gamma>\<rbrakk>
  5363          \<Longrightarrow> cmod (integral {0..1}
  5364                     (\<lambda>u. f x (\<gamma> u) * vector_derivative \<gamma> (at u) - l (\<gamma> u) * vector_derivative \<gamma> (at u))) < e"
  5365       apply (rule le_less_trans [OF integral_norm_bound_integral ie])
  5366         apply (simp add: lintg integrable_diff contour_integrable_on [symmetric])
  5367        apply (blast intro: *)+
  5368       done
  5369     have "\<forall>\<^sub>F x in F. dist (contour_integral \<gamma> (f x)) (contour_integral \<gamma> l) < e"
  5370       apply (rule eventually_mono [OF eventually_conj [OF ev_no' ev_fint]])
  5371       apply (simp add: dist_norm contour_integrable_on path_image_def contour_integral_integral)
  5372       apply (simp add: lintg integral_diff [symmetric] contour_integrable_on [symmetric] le_e)
  5373       done
  5374   }
  5375   then show "((\<lambda>n. contour_integral \<gamma> (f n)) \<longlongrightarrow> contour_integral \<gamma> l) F"
  5376     by (rule tendstoI)
  5377 qed
  5378 
  5379 corollary contour_integral_uniform_limit_circlepath:
  5380   assumes "\<forall>\<^sub>F n::'a in F. (f n) contour_integrable_on (circlepath z r)"
  5381       and "uniform_limit (sphere z r) f l F"
  5382       and "~ (trivial_limit F)" "0 < r"
  5383     shows "l contour_integrable_on (circlepath z r)"
  5384           "((\<lambda>n. contour_integral (circlepath z r) (f n)) \<longlongrightarrow> contour_integral (circlepath z r) l) F"
  5385   using assms by (auto simp: vector_derivative_circlepath norm_mult intro!: contour_integral_uniform_limit)
  5386 
  5387 
  5388 subsection\<open> General stepping result for derivative formulas\<close>
  5389 
  5390 proposition Cauchy_next_derivative:
  5391   assumes "continuous_on (path_image \<gamma>) f'"
  5392       and leB: "\<And>t. t \<in> {0..1} \<Longrightarrow> norm (vector_derivative \<gamma> (at t)) \<le> B"
  5393       and int: "\<And>w. w \<in> s - path_image \<gamma> \<Longrightarrow> ((\<lambda>u. f' u / (u - w)^k) has_contour_integral f w) \<gamma>"
  5394       and k: "k \<noteq> 0"
  5395       and "open s"
  5396       and \<gamma>: "valid_path \<gamma>"
  5397       and w: "w \<in> s - path_image \<gamma>"
  5398     shows "(\<lambda>u. f' u / (u - w)^(Suc k)) contour_integrable_on \<gamma>"
  5399       and "(f has_field_derivative (k * contour_integral \<gamma> (\<lambda>u. f' u/(u - w)^(Suc k))))
  5400            (at w)"  (is "?thes2")
  5401 proof -
  5402   have "open (s - path_image \<gamma>)" using \<open>open s\<close> closed_valid_path_image \<gamma> by blast
  5403   then obtain d where "d>0" and d: "ball w d \<subseteq> s - path_image \<gamma>" using w
  5404     using open_contains_ball by blast
  5405   have [simp]: "\<And>n. cmod (1 + of_nat n) = 1 + of_nat n"
  5406     by (metis norm_of_nat of_nat_Suc)
  5407   have cint: "\<And>x. \<lbrakk>x \<noteq> w; cmod (x - w) < d\<rbrakk>
  5408          \<Longrightarrow> (\<lambda>z. (f' z / (z - x) ^ k - f' z / (z - w) ^ k) / (x * k - w * k)) contour_integrable_on \<gamma>"
  5409     apply (rule contour_integrable_div [OF contour_integrable_diff])
  5410     using int w d
  5411     by (force simp: dist_norm norm_minus_commute intro!: has_contour_integral_integrable)+
  5412   have 1: "\<forall>\<^sub>F n in at w. (\<lambda>x. f' x * (inverse (x - n) ^ k - inverse (x - w) ^ k) / (n - w) / of_nat k)
  5413                          contour_integrable_on \<gamma>"
  5414     unfolding eventually_at
  5415     apply (rule_tac x=d in exI)
  5416     apply (simp add: \<open>d > 0\<close> dist_norm field_simps cint)
  5417     done
  5418   have bim_g: "bounded (image f' (path_image \<gamma>))"
  5419     by (simp add: compact_imp_bounded compact_continuous_image compact_valid_path_image assms)
  5420   then obtain C where "C > 0" and C: "\<And>x. \<lbrakk>0 \<le> x; x \<le> 1\<rbrakk> \<Longrightarrow> cmod (f' (\<gamma> x)) \<le> C"
  5421     by (force simp: bounded_pos path_image_def)
  5422   have twom: "\<forall>\<^sub>F n in at w.
  5423                \<forall>x\<in>path_image \<gamma>.
  5424                 cmod ((inverse (x - n) ^ k - inverse (x - w) ^ k) / (n - w) / k - inverse (x - w) ^ Suc k) < e"
  5425          if "0 < e" for e
  5426   proof -
  5427     have *: "cmod ((inverse (x - u) ^ k - inverse (x - w) ^ k) / ((u - w) * k) - inverse (x - w) ^ Suc k)   < e"
  5428             if x: "x \<in> path_image \<gamma>" and "u \<noteq> w" and uwd: "cmod (u - w) < d/2"
  5429                 and uw_less: "cmod (u - w) < e * (d/2) ^ (k+2) / (1 + real k)"
  5430             for u x
  5431     proof -
  5432       define ff where [abs_def]:
  5433         "ff n w =
  5434           (if n = 0 then inverse(x - w)^k
  5435            else if n = 1 then k / (x - w)^(Suc k)
  5436            else (k * of_real(Suc k)) / (x - w)^(k + 2))" for n :: nat and w
  5437       have km1: "\<And>z::complex. z \<noteq> 0 \<Longrightarrow> z ^ (k - Suc 0) = z ^ k / z"
  5438         by (simp add: field_simps) (metis Suc_pred \<open>k \<noteq> 0\<close> neq0_conv power_Suc)
  5439       have ff1: "(ff i has_field_derivative ff (Suc i) z) (at z within ball w (d/2))"
  5440               if "z \<in> ball w (d/2)" "i \<le> 1" for i z
  5441       proof -
  5442         have "z \<notin> path_image \<gamma>"
  5443           using \<open>x \<in> path_image \<gamma>\<close> d that ball_divide_subset_numeral by blast
  5444         then have xz[simp]: "x \<noteq> z" using \<open>x \<in> path_image \<gamma>\<close> by blast
  5445         then have neq: "x * x + z * z \<noteq> x * (z * 2)"
  5446           by (blast intro: dest!: sum_sqs_eq)
  5447         with xz have "\<And>v. v \<noteq> 0 \<Longrightarrow> (x * x + z * z) * v \<noteq> (x * (z * 2) * v)" by auto
  5448         then have neqq: "\<And>v. v \<noteq> 0 \<Longrightarrow> x * (x * v) + z * (z * v) \<noteq> x * (z * (2 * v))"
  5449           by (simp add: algebra_simps)
  5450         show ?thesis using \<open>i \<le> 1\<close>
  5451           apply (simp add: ff_def dist_norm Nat.le_Suc_eq km1, safe)
  5452           apply (rule derivative_eq_intros | simp add: km1 | simp add: field_simps neq neqq)+
  5453           done
  5454       qed
  5455       { fix a::real and b::real assume ab: "a > 0" "b > 0"
  5456         then have "k * (1 + real k) * (1 / a) \<le> k * (1 + real k) * (4 / b) \<longleftrightarrow> b \<le> 4 * a"
  5457           by (subst mult_le_cancel_left_pos) (use \<open>k \<noteq> 0\<close> in \<open>auto simp: divide_simps\<close>)
  5458         with ab have "real k * (1 + real k) / a \<le> (real k * 4 + real k * real k * 4) / b \<longleftrightarrow> b \<le> 4 * a"
  5459           by (simp add: field_simps)
  5460       } note canc = this
  5461       have ff2: "cmod (ff (Suc 1) v) \<le> real (k * (k + 1)) / (d/2) ^ (k + 2)"
  5462                 if "v \<in> ball w (d/2)" for v
  5463       proof -
  5464         have lessd: "\<And>z. cmod (\<gamma> z - v) < d/2 \<Longrightarrow> cmod (w - \<gamma> z) < d"
  5465           by (metis that norm_minus_commute norm_triangle_half_r dist_norm mem_ball)
  5466         have "d/2 \<le> cmod (x - v)" using d x that
  5467           using lessd d x
  5468           by (auto simp add: dist_norm path_image_def ball_def not_less [symmetric] del: divide_const_simps)
  5469         then have "d \<le> cmod (x - v) * 2"
  5470           by (simp add: divide_simps)
  5471         then have dpow_le: "d ^ (k+2) \<le> (cmod (x - v) * 2) ^ (k+2)"
  5472           using \<open>0 < d\<close> order_less_imp_le power_mono by blast
  5473         have "x \<noteq> v" using that
  5474           using \<open>x \<in> path_image \<gamma>\<close> ball_divide_subset_numeral d by fastforce
  5475         then show ?thesis
  5476         using \<open>d > 0\<close> apply (simp add: ff_def norm_mult norm_divide norm_power dist_norm canc)
  5477         using dpow_le apply (simp add: algebra_simps divide_simps mult_less_0_iff)
  5478         done
  5479       qed
  5480       have ub: "u \<in> ball w (d/2)"
  5481         using uwd by (simp add: dist_commute dist_norm)
  5482       have "cmod (inverse (x - u) ^ k - (inverse (x - w) ^ k + of_nat k * (u - w) / ((x - w) * (x - w) ^ k)))
  5483                   \<le> (real k * 4 + real k * real k * 4) * (cmod (u - w) * cmod (u - w)) / (d * (d * (d/2) ^ k))"
  5484         using complex_taylor [OF _ ff1 ff2 _ ub, of w, simplified]
  5485         by (simp add: ff_def \<open>0 < d\<close>)
  5486       then have "cmod (inverse (x - u) ^ k - (inverse (x - w) ^ k + of_nat k * (u - w) / ((x - w) * (x - w) ^ k)))
  5487                   \<le> (cmod (u - w) * real k) * (1 + real k) * cmod (u - w) / (d/2) ^ (k+2)"
  5488         by (simp add: field_simps)
  5489       then have "cmod (inverse (x - u) ^ k - (inverse (x - w) ^ k + of_nat k * (u - w) / ((x - w) * (x - w) ^ k)))
  5490                  / (cmod (u - w) * real k)
  5491                   \<le> (1 + real k) * cmod (u - w) / (d/2) ^ (k+2)"
  5492         using \<open>k \<noteq> 0\<close> \<open>u \<noteq> w\<close> by (simp add: mult_ac zero_less_mult_iff pos_divide_le_eq)
  5493       also have "\<dots> < e"
  5494         using uw_less \<open>0 < d\<close> by (simp add: mult_ac divide_simps)
  5495       finally have e: "cmod (inverse (x-u)^k - (inverse (x-w)^k + of_nat k * (u-w) / ((x-w) * (x-w)^k)))
  5496                         / cmod ((u - w) * real k)   <   e"
  5497         by (simp add: norm_mult)
  5498       have "x \<noteq> u"
  5499         using uwd \<open>0 < d\<close> x d by (force simp: dist_norm ball_def norm_minus_commute)
  5500       show ?thesis
  5501         apply (rule le_less_trans [OF _ e])
  5502         using \<open>k \<noteq> 0\<close> \<open>x \<noteq> u\<close> \<open>u \<noteq> w\<close>
  5503         apply (simp add: field_simps norm_divide [symmetric])
  5504         done
  5505     qed
  5506     show ?thesis
  5507       unfolding eventually_at
  5508       apply (rule_tac x = "min (d/2) ((e*(d/2)^(k + 2))/(Suc k))" in exI)
  5509       apply (force simp: \<open>d > 0\<close> dist_norm that simp del: power_Suc intro: *)
  5510       done
  5511   qed
  5512   have 2: "uniform_limit (path_image \<gamma>) (\<lambda>n x. f' x * (inverse (x - n) ^ k - inverse (x - w) ^ k) / (n - w) / of_nat k) (\<lambda>x. f' x / (x - w) ^ Suc k) (at w)"
  5513     unfolding uniform_limit_iff dist_norm
  5514   proof clarify
  5515     fix e::real
  5516     assume "0 < e"
  5517     have *: "cmod (f' (\<gamma> x) * (inverse (\<gamma> x - u) ^ k - inverse (\<gamma> x - w) ^ k) / ((u - w) * k) -
  5518                         f' (\<gamma> x) / ((\<gamma> x - w) * (\<gamma> x - w) ^ k)) < e"
  5519               if ec: "cmod ((inverse (\<gamma> x - u) ^ k - inverse (\<gamma> x - w) ^ k) / ((u - w) * k) -
  5520                       inverse (\<gamma> x - w) * inverse (\<gamma> x - w) ^ k) < e / C"
  5521                  and x: "0 \<le> x" "x \<le> 1"
  5522               for u x
  5523     proof (cases "(f' (\<gamma> x)) = 0")
  5524       case True then show ?thesis by (simp add: \<open>0 < e\<close>)
  5525     next
  5526       case False
  5527       have "cmod (f' (\<gamma> x) * (inverse (\<gamma> x - u) ^ k - inverse (\<gamma> x - w) ^ k) / ((u - w) * k) -
  5528                         f' (\<gamma> x) / ((\<gamma> x - w) * (\<gamma> x - w) ^ k)) =
  5529             cmod (f' (\<gamma> x) * ((inverse (\<gamma> x - u) ^ k - inverse (\<gamma> x - w) ^ k) / ((u - w) * k) -
  5530                              inverse (\<gamma> x - w) * inverse (\<gamma> x - w) ^ k))"
  5531         by (simp add: field_simps)
  5532       also have "\<dots> = cmod (f' (\<gamma> x)) *
  5533                        cmod ((inverse (\<gamma> x - u) ^ k - inverse (\<gamma> x - w) ^ k) / ((u - w) * k) -
  5534                              inverse (\<gamma> x - w) * inverse (\<gamma> x - w) ^ k)"
  5535         by (simp add: norm_mult)
  5536       also have "\<dots> < cmod (f' (\<gamma> x)) * (e/C)"
  5537         using False mult_strict_left_mono [OF ec] by force
  5538       also have "\<dots> \<le> e" using C
  5539         by (metis False \<open>0 < e\<close> frac_le less_eq_real_def mult.commute pos_le_divide_eq x zero_less_norm_iff)
  5540       finally show ?thesis .
  5541     qed
  5542     show "\<forall>\<^sub>F n in at w.
  5543               \<forall>x\<in>path_image \<gamma>.
  5544                cmod (f' x * (inverse (x - n) ^ k - inverse (x - w) ^ k) / (n - w) / of_nat k - f' x / (x - w) ^ Suc k) < e"
  5545       using twom [OF divide_pos_pos [OF \<open>0 < e\<close> \<open>C > 0\<close>]]   unfolding path_image_def
  5546       by (force intro: * elim: eventually_mono)
  5547   qed
  5548   show "(\<lambda>u. f' u / (u - w) ^ (Suc k)) contour_integrable_on \<gamma>"
  5549     by (rule contour_integral_uniform_limit [OF 1 2 leB \<gamma>]) auto
  5550   have *: "(\<lambda>n. contour_integral \<gamma> (\<lambda>x. f' x * (inverse (x - n) ^ k - inverse (x - w) ^ k) / (n - w) / k))
  5551            \<midarrow>w\<rightarrow> contour_integral \<gamma> (\<lambda>u. f' u / (u - w) ^ (Suc k))"
  5552     by (rule contour_integral_uniform_limit [OF 1 2 leB \<gamma>]) auto
  5553   have **: "contour_integral \<gamma> (\<lambda>x. f' x * (inverse (x - u) ^ k - inverse (x - w) ^ k) / ((u - w) * k)) =
  5554               (f u - f w) / (u - w) / k"
  5555     if "dist u w < d" for u
  5556   proof -
  5557     have u: "u \<in> s - path_image \<gamma>"
  5558       by (metis subsetD d dist_commute mem_ball that)
  5559     show ?thesis
  5560       apply (rule contour_integral_unique)
  5561       apply (simp add: diff_divide_distrib algebra_simps)
  5562       apply (intro has_contour_integral_diff has_contour_integral_div)
  5563       using u w apply (simp_all add: field_simps int)
  5564       done
  5565   qed
  5566   show ?thes2
  5567     apply (simp add: has_field_derivative_iff del: power_Suc)
  5568     apply (rule Lim_transform_within [OF tendsto_mult_left [OF *] \<open>0 < d\<close> ])
  5569     apply (simp add: \<open>k \<noteq> 0\<close> **)
  5570     done
  5571 qed
  5572 
  5573 corollary Cauchy_next_derivative_circlepath:
  5574   assumes contf: "continuous_on (path_image (circlepath z r)) f"
  5575       and int: "\<And>w. w \<in> ball z r \<Longrightarrow> ((\<lambda>u. f u / (u - w)^k) has_contour_integral g w) (circlepath z r)"
  5576       and k: "k \<noteq> 0"
  5577       and w: "w \<in> ball z r"
  5578     shows "(\<lambda>u. f u / (u - w)^(Suc k)) contour_integrable_on (circlepath z r)"
  5579            (is "?thes1")
  5580       and "(g has_field_derivative (k * contour_integral (circlepath z r) (\<lambda>u. f u/(u - w)^(Suc k)))) (at w)"
  5581            (is "?thes2")
  5582 proof -
  5583   have "r > 0" using w
  5584     using ball_eq_empty by fastforce
  5585   have wim: "w \<in> ball z r - path_image (circlepath z r)"
  5586     using w by (auto simp: dist_norm)
  5587   show ?thes1 ?thes2
  5588     by (rule Cauchy_next_derivative [OF contf _ int k open_ball valid_path_circlepath wim, where B = "2 * pi * \<bar>r\<bar>"];
  5589         auto simp: vector_derivative_circlepath norm_mult)+
  5590 qed
  5591 
  5592 
  5593 text\<open> In particular, the first derivative formula.\<close>
  5594 
  5595 proposition Cauchy_derivative_integral_circlepath: