bessel_derivatives_linear.hpp 4.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107
  1. // Copyright (c) 2013 Anton Bikineev
  2. // Use, modification and distribution are subject to the
  3. // Boost Software License, Version 1.0. (See accompanying file
  4. // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  5. //
  6. // This is a partial header, do not include on it's own!!!
  7. //
  8. // Linear combination for bessel derivatives are defined here
  9. #ifndef BOOST_MATH_SF_DETAIL_BESSEL_DERIVATIVES_LINEAR_HPP
  10. #define BOOST_MATH_SF_DETAIL_BESSEL_DERIVATIVES_LINEAR_HPP
  11. #include <iostream>
  12. #ifdef _MSC_VER
  13. #pragma once
  14. #endif
  15. namespace boost{ namespace math{ namespace detail{
  16. template <class T, class Tag, class Policy>
  17. inline T bessel_j_derivative_linear(T v, T x, Tag tag, Policy pol)
  18. {
  19. return (boost::math::detail::cyl_bessel_j_imp<T>(v-1, x, tag, pol) - boost::math::detail::cyl_bessel_j_imp<T>(v+1, x, tag, pol)) / 2;
  20. }
  21. template <class T, class Policy>
  22. inline T bessel_j_derivative_linear(T v, T x, const bessel_int_tag& tag, Policy pol)
  23. {
  24. return (boost::math::detail::cyl_bessel_j_imp<T>(itrunc(v-1), x, tag, pol) - boost::math::detail::cyl_bessel_j_imp<T>(itrunc(v+1), x, tag, pol)) / 2;
  25. }
  26. template <class T, class Policy>
  27. inline T sph_bessel_j_derivative_linear(unsigned v, T x, Policy pol)
  28. {
  29. return (v / x) * boost::math::detail::sph_bessel_j_imp<T>(v, x, pol) - boost::math::detail::sph_bessel_j_imp<T>(v+1, x, pol);
  30. }
  31. template <class T, class Policy>
  32. inline T bessel_i_derivative_linear(T v, T x, Policy pol)
  33. {
  34. T result = boost::math::detail::cyl_bessel_i_imp<T>(v - 1, x, pol);
  35. if(result >= tools::max_value<T>())
  36. return result; // result is infinite
  37. // Both experimentally, and based on https://www.wolframalpha.com/input?i=BesselI%5Bv%2C+x%5D%2FBesselI%5Bv%2B2%2C+x%5D
  38. // I[v + 1, x] < I[v-1, x], so this can't overflow:
  39. T result2 = boost::math::detail::cyl_bessel_i_imp<T>(v + 1, x, pol);
  40. return result / 2 + result2 / 2;
  41. }
  42. template <class T, class Tag, class Policy>
  43. inline T bessel_k_derivative_linear(T v, T x, Tag tag, Policy pol)
  44. {
  45. T result = boost::math::detail::cyl_bessel_k_imp<T>(v - 1, x, tag, pol);
  46. if(result >= tools::max_value<T>())
  47. return -result; // result is infinite
  48. T result2 = boost::math::detail::cyl_bessel_k_imp<T>(v + 1, x, tag, pol);
  49. if(result2 >= tools::max_value<T>() + result)
  50. return -boost::math::policies::raise_overflow_error<T>("cyl_bessel_k_prime<%1>", 0, pol); // result is infinite
  51. result /= -2;
  52. result2 /= -2;
  53. return result + result2;
  54. }
  55. template <class T, class Policy>
  56. inline T bessel_k_derivative_linear(T v, T x, const bessel_int_tag& tag, Policy pol)
  57. {
  58. T result = boost::math::detail::cyl_bessel_k_imp<T>(itrunc(v - 1), x, tag, pol);
  59. if (result >= tools::max_value<T>())
  60. return -result; // result is infinite
  61. T result2 = boost::math::detail::cyl_bessel_k_imp<T>(itrunc(v + 1), x, tag, pol);
  62. if (result2 >= tools::max_value<T>() + result)
  63. return -boost::math::policies::raise_overflow_error<T>("cyl_bessel_k_prime<%1>", 0, pol); // result is infinite
  64. result /= -2;
  65. result2 /= -2;
  66. return result + result2;
  67. }
  68. template <class T, class Policy>
  69. inline T bessel_k_derivative_linear(T v, T x, const bessel_maybe_int_tag&, Policy pol)
  70. {
  71. using std::floor;
  72. if (floor(v) == v)
  73. return bessel_k_derivative_linear(v, x, bessel_int_tag(), pol);
  74. return bessel_k_derivative_linear(v, x, bessel_no_int_tag(), pol);
  75. }
  76. template <class T, class Tag, class Policy>
  77. inline T bessel_y_derivative_linear(T v, T x, Tag tag, Policy pol)
  78. {
  79. return (boost::math::detail::cyl_neumann_imp<T>(v-1, x, tag, pol) - boost::math::detail::cyl_neumann_imp<T>(v+1, x, tag, pol)) / 2;
  80. }
  81. template <class T, class Policy>
  82. inline T bessel_y_derivative_linear(T v, T x, const bessel_int_tag& tag, Policy pol)
  83. {
  84. return (boost::math::detail::cyl_neumann_imp<T>(itrunc(v-1), x, tag, pol) - boost::math::detail::cyl_neumann_imp<T>(itrunc(v+1), x, tag, pol)) / 2;
  85. }
  86. template <class T, class Policy>
  87. inline T sph_neumann_derivative_linear(unsigned v, T x, Policy pol)
  88. {
  89. return (v / x) * boost::math::detail::sph_neumann_imp<T>(v, x, pol) - boost::math::detail::sph_neumann_imp<T>(v+1, x, pol);
  90. }
  91. }}} // namespaces
  92. #endif // BOOST_MATH_SF_DETAIL_BESSEL_DERIVATIVES_LINEAR_HPP