Automatic Differentiation
 
Loading...
Searching...
No Matches
dirichlet_multinomial_lpmf.hpp
Go to the documentation of this file.
1#ifndef STAN_MATH_PRIM_PROB_DIRICHLET_MULTINOMIAL_LPMF_HPP
2#define STAN_MATH_PRIM_PROB_DIRICHLET_MULTINOMIAL_LPMF_HPP
3
13#include <vector>
14
15namespace stan {
16namespace math {
17
58template <bool propto, typename T_prior_size,
59 require_eigen_col_vector_t<T_prior_size>* = nullptr>
61 const std::vector<int>& ns, const T_prior_size& alpha) {
62 static const char* function = "dirichlet_multinomial_lpmf";
63 check_size_match(function, "Size of number of trials variable", ns.size(),
64 "rows of prior size parameter", alpha.rows());
65 check_nonnegative(function, "Number of trials variable", ns);
66 const auto& alpha_ref = to_ref(alpha);
67 const auto& alpha_val = as_value_array_or_scalar(alpha_ref);
68 check_positive_finite(function, "Prior size parameter", alpha_ref);
69
71 return 0.0;
72 }
73
74 int n_sum = sum(ns);
75 if (n_sum == 0) {
76 return 0.0;
77 }
78
79 // Need to treat as double otherwise Eigen's array log truncates
80 auto ns_array = as_array_or_scalar(ns).template cast<double>();
81 partials_return_t<T_prior_size> a_sum = sum(alpha_val);
84 lp += log(n_sum) - (ns_array > 0).select(log(ns_array), 0.0).sum();
85 }
86
87 lp += lbeta(a_sum, n_sum)
88 - (ns_array > 0).select(lbeta(alpha_val, ns_array), 0.0).sum();
89
90 auto ops_partials = make_partials_propagator(alpha_ref);
92 partials<0>(ops_partials)
93 = (ns_array > 0)
94 .select(digamma(alpha_val + ns_array) - digamma(alpha_val), 0.0)
95 + digamma(a_sum) - digamma(a_sum + n_sum);
96 }
97 return ops_partials.build(lp);
98}
99
100template <typename T_prior_size>
102 const std::vector<int>& ns, const T_prior_size& alpha) {
103 return dirichlet_multinomial_lpmf<false>(ns, alpha);
104}
105
106} // namespace math
107} // namespace stan
108#endif
return_type_t< T_prior_size > dirichlet_multinomial_lpmf(const std::vector< int > &ns, const T_prior_size &alpha)
The log of the Dirichlet-Multinomial probability for the given integer vector and a vector of prior ...
select_< as_operation_cl_t< T_condition >, as_operation_cl_t< T_then >, as_operation_cl_t< T_else > > select(T_condition &&condition, T_then &&then, T_else &&els)
Selection operation on kernel generator expressions.
Definition select.hpp:148
typename return_type< Ts... >::type return_type_t
Convenience type for the return type of the specified template parameters.
T as_array_or_scalar(T &&v)
Returns specified input value.
void check_nonnegative(const char *function, const char *name, const T_y &y)
Check if y is non-negative.
fvar< T > lbeta(const fvar< T > &x1, const fvar< T > &x2)
Definition lbeta.hpp:14
fvar< T > log(const fvar< T > &x)
Definition log.hpp:18
ref_type_t< T && > to_ref(T &&a)
This evaluates expensive Eigen expressions.
Definition to_ref.hpp:17
auto sum(const std::vector< T > &m)
Return the sum of the entries of the specified standard vector.
Definition sum.hpp:23
void check_size_match(const char *function, const char *name_i, T_size1 i, const char *name_j, T_size2 j)
Check if the provided sizes match.
auto as_value_array_or_scalar(T &&v)
Extract the value from an object.
auto make_partials_propagator(Ops &&... ops)
Construct an partials_propagator.
void check_positive_finite(const char *function, const char *name, const T_y &y)
Check if y is positive and finite.
fvar< T > digamma(const fvar< T > &x)
Return the derivative of the log gamma function at the specified argument.
Definition digamma.hpp:23
typename partials_return_type< Args... >::type partials_return_t
The lgamma implementation in stan-math is based on either the reentrant safe lgamma_r implementation ...
Extends std::true_type when instantiated with zero or more template parameters, all of which extend t...
Template metaprogram to calculate whether a summand needs to be included in a proportional (log) prob...