Skip to content

Configuration

rucola.RunConfig(tests=None, mode='ratio', run_consensus='majority', min_series_years=20, max_gap_years=None, max_neighbors=10, min_correlation=0.5, max_distance_km=None, station_ids=None, progress=False, on_step=None) dataclass

Configuration for the González-Rouco six-step detection procedure.

Parameters:

Name Type Description Default
tests list[HomogenizationTest] | None

Homogeneity tests to run at each step. Defaults to [SNHTTest()]. Pass multiple tests for consensus detection.

None
mode CorrectionMode

"ratio" (multiplicative, precipitation) or "difference" (additive, temperature).

'ratio'
run_consensus ConsensusRule

How many tests must agree to classify a station as inhomogeneous during the six-step procedure. "majority" (default), "any" (most sensitive), or "unanimous". "strongest_signal" is accepted but treated as "any" at detection time; its special tiebreak behaviour only applies in :class:NormalizationConfig.

'majority'
min_series_years int

Minimum non-null annual values required to process a station (default: 20).

20
max_gap_years int | None

Stations with a consecutive null gap exceeding this are excluded.

None
max_neighbors int

Maximum number of reference stations (default: 10).

10
min_correlation float

Minimum Pearson correlation to include a neighbor (default: 0.5).

0.5
max_distance_km float | None

Search radius for neighbors in km. None disables the filter.

None
station_ids list[str] | None

Restrict the run to this subset of station IDs.

None

rucola.NormalizationConfig(consensus='majority', break_window_years=2, tiebreak='strongest_signal', min_correction_magnitude=0.0, min_relative_signal=1.0, max_corrections_per_station=2, min_years_from_end=5, predicate=None, overrides=None) dataclass

Configuration for how detections are turned into corrections.

Parameters:

Name Type Description Default
consensus ConsensusRule

How many tests must agree to accept a break. "unanimous" — all tests; "majority" — more than half; "any" — at least one; "strongest_signal" — always use the test with the highest relative signal, ignoring the others.

'majority'
break_window_years int

Tolerance (±years) within which two tests are considered to agree on the same break year.

2
tiebreak Tiebreak

What to do when no consensus is reached. "strongest_signal" — use the detection with the highest relative signal; "skip" — do not correct this station/step.

'strongest_signal'
min_correction_magnitude float

Ignore corrections below this absolute magnitude (ratio: |factor − 1|; difference: |factor|).

0.0
min_relative_signal float

Minimum ratio of test statistic to critical value required to accept a break (default: 1.0). Should match the value used on the :class:HomogenizationTest instances during detection.

1.0
max_corrections_per_station int

Cap on the number of breaks applied per station.

2
predicate BreakPredicate | None

Optional :class:BreakPredicate (or composed predicate) to filter which detected breaks are accepted. Fully serializable.

Example::

from rucola import YearBetween, StationIn, StepIn
NormalizationConfig(
    predicate=YearBetween(min=1960, max=2010) & ~StepIn({1, 2})
)
None
min_years_from_end int

Breaks detected within this many years of either series boundary are rejected as edge-effect artefacts (Hawkins 1977). Must match the value used by the homogeneity tests during detection (default: 5).

5
overrides dict[str, list[tuple[int, float]]] | None

Per-station manual corrections that replace the algorithmically detected breaks entirely. Dict mapping station_id to a list of (break_year, factor) tuples.

None

Break Predicates

rucola.BreakPredicate

Bases: ABC

Abstract base for composable, serializable break predicates.

Combine predicates with & (AND), | (OR), and ~ (NOT):

from rucola import YearBetween, StationIn p = YearBetween(min=1960, max=2010) & StationIn({"S1", "S3"}) p2 = YearBetween(min=1950, max=1960) | YearBetween(min=2000, max=2010) p3 = ~StepIn({1, 2})

__call__(info) abstractmethod

Return True to accept the break, False to discard it.

Source code in src/rucola/_normalization.py
@abstractmethod
def __call__(self, info: BreakInfo) -> bool:
    """Return True to accept the break, False to discard it."""

from_dict(d) classmethod

