1 #ifndef __STAN__PROB__DISTRIBUTIONS__UNIVARIATE__DISCRETE__BERNOULLI_HPP__
2 #define __STAN__PROB__DISTRIBUTIONS__UNIVARIATE__DISCRETE__BERNOULLI_HPP__
17 template <
bool propto,
18 typename T_n,
typename T_prob,
20 typename return_type<T_prob>::type
24 static const char*
function =
"stan::prob::bernoulli_log(%1%)";
44 if (!
check_finite(
function, theta,
"Probability parameter", &logp, Policy()))
47 "Probability parameter", &logp, Policy()))
51 "Random variable",
"Probability parameter",
67 for (
size_t n = 0; n < N; n++) {
70 const double theta_dbl =
value_of(theta_vec[0]);
73 logp += N *
log(theta_dbl);
74 operands_and_partials.
d_x1[0] += N / theta_dbl;
75 }
else if (sum == 0) {
76 logp += N *
log1m(theta_dbl);
77 operands_and_partials.
d_x1[0] += N / (theta_dbl - 1);
79 const double log_theta =
log(theta_dbl);
80 const double log1m_theta =
log1m(theta_dbl);
82 logp += sum * log_theta;
83 logp += (N -
sum) * log1m_theta;
85 operands_and_partials.
d_x1[0] += sum / theta_dbl;
86 operands_and_partials.
d_x1[0] += (N -
sum) / (theta_dbl - 1);
90 for (
size_t n = 0; n < N; n++) {
92 const int n_int =
value_of(n_vec[n]);
93 const double theta_dbl =
value_of(theta_vec[n]);
97 logp +=
log(theta_dbl);
99 logp +=
log1m(theta_dbl);
105 operands_and_partials.
d_x1[n] += 1.0 / theta_dbl;
107 operands_and_partials.
d_x1[n] += 1.0 / (theta_dbl - 1);
111 return operands_and_partials.
to_var(logp);
114 template <
bool propto,
120 const T_prob& theta) {
124 template <
typename T_y,
132 return bernoulli_log<false>(n,theta,Policy());
135 template <
typename T_y,
typename T_prob>
139 const T_prob& theta) {
146 template <
bool propto,
154 static const char*
function =
"stan::prob::bernoulli_logit_log(%1%)";
176 if (!
check_not_nan(
function, theta,
"Logit transformed probability parameter",
181 "Random variable",
"Probability parameter",
195 for (
size_t n = 0; n < N; n++) {
197 const int n_int =
value_of(n_vec[n]);
198 const double theta_dbl =
value_of(theta_vec[n]);
201 const int sign = 2*n_int-1;
202 const double ntheta = sign * theta_dbl;
203 const double exp_m_ntheta =
exp(-ntheta);
207 const static double cutoff = 20.0;
209 logp -= exp_m_ntheta;
210 else if (ntheta < -cutoff)
213 logp -=
log1p(exp_m_ntheta);
218 const static double cutoff = 20.0;
220 operands_and_partials.
d_x1[n] -= exp_m_ntheta;
221 else if (ntheta < -cutoff)
222 operands_and_partials.
d_x1[n] +=
sign;
224 operands_and_partials.
d_x1[n] += sign * exp_m_ntheta / (exp_m_ntheta + 1);
227 return operands_and_partials.
to_var(logp);
231 template <
bool propto,
237 const T_prob& theta) {
242 template <
typename T_n,
250 return bernoulli_logit_log<false>(n,theta,Policy());
254 template <
typename T_n,
259 const T_prob& theta) {
264 template <
bool propto,
typename T_n,
typename T_prob,
class Policy>
268 static const char*
function =
"stan::prob::bernoulli_cdf(%1%)";
285 if (!
check_finite(
function, theta,
"Probability parameter", &P, Policy()))
289 "Probability parameter", &P, Policy()))
294 "Random variable",
"Probability parameter",
309 using boost::math::ibetac;
310 using boost::math::ibeta_derivative;
314 for (
size_t i = 0; i < size; i++) {
316 const double n_dbl =
value_of(n_vec[i]);
317 const double theta_dbl =
value_of(theta_vec[i]);
319 const double Pi = ibetac(n_dbl + 1, 1 - n_dbl, theta_dbl);
324 operands_and_partials.
d_x1[i] += - ibeta_derivative(n_dbl + 1, 1 - n_dbl, theta_dbl) / Pi;
328 for (
size_t i = 0; i < size; i++) {
331 operands_and_partials.
d_x1[i] *= P;
339 template <
bool propto,
typename T_y,
typename T_prob>
345 template <
typename T_y,
typename T_prob,
class Policy>
348 return bernoulli_cdf<false>(n, theta, Policy());
351 template <
typename T_y,
typename T_prob>