clophfit.fitting.robust_se#
Heteroskedasticity-robust (sandwich) standard errors for a fitted well.
The usual standard error trusts the weights: it is s^2 (J'J)^-1, which is
only right when the residuals really do have the variance the weights assumed.
On these plates they do not - the scatter grows with signal, and with plate
position - yet weighting sigma to match costs precision in K, because it
down-weights the plateau points that fix S0 and S1 (see
clophfit.fitting.gain_calibration).
The sandwich estimator takes the other route: keep the weights that fit best and
repair only the uncertainty. With J the weighted Jacobian and e the
weighted residuals,
where Omega is diagonal in the observed squared residuals rather than in an
assumed sigma: e_i^2 (HC0), e_i^2 / (1 - h_i) (HC2) or
e_i^2 / (1 - h_i)^2 (HC3), h the leverage. HC3 is the default here
because the series are short - seven points and three parameters per label - and
HC0 is badly biased in small samples.
What this buys: an interval for K that reflects the scatter the well actually shows, including the part the noise model does not describe. What it does not buy: a different K.
Read the size of the correction with care on short series. On simulated seven-step, two-label wells (nine residual degrees of freedom) HC3 inflates K’s standard error by 1.25x whether the noise is homoscedastic or strongly signal-dependent, and it lifts 95% coverage from 0.91 to 0.95 - but so does using a Student-t quantile with the classical error, which covers 0.94-0.95 while HC3 with the same quantile over-covers at 0.96-0.97. At this series length the inflation is mostly a small-sample correction and not evidence of misspecification; the sandwich earns its keep where the design is longer or the wells are pooled.
Functions#
|
Sandwich covariance of the parameters, from the residuals as they are. |
|
Robust standard error per parameter (the square root of |
|
Model-based and robust standard errors of K, per well. |
Module Contents#
- clophfit.fitting.robust_se.hc_covariance(jac, resid, *, kind='HC3')#
Sandwich covariance of the parameters, from the residuals as they are.
- Parameters:
jac (np.ndarray) –
(n, p)Jacobian of the residuals actually minimised (weighted, if the fit was weighted).resid (np.ndarray) – Those residuals, on the same scale.
kind (HCKind) – Small-sample correction:
HC0none,HC2divides each squared residual by1 - h,HC3by(1 - h)^2(the default).
- Returns:
(p, p)covariance, or None when the Jacobian is rank deficient.- Return type:
np.ndarray | None
Examples
A straight line whose noise grows with x: the robust slope error exceeds the classical one, which believes the constant variance it was given.
>>> import numpy as np >>> rng = np.random.default_rng(0) >>> x = np.linspace(0, 1, 200) >>> j = np.column_stack([np.ones_like(x), x]) >>> e = rng.normal(0, 0.1 + 2 * x) >>> cov = hc_covariance(j, e - j @ np.linalg.lstsq(j, e, rcond=None)[0]) >>> classical = np.var(e, ddof=2) * np.linalg.inv(j.T @ j) >>> bool(cov[1, 1] > classical[1, 1]) True
- clophfit.fitting.robust_se.sandwich_se(jac, resid, *, kind='HC3')#
Robust standard error per parameter (the square root of
hc_covariance()).- Parameters:
jac (np.ndarray) – Weighted Jacobian.
resid (np.ndarray) – Weighted residuals.
kind (HCKind) – Small-sample correction.
- Returns:
Standard errors, or None when the Jacobian is rank deficient.
- Return type:
np.ndarray | None
- clophfit.fitting.robust_se.robust_k_se(table, params, *, is_ph=True, kind='HC3')#
Model-based and robust standard errors of K, per well.
Each well is linearised at its fitted parameters (the same weighted Jacobian the residual tests use, residuals projected through
I - Hso a posterior mean is treated as its least-squares equivalent). K is the first column of that design, so its standard error is read from the two covariances: the classical one,s^2 (J'J)^-1, which trusts the weights, and the sandwich one, which does not.- Parameters:
table (pd.DataFrame) – Residual table with
well,label,x,raw_res,sigma.params (Mapping[str, Mapping[str, float]]) – Well to its fitted
K,S0_<label>,S1_<label>.is_ph (bool) – pH titration (else concentration).
kind (HCKind) – Small-sample correction for the sandwich.
- Returns:
Indexed by well:
k_se_model,k_se_robust,ratio(robust / model),n_pointsanddof.- Return type:
pd.DataFrame