Deserialise from a dict produced by to_dict.

Source code in src/rucola/_normalization.py
@classmethod
def from_dict(cls, d: dict) -> BreakPredicate:
    """Deserialise from a dict produced by to_dict."""
    pred_type = d["type"]
    if pred_type not in _PRED_REGISTRY:
        msg = f"Unknown predicate type {pred_type!r}. Known: {sorted(_PRED_REGISTRY)}"
        raise ValueError(msg)
    return _PRED_REGISTRY[pred_type]._from_dict(d)  # type: ignore[attr-defined]  # noqa: SLF001

to_dict() abstractmethod

Serialise to a JSON-compatible dict.

Source code in src/rucola/_normalization.py
@abstractmethod
def to_dict(self) -> dict:
    """Serialise to a JSON-compatible dict."""

rucola.BreakInfo(station_id, break_year, factor, step, mode, test_results, n_neighbors=0) dataclass

Context passed to a :class:BreakPredicate for each candidate correction.

Parameters:

Name Type Description Default
station_id str

The station being evaluated.

required
break_year int

Consensus break year resolved from the test results.

required
factor float

Correction factor (ratio: multiplicative; difference: additive).

required
step int

Procedure step (1–6) at which this break was detected.

required
mode CorrectionMode

Correction mode — "ratio" or "difference".

required
test_results list[TestResult]

Individual results from each homogeneity test, including each test's suggested break year and test statistic.

required
n_neighbors int

Number of reference stations used to build the reference series at this step. Used by :class:NeighborCountAbove.

0

rucola.YearBetween(min=None, max=None) dataclass

Bases: BreakPredicate

Accept breaks whose year falls within [min, max] (inclusive, both optional).

Parameters:

Name Type Description Default
min int | None

Earliest acceptable break year.

None
max int | None

Latest acceptable break year.

None

rucola.StationIn(station_ids=frozenset()) dataclass

Bases: BreakPredicate

Accept breaks only for stations in the given set.

Parameters:

Name Type Description Default
station_ids Set[str]

Whitelist of station IDs to correct. All others are left uncorrected.

frozenset()

rucola.StepIn(steps=frozenset()) dataclass

Bases: BreakPredicate

Accept breaks detected in specific procedure steps.

Parameters:

Name Type Description Default
steps Set[int]

Set of step numbers to accept (1–6; step 6 is represented as 61/62 internally).

frozenset()

rucola.MagnitudeAbove(threshold=0.0) dataclass

Bases: BreakPredicate

Accept breaks whose correction magnitude exceeds a threshold.

Magnitude is |factor - 1| in ratio mode and |factor| in difference mode.

Parameters:

Name Type Description Default
threshold float

Minimum absolute correction magnitude.

0.0

rucola.TestSignificant(test_name='') dataclass

Bases: BreakPredicate

Accept breaks where a specific test flagged the series as significant.

Parameters:

Name Type Description Default
test_name str

Test name to require (e.g. "snht", "buishand", "pettitt").

''

rucola.SignalAbove(threshold=1.0) dataclass

Bases: BreakPredicate

Accept breaks where the maximum relative signal exceeds a threshold.

Relative signal is test_statistic / critical_value; values above 1.0 are significant. Use this to require a stronger signal than the test's own 95 % threshold without changing the critical value.

Parameters:

Name Type Description Default
threshold float

Minimum relative signal required across any test result.

1.0

rucola.NSignificantAbove(n=1) dataclass

Bases: BreakPredicate

Accept breaks where at least n tests are significant.

Provides finer control than the consensus rule on :class:NormalizationConfig, which uses relative thresholds (any / majority / unanimous). Use this when you want an absolute count independent of how many tests were run.

Parameters:

Name Type Description Default
n int

Minimum number of significant tests required.

1

rucola.NeighborCountAbove(n=1) dataclass

Bases: BreakPredicate

Accept breaks detected using at least n reference stations.

Breaks built from very few neighbors are less reliable. This predicate lets you discard detections that lacked a solid reference pool.

Parameters:

Name Type Description Default
n int

Minimum number of neighbors required.

1