1 #ifndef STAN__PROB__DISTRIBUTIONS__UNIVARIATE__CONTINUOUS__RAYLEIGH_HPP
2 #define STAN__PROB__DISTRIBUTIONS__UNIVARIATE__CONTINUOUS__RAYLEIGH_HPP
4 #include <boost/random/uniform_real_distribution.hpp>
5 #include <boost/random/variate_generator.hpp>
18 template <
bool propto,
19 typename T_y,
typename T_scale>
20 typename return_type<T_y,T_scale>::type
22 static const char*
function =
"stan::prob::rayleigh_log(%1%)";
45 "Random variable",
"Scale parameter",
62 for (
size_t i = 0; i <
length(sigma); i++) {
63 inv_sigma[i] = 1.0 /
value_of(sigma_vec[i]);
68 for (
size_t n = 0; n < N; n++) {
70 const double y_dbl =
value_of(y_vec[n]);
73 const double y_over_sigma = y_dbl * inv_sigma[n];
75 static double NEGATIVE_HALF = -0.5;
79 logp -= 2.0 * log_sigma[n];
83 logp += NEGATIVE_HALF * y_over_sigma * y_over_sigma;
86 double scaled_diff = inv_sigma[n] * y_over_sigma;
88 operands_and_partials.
d_x1[n] += 1.0 / y_dbl - scaled_diff;
90 operands_and_partials.
d_x2[n]
91 += y_over_sigma * scaled_diff - 2.0 * inv_sigma[n];
93 return operands_and_partials.
to_var(logp);
96 template <
typename T_y,
typename T_scale>
100 return rayleigh_log<false>(y,sigma);
103 template <
typename T_y,
typename T_scale>
106 static const char*
function =
"stan::prob::rayleigh_cdf(%1%)";
129 "Random variable",
"Scale parameter",
141 for (
size_t i = 0; i <
length(sigma); i++) {
142 inv_sigma[i] = 1.0 /
value_of(sigma_vec[i]);
145 for (
size_t n = 0; n < N; n++) {
146 const double y_dbl =
value_of(y_vec[n]);
147 const double y_sqr = y_dbl * y_dbl;
148 const double inv_sigma_sqr = inv_sigma[n] * inv_sigma[n];
149 const double exp_val =
exp(-0.5 * y_sqr * inv_sigma_sqr);
152 cdf *= (1.0 - exp_val);
156 for (
size_t n = 0; n < N; n++) {
157 const double y_dbl =
value_of(y_vec[n]);
158 const double y_sqr =
square(y_dbl);
159 const double inv_sigma_sqr =
square(inv_sigma[n]);
160 const double exp_val =
exp(-0.5 * y_sqr * inv_sigma_sqr);
161 const double exp_div_1m_exp = exp_val / (1.0 - exp_val);
164 operands_and_partials.
d_x1[n] += y_dbl * inv_sigma_sqr
165 * exp_div_1m_exp * cdf;
167 operands_and_partials.
d_x2[n] -= y_sqr * inv_sigma_sqr
168 * inv_sigma[n] * exp_div_1m_exp * cdf;
171 return operands_and_partials.
to_var(cdf);
174 template <
typename T_y,
typename T_scale>
177 static const char*
function =
"stan::prob::rayleigh_cdf_log(%1%)";
200 "Random variable",
"Scale parameter",
212 for (
size_t i = 0; i <
length(sigma); i++) {
213 inv_sigma[i] = 1.0 /
value_of(sigma_vec[i]);
216 for (
size_t n = 0; n < N; n++) {
217 const double y_dbl =
value_of(y_vec[n]);
218 const double y_sqr = y_dbl * y_dbl;
219 const double inv_sigma_sqr = inv_sigma[n] * inv_sigma[n];
220 const double exp_val =
exp(-0.5 * y_sqr * inv_sigma_sqr);
221 const double exp_div_1m_exp = exp_val / (1.0 - exp_val);
224 cdf_log +=
log(1.0 - exp_val);
227 operands_and_partials.
d_x1[n] += y_dbl * inv_sigma_sqr
230 operands_and_partials.
d_x2[n] -= y_sqr * inv_sigma_sqr
231 * inv_sigma[n] * exp_div_1m_exp;
234 return operands_and_partials.
to_var(cdf_log);
237 template <
typename T_y,
typename T_scale>
240 static const char*
function =
"stan::prob::rayleigh_ccdf_log(%1%)";
251 double ccdf_log(0.0);
259 check_not_nan(
function, sigma,
"Scale parameter", &ccdf_log);
263 "Random variable",
"Scale parameter",
275 for (
size_t i = 0; i <
length(sigma); i++) {
276 inv_sigma[i] = 1.0 /
value_of(sigma_vec[i]);
279 for (
size_t n = 0; n < N; n++) {
280 const double y_dbl =
value_of(y_vec[n]);
281 const double y_sqr = y_dbl * y_dbl;
282 const double inv_sigma_sqr = inv_sigma[n] * inv_sigma[n];
285 ccdf_log += -0.5 * y_sqr * inv_sigma_sqr;
288 operands_and_partials.
d_x1[n] -= y_dbl * inv_sigma_sqr;
290 operands_and_partials.
d_x2[n] += y_sqr * inv_sigma_sqr
294 return operands_and_partials.
to_var(ccdf_log);
301 using boost::variate_generator;
302 using boost::random::uniform_real_distribution;
304 static const char*
function =
"stan::prob::rayleigh_rng(%1%)";
310 variate_generator<RNG&, uniform_real_distribution<> >
311 uniform_rng(rng, uniform_real_distribution<>(0.0, 1.0));
T square(const T x)
Return the square of the specified argument.
return_type< T_y, T_scale >::type rayleigh_cdf(const T_y &y, const T_scale &sigma)
T_return_type to_var(double logp)
fvar< T > square(const fvar< T > &x)
DoubleVectorView allocates double values to be used as intermediate values.
T value_of(const fvar< T > &v)
Return the value of the specified variable.
A variable implementation that stores operands and derivatives with respect to the variable...
boost::math::tools::promote_args< typename scalar_type< T1 >::type, typename scalar_type< T2 >::type, typename scalar_type< T3 >::type, typename scalar_type< T4 >::type, typename scalar_type< T5 >::type, typename scalar_type< T6 >::type >::type type
return_type< T_y, T_scale >::type rayleigh_ccdf_log(const T_y &y, const T_scale &sigma)
Metaprogram to determine if a type has a base scalar type that can be assigned to type double...
double value_of(const T x)
Return the value of the specified scalar argument converted to a double value.
Template metaprogram to calculate whether a summand needs to be included in a proportional (log) prob...
fvar< T > sqrt(const fvar< T > &x)
VectorView< double *, is_vector< T2 >::value, is_constant_struct< T2 >::value > d_x2
double uniform_rng(const double alpha, const double beta, RNG &rng)
bool check_nonnegative(const char *function, const T_y &y, const char *name, T_result *result)
bool check_consistent_sizes(const char *function, const T1 &x1, const T2 &x2, const char *name1, const char *name2, T_result *result)
size_t max_size(const T1 &x1, const T2 &x2)
bool check_positive(const char *function, const T_y &y, const char *name, T_result *result)
return_type< T_y, T_scale >::type rayleigh_cdf_log(const T_y &y, const T_scale &sigma)
return_type< T_y, T_scale >::type rayleigh_log(const T_y &y, const T_scale &sigma)
bool check_not_nan(const char *function, const T_y &y, const char *name, T_result *result)
Checks if the variable y is nan.
VectorView< double *, is_vector< T1 >::value, is_constant_struct< T1 >::value > d_x1
double rayleigh_rng(const double sigma, RNG &rng)
fvar< T > log(const fvar< T > &x)
VectorView is a template metaprogram that takes its argument and allows it to be used like a vector...
fvar< T > exp(const fvar< T > &x)