Работа с численными расчетами, имеющими экспоненциальные термины, часто становится болезненной, благодаря ошибкам переполнения. Например, предположим, что у вас плотность вероятности, P(x)=C*exp(f(x)/k)
, где k - очень малое число, например порядка 10^(-5)
.
Чтобы найти значение C
, необходимо проинтегрировать P(x)
. Здесь возникает ошибка переполнения. Я знаю, что это также зависит от формы f(x)
. Но на этот момент предположим, что f(x)=sin(x)
.
Как бороться с такими проблемами?
Какие трюки мы можем использовать, чтобы избежать их?
Является ли серьезность таких проблем языковой зависимой? Если да, на каком языке следует писать свой код?
Как я упоминал в комментариях, я настоятельно рекомендую использовать аналитические методы, насколько это возможно. Однако, если вы хотите вычислить интегралы вида
I=Integral[Exp[f(x)],{x,a,b}]
Где f (x) может потенциально переполнить экспоненту, тогда вы можете немного перенормировать систему следующим образом:
Предположим, что f (c) является максимумом f (x) в области [a, b], тогда вы можете написать:
I=Exp[f(c)] Integral[Exp[f(x)-f(c)],{x,a,b}]
Это уродливый трюк, но по крайней мере ваши экспоненты будут небольшими в интеграле.
примечание: только что понял, что это комментарий roygvib
Один из вариантов - использование научной библиотеки GSL - GNU (доступны оболочки python и fortran). Существует функция gsl_sf_exp_e10_e
которая согласно документации
вычисляет экспоненту \exp (x) с помощью типа gsl_sf_result_e10, чтобы вернуть результат с расширенным диапазоном. Эта функция может быть полезна, если значение \exp (x) переполнит числовой диапазон double.
Однако я хотел бы отметить, что он замедляется из-за дополнительных проверок во время оценки.
PS Как было сказано ранее, лучше использовать аналитические решения там, где это возможно.
+
вместо*
?