use chrono::{DateTime, Utc};
use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct BetaPosterior {
pub alpha: f64,
pub beta: f64,
pub n: u64,
pub c_self: f64,
pub kappa: f64,
pub last_update: DateTime<Utc>,
}
impl BetaPosterior {
pub fn from_self_confidence(c_self: f64, kappa: f64) -> Self {
let c = c_self.clamp(0.0, 1.0);
Self {
alpha: kappa * c,
beta: kappa * (1.0 - c),
n: 0,
c_self: c,
kappa,
last_update: Utc::now(),
}
}
pub fn mean(&self) -> f64 {
let t = self.alpha + self.beta;
if t <= 0.0 { 0.0 } else { self.alpha / t }
}
pub fn variance(&self) -> f64 {
let t = self.alpha + self.beta;
if t <= 0.0 {
return 0.0;
}
(self.alpha * self.beta) / (t * t * (t + 1.0))
}
pub fn score(&self, gamma: f64) -> f64 {
self.mean() - gamma * self.variance().sqrt()
}
pub fn update(&mut self, outcome: bool, lambda: f64) {
self.alpha *= lambda;
self.beta *= lambda;
if outcome {
self.alpha += 1.0;
} else {
self.beta += 1.0;
}
self.n += 1;
self.last_update = Utc::now();
}
}