-
-
Notifications
You must be signed in to change notification settings - Fork 10
Add mode method for Discrete distributions #660
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
Codecov ReportAttention: Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## main #660 +/- ##
===========================================
- Coverage 82.23% 49.44% -32.79%
===========================================
Files 101 107 +6
Lines 8020 8808 +788
===========================================
- Hits 6595 4355 -2240
- Misses 1425 4453 +3028 ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
preliz/distributions/zi_binomial.py
Outdated
binomial_raw_mode = Binomial(self.n, self.p).mode() | ||
binomial_mode = ( | ||
min(binomial_raw_mode) | ||
if isinstance(binomial_raw_mode, tuple) | ||
else int(binomial_raw_mode) | ||
) | ||
if self.psi == 0: | ||
return 0 | ||
elif self.psi == 1: | ||
return binomial_mode | ||
else: | ||
prob_zero = (1 - self.psi) + self.psi * (1 - self.p) ** self.n | ||
prob_binomial_mode = self.psi * np.exp( | ||
gammaln(self.n + 1) | ||
- gammaln(binomial_mode + 1) | ||
- gammaln(self.n - binomial_mode + 1) | ||
+ binomial_mode * np.log(self.p) | ||
+ (self.n - binomial_mode) * np.log1p(-self.p) | ||
) | ||
return 0 if prob_zero > prob_binomial_mode else binomial_mode |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would write this as
binomial_raw_mode = Binomial(self.n, self.p).mode() | |
binomial_mode = ( | |
min(binomial_raw_mode) | |
if isinstance(binomial_raw_mode, tuple) | |
else int(binomial_raw_mode) | |
) | |
if self.psi == 0: | |
return 0 | |
elif self.psi == 1: | |
return binomial_mode | |
else: | |
prob_zero = (1 - self.psi) + self.psi * (1 - self.p) ** self.n | |
prob_binomial_mode = self.psi * np.exp( | |
gammaln(self.n + 1) | |
- gammaln(binomial_mode + 1) | |
- gammaln(self.n - binomial_mode + 1) | |
+ binomial_mode * np.log(self.p) | |
+ (self.n - binomial_mode) * np.log1p(-self.p) | |
) | |
return 0 if prob_zero > prob_binomial_mode else binomial_mode | |
if self.psi == 0: | |
return 0 | |
else: | |
bin_dist = Binomial(self.n, self.p) | |
binomial_raw_mode = bin_dist.mode() | |
binomial_mode = ( | |
min(binomial_raw_mode) | |
if isinstance(binomial_raw_mode, tuple) | |
else int(binomial_raw_mode) | |
) | |
if self.psi == 1: | |
return binomial_mode | |
else: | |
prob_zero = (1 - self.psi) + self.psi * (1 - self.p) ** self.n | |
prob_binomial_mode = self.psi * bin_dist.pdf(binomial_mode) | |
return 0 if prob_zero > prob_binomial_mode else binomial_mode |
But then I realized I was confused about how we have implemented ZIB. When we talked, I had the wrong idea that we have explicitly impleted as a binomial + a zero_inflation. So may we should use the pmf method you suggested like this:
x_vals = self.xvals("full")
pmf_vals = self.pdf(x_vals)
return x_vals[np.argmax(pmf_vals)].astype(int)
This should be implemented as a general method for all the missing discrete variables (unless we have a more direct way for them).
Could you add this to all the discrete distributions without a mode method? We can later replace some of them with a specific method if available or easy-to-implemet |
Description
find_discrete_mode
ininternal.optimization
. It can be used in the remaining discrete distributions which don't have an analytical or simple solution for the mode. It evaluates the PMF over the distribution's support and returns the value with the highest probability.Checklist