docs: complete the public API documentation contract
Closes the last open item in #25. `cargo clippy -W missing_errors_doc -W missing_panics_doc -W must_use_candidate -W doc_markdown` went from 56 warnings to zero. The 13 hand-written sections name the actual variants each function returns rather than gesturing at "an error". Establishing that meant reading the error paths — `Game::ranked` alone returns four distinct variants, and `record_draw` can hit TieWithoutDrawProbability where `record_winner` provably cannot, since a two-team decisive outcome has nothing to tie. Documenting those as interchangeable would have been worse than leaving them undocumented, because a reader would trust it. Two existing doc comments already described panics in prose but not under a `# Panics` heading, so neither rustdoc nor clippy surfaced them: `Outcome::winner` and `EventBuilder::weights`. Both now carry the heading, and `Outcome::winner` gained the note that it ties every loser, so `n >= 3` needs a positive p_draw — the crate's easiest error to hit by accident. The 43 mechanical fixes (31 `#[must_use]` on pure accessors, 11 missing backticks) were applied with `cargo clippy --fix`. `#[must_use]` on Gaussian's arithmetic and on `posteriors()` matters: discarding those results is always a bug, and until now nothing said so. Also documented why `[profile.release] debug = true` exists — cargo-flamegraph needs the symbols, and library profile settings are ignored downstream, so it reads as an oversight without the note. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01T5SYDExxL4vZgvunrcNSMc
This commit is contained in:
+28
@@ -145,6 +145,7 @@ impl<T: Time, D: Drift<T>> OwnedGame<T, D> {
|
||||
}
|
||||
}
|
||||
|
||||
#[must_use]
|
||||
pub fn posteriors(&self) -> Vec<Vec<Gaussian>> {
|
||||
self.likelihoods
|
||||
.iter()
|
||||
@@ -153,6 +154,7 @@ impl<T: Time, D: Drift<T>> OwnedGame<T, D> {
|
||||
.collect()
|
||||
}
|
||||
|
||||
#[must_use]
|
||||
pub fn log_evidence(&self) -> f64 {
|
||||
self.log_evidence
|
||||
}
|
||||
@@ -409,6 +411,7 @@ impl<'a, T: Time, D: Drift<T>> Game<'a, T, D> {
|
||||
self.likelihoods = likelihoods;
|
||||
}
|
||||
|
||||
#[must_use]
|
||||
pub fn posteriors(&self) -> Vec<Vec<Gaussian>> {
|
||||
self.likelihoods
|
||||
.iter()
|
||||
@@ -422,12 +425,21 @@ impl<'a, T: Time, D: Drift<T>> Game<'a, T, D> {
|
||||
.collect::<Vec<_>>()
|
||||
}
|
||||
|
||||
#[must_use]
|
||||
pub fn log_evidence(&self) -> f64 {
|
||||
self.log_evidence
|
||||
}
|
||||
}
|
||||
|
||||
impl<T: Time, D: Drift<T>> Game<'_, T, D> {
|
||||
/// # Errors
|
||||
///
|
||||
/// - `InvalidProbability` if `options.p_draw` is outside `[0.0, 1.0)`.
|
||||
/// - `MismatchedShape` if the outcome's rank count differs from `teams.len()`.
|
||||
/// - `WrongOutcomeKind` if `outcome` is not `Outcome::Ranked`.
|
||||
/// - `TieWithoutDrawProbability` if the outcome ties two teams while
|
||||
/// `p_draw` is zero: the truncation margin is then zero and the two-sided
|
||||
/// tie update evaluates `0/0`.
|
||||
pub fn ranked(
|
||||
teams: &[&[Rating<T, D>]],
|
||||
outcome: crate::Outcome,
|
||||
@@ -478,6 +490,12 @@ impl<T: Time, D: Drift<T>> Game<'_, T, D> {
|
||||
))
|
||||
}
|
||||
|
||||
/// # Errors
|
||||
///
|
||||
/// - `InvalidParameter` if `options.score_sigma` is not strictly positive,
|
||||
/// or is NaN.
|
||||
/// - `MismatchedShape` if the outcome's score count differs from `teams.len()`.
|
||||
/// - `WrongOutcomeKind` if `outcome` is not `Outcome::Scored`.
|
||||
pub fn scored(
|
||||
teams: &[&[Rating<T, D>]],
|
||||
outcome: crate::Outcome,
|
||||
@@ -515,6 +533,12 @@ impl<T: Time, D: Drift<T>> Game<'_, T, D> {
|
||||
))
|
||||
}
|
||||
|
||||
/// # Errors
|
||||
///
|
||||
/// Delegates to [`Game::ranked`] with default options, so it returns the
|
||||
/// same errors — in practice `WrongOutcomeKind` for a non-ranked outcome,
|
||||
/// or `TieWithoutDrawProbability` for a draw, since the default `p_draw`
|
||||
/// applies rather than one you chose.
|
||||
pub fn one_v_one(
|
||||
a: &Rating<T, D>,
|
||||
b: &Rating<T, D>,
|
||||
@@ -525,6 +549,10 @@ impl<T: Time, D: Drift<T>> Game<'_, T, D> {
|
||||
Ok((post[0][0], post[1][0]))
|
||||
}
|
||||
|
||||
/// # Errors
|
||||
///
|
||||
/// Wraps each player in a one-member team and delegates to
|
||||
/// [`Game::ranked`], so it returns the same errors.
|
||||
pub fn free_for_all(
|
||||
players: &[&Rating<T, D>],
|
||||
outcome: crate::Outcome,
|
||||
|
||||
Reference in New Issue
Block a user