src/HOL/Deriv.thy
changeset 56381 0556204bc230
parent 56371 fb9ae0727548
child 56409 36489d77c484
equal deleted inserted replaced
56380:9bb2856cc845 56381:0556204bc230
    25 text {*
    25 text {*
    26   Usually the filter @{term F} is @{term "at x within s"}.  @{term "(f has_derivative D)
    26   Usually the filter @{term F} is @{term "at x within s"}.  @{term "(f has_derivative D)
    27   (at x within s)"} means: @{term D} is the derivative of function @{term f} at point @{term x}
    27   (at x within s)"} means: @{term D} is the derivative of function @{term f} at point @{term x}
    28   within the set @{term s}. Where @{term s} is used to express left or right sided derivatives. In
    28   within the set @{term s}. Where @{term s} is used to express left or right sided derivatives. In
    29   most cases @{term s} is either a variable or @{term UNIV}.
    29   most cases @{term s} is either a variable or @{term UNIV}.
       
    30 *}
       
    31 
       
    32 lemma has_derivative_eq_rhs: "(f has_derivative f') F \<Longrightarrow> f' = g' \<Longrightarrow> (f has_derivative g') F"
       
    33   by simp
       
    34 
       
    35 definition 
       
    36   has_field_derivative :: "('a::real_normed_field \<Rightarrow> 'a) \<Rightarrow> 'a \<Rightarrow> 'a filter \<Rightarrow> bool"
       
    37   (infix "(has'_field'_derivative)" 50)
       
    38 where
       
    39   "(f has_field_derivative D) F \<longleftrightarrow> (f has_derivative op * D) F"
       
    40 
       
    41 lemma DERIV_cong: "(f has_field_derivative X) F \<Longrightarrow> X = Y \<Longrightarrow> (f has_field_derivative Y) F"
       
    42   by simp
       
    43 
       
    44 definition
       
    45   has_vector_derivative :: "(real \<Rightarrow> 'b::real_normed_vector) \<Rightarrow> 'b \<Rightarrow> real filter \<Rightarrow> bool"
       
    46   (infix "has'_vector'_derivative" 50)
       
    47 where
       
    48   "(f has_vector_derivative f') net \<longleftrightarrow> (f has_derivative (\<lambda>x. x *\<^sub>R f')) net"
       
    49 
       
    50 lemma has_vector_derivative_eq_rhs: "(f has_vector_derivative X) F \<Longrightarrow> X = Y \<Longrightarrow> (f has_vector_derivative Y) F"
       
    51   by simp
       
    52 
       
    53 ML {*
       
    54 
       
    55 structure Derivative_Intros = Named_Thms
       
    56 (
       
    57   val name = @{binding derivative_intros}
       
    58   val description = "structural introduction rules for derivatives"
       
    59 )
       
    60 
       
    61 *}
       
    62 
       
    63 setup {*
       
    64   let
       
    65     val eq_thms = [@{thm has_derivative_eq_rhs}, @{thm DERIV_cong}, @{thm has_vector_derivative_eq_rhs}]
       
    66     fun eq_rule thm = get_first (try (fn eq_thm => eq_thm OF [thm])) eq_thms
       
    67   in
       
    68     Derivative_Intros.setup #>
       
    69     Global_Theory.add_thms_dynamic
       
    70       (@{binding derivative_eq_intros}, map_filter eq_rule o Derivative_Intros.get o Context.proof_of)
       
    71   end;
    30 *}
    72 *}
    31 
    73 
    32 text {*
    74 text {*
    33   The following syntax is only used as a legacy syntax.
    75   The following syntax is only used as a legacy syntax.
    34 *}
    76 *}
    36   FDERIV :: "('a::real_normed_vector \<Rightarrow> 'b::real_normed_vector) \<Rightarrow> 'a \<Rightarrow>  ('a \<Rightarrow> 'b) \<Rightarrow> bool"
    78   FDERIV :: "('a::real_normed_vector \<Rightarrow> 'b::real_normed_vector) \<Rightarrow> 'a \<Rightarrow>  ('a \<Rightarrow> 'b) \<Rightarrow> bool"
    37   ("(FDERIV (_)/ (_)/ :> (_))" [1000, 1000, 60] 60)
    79   ("(FDERIV (_)/ (_)/ :> (_))" [1000, 1000, 60] 60)
    38 where
    80 where
    39   "FDERIV f x :> f' \<equiv> (f has_derivative f') (at x)"
    81   "FDERIV f x :> f' \<equiv> (f has_derivative f') (at x)"
    40 
    82 
    41 
       
    42 lemma has_derivative_eq_rhs: "(f has_derivative f') F \<Longrightarrow> f' = g' \<Longrightarrow> (f has_derivative g') F"
       
    43   by simp
       
    44 
       
    45 ML {*
       
    46 
       
    47 structure has_derivative_Intros = Named_Thms
       
    48 (
       
    49   val name = @{binding has_derivative_intros}
       
    50   val description = "introduction rules for FDERIV"
       
    51 )
       
    52 
       
    53 *}
       
    54 
       
    55 setup {*
       
    56   has_derivative_Intros.setup #>
       
    57   Global_Theory.add_thms_dynamic (@{binding has_derivative_eq_intros},
       
    58     map_filter (try (fn thm => @{thm has_derivative_eq_rhs} OF [thm])) o has_derivative_Intros.get o Context.proof_of);
       
    59 *}
       
    60 
       
    61 lemma has_derivative_bounded_linear: "(f has_derivative f') F \<Longrightarrow> bounded_linear f'"
    83 lemma has_derivative_bounded_linear: "(f has_derivative f') F \<Longrightarrow> bounded_linear f'"
    62   by (simp add: has_derivative_def)
    84   by (simp add: has_derivative_def)
    63 
    85 
    64 lemma has_derivative_linear: "(f has_derivative f') F \<Longrightarrow> linear f'"
    86 lemma has_derivative_linear: "(f has_derivative f') F \<Longrightarrow> linear f'"
    65   using bounded_linear.linear[OF has_derivative_bounded_linear] .
    87   using bounded_linear.linear[OF has_derivative_bounded_linear] .
    66 
    88 
    67 lemma has_derivative_ident[has_derivative_intros, simp]: "((\<lambda>x. x) has_derivative (\<lambda>x. x)) F"
    89 lemma has_derivative_ident[derivative_intros, simp]: "((\<lambda>x. x) has_derivative (\<lambda>x. x)) F"
    68   by (simp add: has_derivative_def tendsto_const)
    90   by (simp add: has_derivative_def tendsto_const)
    69 
    91 
    70 lemma has_derivative_const[has_derivative_intros, simp]: "((\<lambda>x. c) has_derivative (\<lambda>x. 0)) F"
    92 lemma has_derivative_const[derivative_intros, simp]: "((\<lambda>x. c) has_derivative (\<lambda>x. 0)) F"
    71   by (simp add: has_derivative_def tendsto_const)
    93   by (simp add: has_derivative_def tendsto_const)
    72 
    94 
    73 lemma (in bounded_linear) bounded_linear: "bounded_linear f" ..
    95 lemma (in bounded_linear) bounded_linear: "bounded_linear f" ..
    74 
    96 
    75 lemma (in bounded_linear) has_derivative:
    97 lemma (in bounded_linear) has_derivative:
    79   apply (erule bounded_linear_compose [OF bounded_linear])
   101   apply (erule bounded_linear_compose [OF bounded_linear])
    80   apply (drule tendsto)
   102   apply (drule tendsto)
    81   apply (simp add: scaleR diff add zero)
   103   apply (simp add: scaleR diff add zero)
    82   done
   104   done
    83 
   105 
    84 lemmas has_derivative_scaleR_right [has_derivative_intros] =
   106 lemmas has_derivative_scaleR_right [derivative_intros] =
    85   bounded_linear.has_derivative [OF bounded_linear_scaleR_right]
   107   bounded_linear.has_derivative [OF bounded_linear_scaleR_right]
    86 
   108 
    87 lemmas has_derivative_scaleR_left [has_derivative_intros] =
   109 lemmas has_derivative_scaleR_left [derivative_intros] =
    88   bounded_linear.has_derivative [OF bounded_linear_scaleR_left]
   110   bounded_linear.has_derivative [OF bounded_linear_scaleR_left]
    89 
   111 
    90 lemmas has_derivative_mult_right [has_derivative_intros] =
   112 lemmas has_derivative_mult_right [derivative_intros] =
    91   bounded_linear.has_derivative [OF bounded_linear_mult_right]
   113   bounded_linear.has_derivative [OF bounded_linear_mult_right]
    92 
   114 
    93 lemmas has_derivative_mult_left [has_derivative_intros] =
   115 lemmas has_derivative_mult_left [derivative_intros] =
    94   bounded_linear.has_derivative [OF bounded_linear_mult_left]
   116   bounded_linear.has_derivative [OF bounded_linear_mult_left]
    95 
   117 
    96 lemma has_derivative_add[simp, has_derivative_intros]:
   118 lemma has_derivative_add[simp, derivative_intros]:
    97   assumes f: "(f has_derivative f') F" and g: "(g has_derivative g') F"
   119   assumes f: "(f has_derivative f') F" and g: "(g has_derivative g') F"
    98   shows "((\<lambda>x. f x + g x) has_derivative (\<lambda>x. f' x + g' x)) F"
   120   shows "((\<lambda>x. f x + g x) has_derivative (\<lambda>x. f' x + g' x)) F"
    99   unfolding has_derivative_def
   121   unfolding has_derivative_def
   100 proof safe
   122 proof safe
   101   let ?x = "Lim F (\<lambda>x. x)"
   123   let ?x = "Lim F (\<lambda>x. x)"
   104     using f g by (intro tendsto_add) (auto simp: has_derivative_def)
   126     using f g by (intro tendsto_add) (auto simp: has_derivative_def)
   105   then show "(?D (\<lambda>x. f x + g x) (\<lambda>x. f' x + g' x) ---> 0) F"
   127   then show "(?D (\<lambda>x. f x + g x) (\<lambda>x. f' x + g' x) ---> 0) F"
   106     by (simp add: field_simps scaleR_add_right scaleR_diff_right)
   128     by (simp add: field_simps scaleR_add_right scaleR_diff_right)
   107 qed (blast intro: bounded_linear_add f g has_derivative_bounded_linear)
   129 qed (blast intro: bounded_linear_add f g has_derivative_bounded_linear)
   108 
   130 
   109 lemma has_derivative_setsum[simp, has_derivative_intros]:
   131 lemma has_derivative_setsum[simp, derivative_intros]:
   110   assumes f: "\<And>i. i \<in> I \<Longrightarrow> (f i has_derivative f' i) F"
   132   assumes f: "\<And>i. i \<in> I \<Longrightarrow> (f i has_derivative f' i) F"
   111   shows "((\<lambda>x. \<Sum>i\<in>I. f i x) has_derivative (\<lambda>x. \<Sum>i\<in>I. f' i x)) F"
   133   shows "((\<lambda>x. \<Sum>i\<in>I. f i x) has_derivative (\<lambda>x. \<Sum>i\<in>I. f' i x)) F"
   112 proof cases
   134 proof cases
   113   assume "finite I" from this f show ?thesis
   135   assume "finite I" from this f show ?thesis
   114     by induct (simp_all add: f)
   136     by induct (simp_all add: f)
   115 qed simp
   137 qed simp
   116 
   138 
   117 lemma has_derivative_minus[simp, has_derivative_intros]: "(f has_derivative f') F \<Longrightarrow> ((\<lambda>x. - f x) has_derivative (\<lambda>x. - f' x)) F"
   139 lemma has_derivative_minus[simp, derivative_intros]: "(f has_derivative f') F \<Longrightarrow> ((\<lambda>x. - f x) has_derivative (\<lambda>x. - f' x)) F"
   118   using has_derivative_scaleR_right[of f f' F "-1"] by simp
   140   using has_derivative_scaleR_right[of f f' F "-1"] by simp
   119 
   141 
   120 lemma has_derivative_diff[simp, has_derivative_intros]:
   142 lemma has_derivative_diff[simp, derivative_intros]:
   121   "(f has_derivative f') F \<Longrightarrow> (g has_derivative g') F \<Longrightarrow> ((\<lambda>x. f x - g x) has_derivative (\<lambda>x. f' x - g' x)) F"
   143   "(f has_derivative f') F \<Longrightarrow> (g has_derivative g') F \<Longrightarrow> ((\<lambda>x. f x - g x) has_derivative (\<lambda>x. f' x - g' x)) F"
   122   by (simp only: diff_conv_add_uminus has_derivative_add has_derivative_minus)
   144   by (simp only: diff_conv_add_uminus has_derivative_add has_derivative_minus)
   123 
   145 
   124 lemma has_derivative_at_within:
   146 lemma has_derivative_at_within:
   125   "(f has_derivative f') (at x within s) \<longleftrightarrow>
   147   "(f has_derivative f') (at x within s) \<longleftrightarrow>
   318       by (simp add: add_divide_distrib Ng_def Nf_def)
   340       by (simp add: add_divide_distrib Ng_def Nf_def)
   319     finally show "?fun1 y \<le> ?fun2 y" .
   341     finally show "?fun1 y \<le> ?fun2 y" .
   320   qed simp
   342   qed simp
   321 qed
   343 qed
   322 
   344 
   323 lemmas has_derivative_mult[simp, has_derivative_intros] = bounded_bilinear.FDERIV[OF bounded_bilinear_mult]
   345 lemmas has_derivative_mult[simp, derivative_intros] = bounded_bilinear.FDERIV[OF bounded_bilinear_mult]
   324 lemmas has_derivative_scaleR[simp, has_derivative_intros] = bounded_bilinear.FDERIV[OF bounded_bilinear_scaleR]
   346 lemmas has_derivative_scaleR[simp, derivative_intros] = bounded_bilinear.FDERIV[OF bounded_bilinear_scaleR]
   325 
   347 
   326 lemma has_derivative_setprod[simp, has_derivative_intros]:
   348 lemma has_derivative_setprod[simp, derivative_intros]:
   327   fixes f :: "'i \<Rightarrow> 'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   349   fixes f :: "'i \<Rightarrow> 'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   328   assumes f: "\<And>i. i \<in> I \<Longrightarrow> (f i has_derivative f' i) (at x within s)"
   350   assumes f: "\<And>i. i \<in> I \<Longrightarrow> (f i has_derivative f' i) (at x within s)"
   329   shows "((\<lambda>x. \<Prod>i\<in>I. f i x) has_derivative (\<lambda>y. \<Sum>i\<in>I. f' i y * (\<Prod>j\<in>I - {i}. f j x))) (at x within s)"
   351   shows "((\<lambda>x. \<Prod>i\<in>I. f i x) has_derivative (\<lambda>y. \<Sum>i\<in>I. f' i y * (\<Prod>j\<in>I - {i}. f j x))) (at x within s)"
   330 proof cases
   352 proof cases
   331   assume "finite I" from this f show ?thesis
   353   assume "finite I" from this f show ?thesis
   339     finally show ?case
   361     finally show ?case
   340       using insert by simp
   362       using insert by simp
   341   qed simp  
   363   qed simp  
   342 qed simp
   364 qed simp
   343 
   365 
   344 lemma has_derivative_power[simp, has_derivative_intros]:
   366 lemma has_derivative_power[simp, derivative_intros]:
   345   fixes f :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   367   fixes f :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   346   assumes f: "(f has_derivative f') (at x within s)"
   368   assumes f: "(f has_derivative f') (at x within s)"
   347   shows "((\<lambda>x. f x^n) has_derivative (\<lambda>y. of_nat n * f' y * f x^(n - 1))) (at x within s)"
   369   shows "((\<lambda>x. f x^n) has_derivative (\<lambda>y. of_nat n * f' y * f x^(n - 1))) (at x within s)"
   348   using has_derivative_setprod[OF f, of "{..< n}"] by (simp add: setprod_constant ac_simps)
   370   using has_derivative_setprod[OF f, of "{..< n}"] by (simp add: setprod_constant ac_simps)
   349 
   371 
   390     by simp
   412     by simp
   391   finally show "norm (?inv y - ?inv x - ?f (y -x)) / norm (y - x) \<le>
   413   finally show "norm (?inv y - ?inv x - ?f (y -x)) / norm (y - x) \<le>
   392       norm (?inv y - ?inv x) * norm (?inv x)" .
   414       norm (?inv y - ?inv x) * norm (?inv x)" .
   393 qed
   415 qed
   394 
   416 
   395 lemma has_derivative_inverse[simp, has_derivative_intros]:
   417 lemma has_derivative_inverse[simp, derivative_intros]:
   396   fixes f :: "_ \<Rightarrow> 'a::real_normed_div_algebra"
   418   fixes f :: "_ \<Rightarrow> 'a::real_normed_div_algebra"
   397   assumes x:  "f x \<noteq> 0" and f: "(f has_derivative f') (at x within s)"
   419   assumes x:  "f x \<noteq> 0" and f: "(f has_derivative f') (at x within s)"
   398   shows "((\<lambda>x. inverse (f x)) has_derivative (\<lambda>h. - (inverse (f x) * f' h * inverse (f x)))) (at x within s)"
   420   shows "((\<lambda>x. inverse (f x)) has_derivative (\<lambda>h. - (inverse (f x) * f' h * inverse (f x)))) (at x within s)"
   399   using has_derivative_compose[OF f has_derivative_inverse', OF x] .
   421   using has_derivative_compose[OF f has_derivative_inverse', OF x] .
   400 
   422 
   401 lemma has_derivative_divide[simp, has_derivative_intros]:
   423 lemma has_derivative_divide[simp, derivative_intros]:
   402   fixes f :: "_ \<Rightarrow> 'a::real_normed_div_algebra"
   424   fixes f :: "_ \<Rightarrow> 'a::real_normed_div_algebra"
   403   assumes f: "(f has_derivative f') (at x within s)" and g: "(g has_derivative g') (at x within s)" 
   425   assumes f: "(f has_derivative f') (at x within s)" and g: "(g has_derivative g') (at x within s)" 
   404   assumes x: "g x \<noteq> 0"
   426   assumes x: "g x \<noteq> 0"
   405   shows "((\<lambda>x. f x / g x) has_derivative
   427   shows "((\<lambda>x. f x / g x) has_derivative
   406                 (\<lambda>h. - f x * (inverse (g x) * g' h * inverse (g x)) + f' h / g x)) (at x within s)"
   428                 (\<lambda>h. - f x * (inverse (g x) * g' h * inverse (g x)) + f' h / g x)) (at x within s)"
   407   using has_derivative_mult[OF f has_derivative_inverse[OF x g]]
   429   using has_derivative_mult[OF f has_derivative_inverse[OF x g]]
   408   by (simp add: divide_inverse field_simps)
   430   by (simp add: divide_inverse field_simps)
   409 
   431 
   410 text{*Conventional form requires mult-AC laws. Types real and complex only.*}
   432 text{*Conventional form requires mult-AC laws. Types real and complex only.*}
   411 
   433 
   412 lemma has_derivative_divide'[has_derivative_intros]: 
   434 lemma has_derivative_divide'[derivative_intros]: 
   413   fixes f :: "_ \<Rightarrow> 'a::real_normed_field"
   435   fixes f :: "_ \<Rightarrow> 'a::real_normed_field"
   414   assumes f: "(f has_derivative f') (at x within s)" and g: "(g has_derivative g') (at x within s)" and x: "g x \<noteq> 0"
   436   assumes f: "(f has_derivative f') (at x within s)" and g: "(g has_derivative g') (at x within s)" and x: "g x \<noteq> 0"
   415   shows "((\<lambda>x. f x / g x) has_derivative (\<lambda>h. (f' h * g x - f x * g' h) / (g x * g x))) (at x within s)"
   437   shows "((\<lambda>x. f x / g x) has_derivative (\<lambda>h. (f' h * g x - f x * g' h) / (g x * g x))) (at x within s)"
   416 proof -
   438 proof -
   417   { fix h
   439   { fix h
   483 lemma differentiable_subset: "f differentiable (at x within s) \<Longrightarrow> t \<subseteq> s \<Longrightarrow> f differentiable (at x within t)"
   505 lemma differentiable_subset: "f differentiable (at x within s) \<Longrightarrow> t \<subseteq> s \<Longrightarrow> f differentiable (at x within t)"
   484   unfolding differentiable_def by (blast intro: has_derivative_subset)
   506   unfolding differentiable_def by (blast intro: has_derivative_subset)
   485 
   507 
   486 lemmas differentiable_within_subset = differentiable_subset
   508 lemmas differentiable_within_subset = differentiable_subset
   487 
   509 
   488 lemma differentiable_ident [simp]: "(\<lambda>x. x) differentiable F"
   510 lemma differentiable_ident [simp, derivative_intros]: "(\<lambda>x. x) differentiable F"
   489   unfolding differentiable_def by (blast intro: has_derivative_ident)
   511   unfolding differentiable_def by (blast intro: has_derivative_ident)
   490 
   512 
   491 lemma differentiable_const [simp]: "(\<lambda>z. a) differentiable F"
   513 lemma differentiable_const [simp, derivative_intros]: "(\<lambda>z. a) differentiable F"
   492   unfolding differentiable_def by (blast intro: has_derivative_const)
   514   unfolding differentiable_def by (blast intro: has_derivative_const)
   493 
   515 
   494 lemma differentiable_in_compose:
   516 lemma differentiable_in_compose:
   495   "f differentiable (at (g x) within (g`s)) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f (g x)) differentiable (at x within s)"
   517   "f differentiable (at (g x) within (g`s)) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f (g x)) differentiable (at x within s)"
   496   unfolding differentiable_def by (blast intro: has_derivative_in_compose)
   518   unfolding differentiable_def by (blast intro: has_derivative_in_compose)
   497 
   519 
   498 lemma differentiable_compose:
   520 lemma differentiable_compose:
   499   "f differentiable (at (g x)) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f (g x)) differentiable (at x within s)"
   521   "f differentiable (at (g x)) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f (g x)) differentiable (at x within s)"
   500   by (blast intro: differentiable_in_compose differentiable_subset)
   522   by (blast intro: differentiable_in_compose differentiable_subset)
   501 
   523 
   502 lemma differentiable_sum [simp]:
   524 lemma differentiable_sum [simp, derivative_intros]:
   503   "f differentiable F \<Longrightarrow> g differentiable F \<Longrightarrow> (\<lambda>x. f x + g x) differentiable F"
   525   "f differentiable F \<Longrightarrow> g differentiable F \<Longrightarrow> (\<lambda>x. f x + g x) differentiable F"
   504   unfolding differentiable_def by (blast intro: has_derivative_add)
   526   unfolding differentiable_def by (blast intro: has_derivative_add)
   505 
   527 
   506 lemma differentiable_minus [simp]:
   528 lemma differentiable_minus [simp, derivative_intros]:
   507   "f differentiable F \<Longrightarrow> (\<lambda>x. - f x) differentiable F"
   529   "f differentiable F \<Longrightarrow> (\<lambda>x. - f x) differentiable F"
   508   unfolding differentiable_def by (blast intro: has_derivative_minus)
   530   unfolding differentiable_def by (blast intro: has_derivative_minus)
   509 
   531 
   510 lemma differentiable_diff [simp]:
   532 lemma differentiable_diff [simp, derivative_intros]:
   511   "f differentiable F \<Longrightarrow> g differentiable F \<Longrightarrow> (\<lambda>x. f x - g x) differentiable F"
   533   "f differentiable F \<Longrightarrow> g differentiable F \<Longrightarrow> (\<lambda>x. f x - g x) differentiable F"
   512   unfolding differentiable_def by (blast intro: has_derivative_diff)
   534   unfolding differentiable_def by (blast intro: has_derivative_diff)
   513 
   535 
   514 lemma differentiable_mult [simp]:
   536 lemma differentiable_mult [simp, derivative_intros]:
   515   fixes f g :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_algebra"
   537   fixes f g :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_algebra"
   516   shows "f differentiable (at x within s) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f x * g x) differentiable (at x within s)"
   538   shows "f differentiable (at x within s) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f x * g x) differentiable (at x within s)"
   517   unfolding differentiable_def by (blast intro: has_derivative_mult)
   539   unfolding differentiable_def by (blast intro: has_derivative_mult)
   518 
   540 
   519 lemma differentiable_inverse [simp]:
   541 lemma differentiable_inverse [simp, derivative_intros]:
   520   fixes f :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   542   fixes f :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   521   shows "f differentiable (at x within s) \<Longrightarrow> f x \<noteq> 0 \<Longrightarrow> (\<lambda>x. inverse (f x)) differentiable (at x within s)"
   543   shows "f differentiable (at x within s) \<Longrightarrow> f x \<noteq> 0 \<Longrightarrow> (\<lambda>x. inverse (f x)) differentiable (at x within s)"
   522   unfolding differentiable_def by (blast intro: has_derivative_inverse)
   544   unfolding differentiable_def by (blast intro: has_derivative_inverse)
   523 
   545 
   524 lemma differentiable_divide [simp]:
   546 lemma differentiable_divide [simp, derivative_intros]:
   525   fixes f g :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   547   fixes f g :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   526   shows "f differentiable (at x within s) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> g x \<noteq> 0 \<Longrightarrow> (\<lambda>x. f x / g x) differentiable (at x within s)"
   548   shows "f differentiable (at x within s) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> g x \<noteq> 0 \<Longrightarrow> (\<lambda>x. f x / g x) differentiable (at x within s)"
   527   unfolding divide_inverse using assms by simp
   549   unfolding divide_inverse using assms by simp
   528 
   550 
   529 lemma differentiable_power [simp]:
   551 lemma differentiable_power [simp, derivative_intros]:
   530   fixes f g :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   552   fixes f g :: "'a :: real_normed_vector \<Rightarrow> 'b :: real_normed_field"
   531   shows "f differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f x ^ n) differentiable (at x within s)"
   553   shows "f differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f x ^ n) differentiable (at x within s)"
   532   unfolding differentiable_def by (blast intro: has_derivative_power)
   554   unfolding differentiable_def by (blast intro: has_derivative_power)
   533 
   555 
   534 lemma differentiable_scaleR [simp]:
   556 lemma differentiable_scaleR [simp, derivative_intros]:
   535   "f differentiable (at x within s) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f x *\<^sub>R g x) differentiable (at x within s)"
   557   "f differentiable (at x within s) \<Longrightarrow> g differentiable (at x within s) \<Longrightarrow> (\<lambda>x. f x *\<^sub>R g x) differentiable (at x within s)"
   536   unfolding differentiable_def by (blast intro: has_derivative_scaleR)
   558   unfolding differentiable_def by (blast intro: has_derivative_scaleR)
   537 
       
   538 definition 
       
   539   has_field_derivative :: "('a::real_normed_field \<Rightarrow> 'a) \<Rightarrow> 'a \<Rightarrow> 'a filter \<Rightarrow> bool"
       
   540   (infix "(has'_field'_derivative)" 50)
       
   541 where
       
   542   "(f has_field_derivative D) F \<longleftrightarrow> (f has_derivative op * D) F"
       
   543 
   559 
   544 lemma has_derivative_imp_has_field_derivative:
   560 lemma has_derivative_imp_has_field_derivative:
   545   "(f has_derivative D) F \<Longrightarrow> (\<And>x. x * D' = D x) \<Longrightarrow> (f has_field_derivative D') F"
   561   "(f has_derivative D) F \<Longrightarrow> (\<And>x. x * D' = D x) \<Longrightarrow> (f has_field_derivative D') F"
   546   unfolding has_field_derivative_def 
   562   unfolding has_field_derivative_def 
   547   by (rule has_derivative_eq_rhs[of f D]) (simp_all add: fun_eq_iff mult_commute)
   563   by (rule has_derivative_eq_rhs[of f D]) (simp_all add: fun_eq_iff mult_commute)
   553   "(f has_field_derivative f') (at x within s) \<Longrightarrow> t \<subseteq> s 
   569   "(f has_field_derivative f') (at x within s) \<Longrightarrow> t \<subseteq> s 
   554    \<Longrightarrow> (f has_field_derivative f') (at x within t)"
   570    \<Longrightarrow> (f has_field_derivative f') (at x within t)"
   555   by (simp add: has_field_derivative_def has_derivative_within_subset)
   571   by (simp add: has_field_derivative_def has_derivative_within_subset)
   556 
   572 
   557 abbreviation (input)
   573 abbreviation (input)
   558   deriv :: "('a::real_normed_field \<Rightarrow> 'a) \<Rightarrow> 'a \<Rightarrow> 'a \<Rightarrow> bool"
   574   DERIV :: "('a::real_normed_field \<Rightarrow> 'a) \<Rightarrow> 'a \<Rightarrow> 'a \<Rightarrow> bool"
   559   ("(DERIV (_)/ (_)/ :> (_))" [1000, 1000, 60] 60)
   575   ("(DERIV (_)/ (_)/ :> (_))" [1000, 1000, 60] 60)
   560 where
   576 where
   561   "DERIV f x :> D \<equiv> (f has_field_derivative D) (at x)"
   577   "DERIV f x :> D \<equiv> (f has_field_derivative D) (at x)"
   562 
   578 
   563 abbreviation 
   579 abbreviation 
   586   by (auto elim: real_differentiableE)
   602   by (auto elim: real_differentiableE)
   587 
   603 
   588 lemma differentiableI: "(f has_real_derivative D) (at x within s) \<Longrightarrow> f differentiable (at x within s)"
   604 lemma differentiableI: "(f has_real_derivative D) (at x within s) \<Longrightarrow> f differentiable (at x within s)"
   589   by (force simp add: real_differentiable_def)
   605   by (force simp add: real_differentiable_def)
   590 
   606 
   591 lemma deriv_def:
   607 lemma DERIV_def: "DERIV f x :> D \<longleftrightarrow> (\<lambda>h. (f (x + h) - f x) / h) -- 0 --> D"
   592   "DERIV f x :> D \<longleftrightarrow> (\<lambda>h. (f (x + h) - f x) / h) -- 0 --> D"
       
   593   apply (simp add: has_field_derivative_def has_derivative_at bounded_linear_mult_right LIM_zero_iff[symmetric, of _ D])
   608   apply (simp add: has_field_derivative_def has_derivative_at bounded_linear_mult_right LIM_zero_iff[symmetric, of _ D])
   594   apply (subst (2) tendsto_norm_zero_iff[symmetric])
   609   apply (subst (2) tendsto_norm_zero_iff[symmetric])
   595   apply (rule filterlim_cong)
   610   apply (rule filterlim_cong)
   596   apply (simp_all add: eventually_at_filter field_simps nonzero_norm_divide)
   611   apply (simp_all add: eventually_at_filter field_simps nonzero_norm_divide)
   597   done
   612   done
   600   by (simp add: fun_eq_iff mult_commute)
   615   by (simp add: fun_eq_iff mult_commute)
   601 
   616 
   602 subsection {* Derivatives *}
   617 subsection {* Derivatives *}
   603 
   618 
   604 lemma DERIV_D: "DERIV f x :> D \<Longrightarrow> (\<lambda>h. (f (x + h) - f x) / h) -- 0 --> D"
   619 lemma DERIV_D: "DERIV f x :> D \<Longrightarrow> (\<lambda>h. (f (x + h) - f x) / h) -- 0 --> D"
   605   by (simp add: deriv_def)
   620   by (simp add: DERIV_def)
   606 
   621 
   607 lemma DERIV_const [simp]: "((\<lambda>x. k) has_field_derivative 0) (at x within s)"
   622 lemma DERIV_const [simp, derivative_intros]: "((\<lambda>x. k) has_field_derivative 0) F"
   608   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_const]) auto
   623   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_const]) auto
   609 
   624 
   610 lemma DERIV_ident [simp]: "((\<lambda>x. x) has_field_derivative 1) (at x within s)"
   625 lemma DERIV_ident [simp, derivative_intros]: "((\<lambda>x. x) has_field_derivative 1) F"
   611   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_ident]) auto
   626   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_ident]) auto
   612 
   627 
   613 lemma field_differentiable_add:
   628 lemma field_differentiable_add[derivative_intros]:
   614   assumes "(f has_field_derivative f') F" "(g has_field_derivative g') F"
   629   "(f has_field_derivative f') F \<Longrightarrow> (g has_field_derivative g') F \<Longrightarrow> 
   615     shows "((\<lambda>z. f z + g z) has_field_derivative f' + g') F"
   630     ((\<lambda>z. f z + g z) has_field_derivative f' + g') F"
   616   apply (rule has_derivative_imp_has_field_derivative[OF has_derivative_add])
   631   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_add])
   617   using assms 
   632      (auto simp: has_field_derivative_def field_simps mult_commute_abs)
   618   by (auto simp: has_field_derivative_def field_simps mult_commute_abs)
       
   619 
   633 
   620 corollary DERIV_add:
   634 corollary DERIV_add:
   621   "(f has_field_derivative D) (at x within s) \<Longrightarrow> (g has_field_derivative E) (at x within s) \<Longrightarrow>
   635   "(f has_field_derivative D) (at x within s) \<Longrightarrow> (g has_field_derivative E) (at x within s) \<Longrightarrow>
   622   ((\<lambda>x. f x + g x) has_field_derivative D + E) (at x within s)"
   636   ((\<lambda>x. f x + g x) has_field_derivative D + E) (at x within s)"
   623   by (rule field_differentiable_add)
   637   by (rule field_differentiable_add)
   624 
   638 
   625 lemma field_differentiable_minus:
   639 lemma field_differentiable_minus[derivative_intros]:
   626   assumes "(f has_field_derivative f') F" 
   640   "(f has_field_derivative f') F \<Longrightarrow> ((\<lambda>z. - (f z)) has_field_derivative -f') F"
   627     shows "((\<lambda>z. - (f z)) has_field_derivative -f') F"
   641   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_minus])
   628   apply (rule has_derivative_imp_has_field_derivative[OF has_derivative_minus])
   642      (auto simp: has_field_derivative_def field_simps mult_commute_abs)
   629   using assms 
       
   630   by (auto simp: has_field_derivative_def field_simps mult_commute_abs)
       
   631 
   643 
   632 corollary DERIV_minus: "(f has_field_derivative D) (at x within s) \<Longrightarrow> ((\<lambda>x. - f x) has_field_derivative -D) (at x within s)"
   644 corollary DERIV_minus: "(f has_field_derivative D) (at x within s) \<Longrightarrow> ((\<lambda>x. - f x) has_field_derivative -D) (at x within s)"
   633   by (rule field_differentiable_minus)
   645   by (rule field_differentiable_minus)
   634 
   646 
   635 lemma field_differentiable_diff:
   647 lemma field_differentiable_diff[derivative_intros]:
   636   assumes "(f has_field_derivative f') F" "(g has_field_derivative g') F"
   648   "(f has_field_derivative f') F \<Longrightarrow> (g has_field_derivative g') F \<Longrightarrow> ((\<lambda>z. f z - g z) has_field_derivative f' - g') F"
   637     shows "((\<lambda>z. f z - g z) has_field_derivative f' - g') F"
   649   by (simp only: assms diff_conv_add_uminus field_differentiable_add field_differentiable_minus)
   638 by (simp only: assms diff_conv_add_uminus field_differentiable_add field_differentiable_minus)
       
   639 
   650 
   640 corollary DERIV_diff:
   651 corollary DERIV_diff:
   641   "(f has_field_derivative D) (at x within s) \<Longrightarrow> (g has_field_derivative E) (at x within s) \<Longrightarrow>
   652   "(f has_field_derivative D) (at x within s) \<Longrightarrow> (g has_field_derivative E) (at x within s) \<Longrightarrow>
   642   ((\<lambda>x. f x - g x) has_field_derivative D - E) (at x within s)"
   653   ((\<lambda>x. f x - g x) has_field_derivative D - E) (at x within s)"
   643   by (rule field_differentiable_diff)
   654   by (rule field_differentiable_diff)
   656   "(f has_field_derivative D) (at x within s) \<Longrightarrow> (g has_field_derivative E) (at x within s) \<Longrightarrow>
   667   "(f has_field_derivative D) (at x within s) \<Longrightarrow> (g has_field_derivative E) (at x within s) \<Longrightarrow>
   657   ((\<lambda>x. f x * g x) has_field_derivative f x * E + D * g x) (at x within s)"
   668   ((\<lambda>x. f x * g x) has_field_derivative f x * E + D * g x) (at x within s)"
   658   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_mult])
   669   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_mult])
   659      (auto simp: field_simps mult_commute_abs dest: has_field_derivative_imp_has_derivative)
   670      (auto simp: field_simps mult_commute_abs dest: has_field_derivative_imp_has_derivative)
   660 
   671 
   661 lemma DERIV_mult:
   672 lemma DERIV_mult[derivative_intros]:
   662   "(f has_field_derivative Da) (at x within s) \<Longrightarrow> (g has_field_derivative Db) (at x within s) \<Longrightarrow>
   673   "(f has_field_derivative Da) (at x within s) \<Longrightarrow> (g has_field_derivative Db) (at x within s) \<Longrightarrow>
   663   ((\<lambda>x. f x * g x) has_field_derivative Da * g x + Db * f x) (at x within s)"
   674   ((\<lambda>x. f x * g x) has_field_derivative Da * g x + Db * f x) (at x within s)"
   664   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_mult])
   675   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_mult])
   665      (auto simp: field_simps dest: has_field_derivative_imp_has_derivative)
   676      (auto simp: field_simps dest: has_field_derivative_imp_has_derivative)
   666 
   677 
   670   "(f has_field_derivative D) (at x within s) ==> ((\<lambda>x. c * f x) has_field_derivative c * D) (at x within s)"
   681   "(f has_field_derivative D) (at x within s) ==> ((\<lambda>x. c * f x) has_field_derivative c * D) (at x within s)"
   671   by (drule DERIV_mult' [OF DERIV_const], simp)
   682   by (drule DERIV_mult' [OF DERIV_const], simp)
   672 
   683 
   673 lemma DERIV_cmult_right:
   684 lemma DERIV_cmult_right:
   674   "(f has_field_derivative D) (at x within s) ==> ((\<lambda>x. f x * c) has_field_derivative D * c) (at x within s)"
   685   "(f has_field_derivative D) (at x within s) ==> ((\<lambda>x. f x * c) has_field_derivative D * c) (at x within s)"
   675   using DERIV_cmult   by (force simp add: mult_ac)
   686   using DERIV_cmult by (force simp add: mult_ac)
   676 
   687 
   677 lemma DERIV_cmult_Id [simp]: "(op * c has_field_derivative c) (at x within s)"
   688 lemma DERIV_cmult_Id [simp]: "(op * c has_field_derivative c) (at x within s)"
   678   by (cut_tac c = c and x = x in DERIV_ident [THEN DERIV_cmult], simp)
   689   by (cut_tac c = c and x = x in DERIV_ident [THEN DERIV_cmult], simp)
   679 
   690 
   680 lemma DERIV_cdivide:
   691 lemma DERIV_cdivide:
   681   "(f has_field_derivative D) (at x within s) \<Longrightarrow> ((\<lambda>x. f x / c) has_field_derivative D / c) (at x within s)"
   692   "(f has_field_derivative D) (at x within s) \<Longrightarrow> ((\<lambda>x. f x / c) has_field_derivative D / c) (at x within s)"
   682   using DERIV_cmult_right[of f D x s "1 / c"] by simp
   693   using DERIV_cmult_right[of f D x s "1 / c"] by simp
   683 
   694 
   684 lemma DERIV_unique:
   695 lemma DERIV_unique:
   685   "DERIV f x :> D \<Longrightarrow> DERIV f x :> E \<Longrightarrow> D = E"
   696   "DERIV f x :> D \<Longrightarrow> DERIV f x :> E \<Longrightarrow> D = E"
   686   unfolding deriv_def by (rule LIM_unique) 
   697   unfolding DERIV_def by (rule LIM_unique) 
   687 
   698 
   688 lemma DERIV_setsum:
   699 lemma DERIV_setsum[derivative_intros]:
   689   "(\<And> n. n \<in> S \<Longrightarrow> ((\<lambda>x. f x n) has_field_derivative (f' x n)) F) \<Longrightarrow> 
   700   "(\<And> n. n \<in> S \<Longrightarrow> ((\<lambda>x. f x n) has_field_derivative (f' x n)) F) \<Longrightarrow> 
   690     ((\<lambda>x. setsum (f x) S) has_field_derivative setsum (f' x) S) F"
   701     ((\<lambda>x. setsum (f x) S) has_field_derivative setsum (f' x) S) F"
   691   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_setsum])
   702   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_setsum])
   692      (auto simp: setsum_right_distrib mult_commute_abs dest: has_field_derivative_imp_has_derivative)
   703      (auto simp: setsum_right_distrib mult_commute_abs dest: has_field_derivative_imp_has_derivative)
   693 
   704 
   694 lemma DERIV_inverse':
   705 lemma DERIV_inverse'[derivative_intros]:
   695   "(f has_field_derivative D) (at x within s) \<Longrightarrow> f x \<noteq> 0 \<Longrightarrow>
   706   "(f has_field_derivative D) (at x within s) \<Longrightarrow> f x \<noteq> 0 \<Longrightarrow>
   696   ((\<lambda>x. inverse (f x)) has_field_derivative - (inverse (f x) * D * inverse (f x))) (at x within s)"
   707   ((\<lambda>x. inverse (f x)) has_field_derivative - (inverse (f x) * D * inverse (f x))) (at x within s)"
   697   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_inverse])
   708   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_inverse])
   698      (auto dest: has_field_derivative_imp_has_derivative)
   709      (auto dest: has_field_derivative_imp_has_derivative)
   699 
   710 
   710   ((\<lambda>x. inverse (f x)) has_field_derivative (- (d * inverse(f x ^ Suc (Suc 0))))) (at x within s)"
   721   ((\<lambda>x. inverse (f x)) has_field_derivative (- (d * inverse(f x ^ Suc (Suc 0))))) (at x within s)"
   711   by (drule (1) DERIV_inverse') (simp add: mult_ac nonzero_inverse_mult_distrib)
   722   by (drule (1) DERIV_inverse') (simp add: mult_ac nonzero_inverse_mult_distrib)
   712 
   723 
   713 text {* Derivative of quotient *}
   724 text {* Derivative of quotient *}
   714 
   725 
   715 lemma DERIV_divide:
   726 lemma DERIV_divide[derivative_intros]:
   716   "(f has_field_derivative D) (at x within s) \<Longrightarrow>
   727   "(f has_field_derivative D) (at x within s) \<Longrightarrow>
   717   (g has_field_derivative E) (at x within s) \<Longrightarrow> g x \<noteq> 0 \<Longrightarrow>
   728   (g has_field_derivative E) (at x within s) \<Longrightarrow> g x \<noteq> 0 \<Longrightarrow>
   718   ((\<lambda>x. f x / g x) has_field_derivative (D * g x - f x * E) / (g x * g x)) (at x within s)"
   729   ((\<lambda>x. f x / g x) has_field_derivative (D * g x - f x * E) / (g x * g x)) (at x within s)"
   719   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_divide])
   730   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_divide])
   720      (auto dest: has_field_derivative_imp_has_derivative simp: field_simps nonzero_inverse_mult_distrib divide_inverse)
   731      (auto dest: has_field_derivative_imp_has_derivative simp: field_simps nonzero_inverse_mult_distrib divide_inverse)
   729   "(f has_field_derivative D) (at x within s) \<Longrightarrow>
   740   "(f has_field_derivative D) (at x within s) \<Longrightarrow>
   730   ((\<lambda>x. f x ^ Suc n) has_field_derivative (1 + of_nat n) * (D * f x ^ n)) (at x within s)"
   741   ((\<lambda>x. f x ^ Suc n) has_field_derivative (1 + of_nat n) * (D * f x ^ n)) (at x within s)"
   731   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_power])
   742   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_power])
   732      (auto simp: has_field_derivative_def)
   743      (auto simp: has_field_derivative_def)
   733 
   744 
   734 lemma DERIV_power:
   745 lemma DERIV_power[derivative_intros]:
   735   "(f has_field_derivative D) (at x within s) \<Longrightarrow>
   746   "(f has_field_derivative D) (at x within s) \<Longrightarrow>
   736   ((\<lambda>x. f x ^ n) has_field_derivative of_nat n * (D * f x ^ (n - Suc 0))) (at x within s)"
   747   ((\<lambda>x. f x ^ n) has_field_derivative of_nat n * (D * f x ^ (n - Suc 0))) (at x within s)"
   737   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_power])
   748   by (rule has_derivative_imp_has_field_derivative[OF has_derivative_power])
   738      (auto simp: has_field_derivative_def)
   749      (auto simp: has_field_derivative_def)
   739 
   750 
   776   assumes "(\<And>x. DERIV g x :> g'(x))"
   787   assumes "(\<And>x. DERIV g x :> g'(x))"
   777       and "DERIV f x :> f'" 
   788       and "DERIV f x :> f'" 
   778     shows "DERIV (\<lambda>x. g(f x)) x :> f' * g'(f x)"
   789     shows "DERIV (\<lambda>x. g(f x)) x :> f' * g'(f x)"
   779   by (metis UNIV_I DERIV_chain_s [of UNIV] assms)
   790   by (metis UNIV_I DERIV_chain_s [of UNIV] assms)
   780 
   791 
   781 
       
   782 subsubsection {* @{text "DERIV_intros"} *}
       
   783 
       
   784 ML {*
       
   785 structure Deriv_Intros = Named_Thms
       
   786 (
       
   787   val name = @{binding DERIV_intros}
       
   788   val description = "DERIV introduction rules"
       
   789 )
       
   790 *}
       
   791 
       
   792 setup Deriv_Intros.setup
       
   793 
       
   794 lemma DERIV_cong: "(f has_field_derivative X) (at x within s) \<Longrightarrow> X = Y \<Longrightarrow> (f has_field_derivative Y) (at x within s)"
       
   795   by simp
       
   796 
       
   797 declare
   792 declare
   798   DERIV_const[THEN DERIV_cong, DERIV_intros]
   793   DERIV_power[where 'a=real, unfolded real_of_nat_def[symmetric], derivative_intros]
   799   DERIV_ident[THEN DERIV_cong, DERIV_intros]
       
   800   DERIV_add[THEN DERIV_cong, DERIV_intros]
       
   801   DERIV_minus[THEN DERIV_cong, DERIV_intros]
       
   802   DERIV_mult[THEN DERIV_cong, DERIV_intros]
       
   803   DERIV_diff[THEN DERIV_cong, DERIV_intros]
       
   804   DERIV_inverse'[THEN DERIV_cong, DERIV_intros]
       
   805   DERIV_divide[THEN DERIV_cong, DERIV_intros]
       
   806   DERIV_power[where 'a=real, THEN DERIV_cong,
       
   807               unfolded real_of_nat_def[symmetric], DERIV_intros]
       
   808   DERIV_setsum[THEN DERIV_cong, DERIV_intros]
       
   809 
   794 
   810 text{*Alternative definition for differentiability*}
   795 text{*Alternative definition for differentiability*}
   811 
   796 
   812 lemma DERIV_LIM_iff:
   797 lemma DERIV_LIM_iff:
   813   fixes f :: "'a::{real_normed_vector,inverse} \<Rightarrow> 'a" shows
   798   fixes f :: "'a::{real_normed_vector,inverse} \<Rightarrow> 'a" shows
   819 apply (drule_tac k="a" in LIM_offset)
   804 apply (drule_tac k="a" in LIM_offset)
   820 apply (simp add: add_commute)
   805 apply (simp add: add_commute)
   821 done
   806 done
   822 
   807 
   823 lemma DERIV_iff2: "(DERIV f x :> D) \<longleftrightarrow> (\<lambda>z. (f z - f x) / (z - x)) --x --> D"
   808 lemma DERIV_iff2: "(DERIV f x :> D) \<longleftrightarrow> (\<lambda>z. (f z - f x) / (z - x)) --x --> D"
   824   by (simp add: deriv_def DERIV_LIM_iff)
   809   by (simp add: DERIV_def DERIV_LIM_iff)
   825 
   810 
   826 lemma DERIV_cong_ev: "x = y \<Longrightarrow> eventually (\<lambda>x. f x = g x) (nhds x) \<Longrightarrow> u = v \<Longrightarrow>
   811 lemma DERIV_cong_ev: "x = y \<Longrightarrow> eventually (\<lambda>x. f x = g x) (nhds x) \<Longrightarrow> u = v \<Longrightarrow>
   827     DERIV f x :> u \<longleftrightarrow> DERIV g y :> v"
   812     DERIV f x :> u \<longleftrightarrow> DERIV g y :> v"
   828   unfolding DERIV_iff2
   813   unfolding DERIV_iff2
   829 proof (rule filterlim_cong)
   814 proof (rule filterlim_cong)
   834     by (auto simp: eventually_at_filter elim: eventually_elim1)
   819     by (auto simp: eventually_at_filter elim: eventually_elim1)
   835 qed simp_all
   820 qed simp_all
   836 
   821 
   837 lemma DERIV_shift:
   822 lemma DERIV_shift:
   838   "(DERIV f (x + z) :> y) \<longleftrightarrow> (DERIV (\<lambda>x. f (x + z)) x :> y)"
   823   "(DERIV f (x + z) :> y) \<longleftrightarrow> (DERIV (\<lambda>x. f (x + z)) x :> y)"
   839   by (simp add: deriv_def field_simps)
   824   by (simp add: DERIV_def field_simps)
   840 
   825 
   841 lemma DERIV_mirror:
   826 lemma DERIV_mirror:
   842   "(DERIV f (- x) :> y) \<longleftrightarrow> (DERIV (\<lambda>x. f (- x::real) :: real) x :> - y)"
   827   "(DERIV f (- x) :> y) \<longleftrightarrow> (DERIV (\<lambda>x. f (- x::real) :: real) x :> - y)"
   843   by (simp add: deriv_def filterlim_at_split filterlim_at_left_to_right
   828   by (simp add: DERIV_def filterlim_at_split filterlim_at_left_to_right
   844                 tendsto_minus_cancel_left field_simps conj_commute)
   829                 tendsto_minus_cancel_left field_simps conj_commute)
   845 
   830 
   846 text {* Caratheodory formulation of derivative at a point *}
   831 text {* Caratheodory formulation of derivative at a point *}
   847 
   832 
   848 lemma CARAT_DERIV: (*FIXME: SUPERSEDED BY THE ONE IN Deriv.thy. But still used by NSA/HDeriv.thy*)
   833 lemma CARAT_DERIV: (*FIXME: SUPERSEDED BY THE ONE IN Deriv.thy. But still used by NSA/HDeriv.thy*)
   853   show "\<exists>g. (\<forall>z. f z - f x = g z * (z-x)) \<and> isCont g x \<and> g x = l"
   838   show "\<exists>g. (\<forall>z. f z - f x = g z * (z-x)) \<and> isCont g x \<and> g x = l"
   854   proof (intro exI conjI)
   839   proof (intro exI conjI)
   855     let ?g = "(%z. if z = x then l else (f z - f x) / (z-x))"
   840     let ?g = "(%z. if z = x then l else (f z - f x) / (z-x))"
   856     show "\<forall>z. f z - f x = ?g z * (z-x)" by simp
   841     show "\<forall>z. f z - f x = ?g z * (z-x)" by simp
   857     show "isCont ?g x" using der
   842     show "isCont ?g x" using der
   858       by (simp add: isCont_iff deriv_def cong: LIM_equal [rule_format])
   843       by (simp add: isCont_iff DERIV_def cong: LIM_equal [rule_format])
   859     show "?g x = l" by simp
   844     show "?g x = l" by simp
   860   qed
   845   qed
   861 next
   846 next
   862   assume "?rhs"
   847   assume "?rhs"
   863   then obtain g where
   848   then obtain g where
   864     "(\<forall>z. f z - f x = g z * (z-x))" and "isCont g x" and "g x = l" by blast
   849     "(\<forall>z. f z - f x = g z * (z-x))" and "isCont g x" and "g x = l" by blast
   865   thus "(DERIV f x :> l)"
   850   thus "(DERIV f x :> l)"
   866      by (auto simp add: isCont_iff deriv_def cong: LIM_cong)
   851      by (auto simp add: isCont_iff DERIV_def cong: LIM_cong)
   867 qed
   852 qed
   868 
   853 
   869 text {*
   854 text {*
   870  Let's do the standard proof, though theorem
   855  Let's do the standard proof, though theorem
   871  @{text "LIM_mult2"} follows from a NS proof
   856  @{text "LIM_mult2"} follows from a NS proof
  1475   hence "\<exists>D. DERIV f c :> D" by (rule differentiableD)
  1460   hence "\<exists>D. DERIV f c :> D" by (rule differentiableD)
  1476   then obtain f'c where f'cdef: "DERIV f c :> f'c" ..
  1461   then obtain f'c where f'cdef: "DERIV f c :> f'c" ..
  1477 
  1462 
  1478   from cdef have "DERIV ?h c :> l" by auto
  1463   from cdef have "DERIV ?h c :> l" by auto
  1479   moreover have "DERIV ?h c :>  g'c * (f b - f a) - f'c * (g b - g a)"
  1464   moreover have "DERIV ?h c :>  g'c * (f b - f a) - f'c * (g b - g a)"
  1480     using g'cdef f'cdef by (auto intro!: DERIV_intros)
  1465     using g'cdef f'cdef by (auto intro!: derivative_eq_intros)
  1481   ultimately have leq: "l =  g'c * (f b - f a) - f'c * (g b - g a)" by (rule DERIV_unique)
  1466   ultimately have leq: "l =  g'c * (f b - f a) - f'c * (g b - g a)" by (rule DERIV_unique)
  1482 
  1467 
  1483   {
  1468   {
  1484     from cdef have "?h b - ?h a = (b - a) * l" by auto
  1469     from cdef have "?h b - ?h a = (b - a) * l" by auto
  1485     also from leq have "\<dots> = (b - a) * (g'c * (f b - f a) - f'c * (g b - g a))" by simp
  1470     also from leq have "\<dots> = (b - a) * (g'c * (f b - f a) - f'c * (g b - g a))" by simp