mirror of
https://github.com/Hestia-Homes/Model.git
synced 2026-06-08 11:17:27 +00:00
P2.3: delete table_12_cert_calibration.py (no remaining consumers)
ADR-0010 §2: the cert-calibration price table was bug-masking pre-March-2025 SAP values fit against a mixture-distribution of two spec-version regimes. P2.1 swapped the probe to SAP_10_2_SPEC_PRICES, P2.2 migrated the golden fixtures, leaving no external consumers. File deletion is mechanical at this point. Also updates the cert_to_inputs() docstring at L741-L751: removes the stale reference to CERT_CALIBRATION_PRICES, points at ADR-0010 and the Validation Cohort filter as the parity-validation mechanism. All 152 SAP + ml_training_data tests pass with the file gone. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
parent
28e9dd3864
commit
cd6ac9b16d
2 changed files with 7 additions and 135 deletions
|
|
@ -743,12 +743,13 @@ def cert_to_inputs(
|
|||
) -> CalculatorInputs:
|
||||
"""Build a typed `CalculatorInputs` aggregate from an `EpcPropertyData`.
|
||||
|
||||
`prices` defaults to the SAP 10.2/10.3 spec-mandated Table 12 values
|
||||
(`SAP_10_2_SPEC_PRICES`). For parity validation against the cert
|
||||
corpus's lodged ratings, pass `CERT_CALIBRATION_PRICES` from
|
||||
`domain.sap.tables.table_12_cert_calibration` — the cert assessor
|
||||
software diverges from the published spec on unit prices (see slice
|
||||
S-B9 + docs/sap-spec/PARITY_FINDINGS.md)."""
|
||||
`prices` defaults to `SAP_10_2_SPEC_PRICES` (SAP 10.2, 14-03-2025
|
||||
amendment) and is the only price set the codebase uses, per
|
||||
ADR-0010. The historical cert-calibration price table was deleted
|
||||
in P2.3 (commit log) once its bug-masking role was understood;
|
||||
parity validation now relies on the Validation Cohort filter
|
||||
(inspection_date ≥ 2025-07-01) rather than a per-cert price
|
||||
override."""
|
||||
dim = dimensions_from_cert(epc)
|
||||
window_total_area, window_avg_u = _window_total_area_and_avg_u(epc.sap_windows)
|
||||
exposure = _dwelling_exposure(epc.dwelling_type)
|
||||
|
|
|
|||
|
|
@ -1,129 +0,0 @@
|
|||
"""Empirical fuel-price table that matches the cert corpus's lodged
|
||||
ratings — not the spec-mandated SAP 10.2/10.3 Table 12.
|
||||
|
||||
These prices are an EMPIRICAL CALIBRATION: the cert assessor software
|
||||
that produced `energy_rating_current` in the corpus appears to use
|
||||
prices ~10-25% lower than the SAP 10.2 spec mandates (§12.2). Whether
|
||||
that gap comes from a pre-amendment SAP 10.2 publication, an RdSAP §19
|
||||
override, or frozen lodgement-time prices is an open investigation
|
||||
(see commit S-B9 + dev discussion thread).
|
||||
|
||||
Use this table when running parity validation against
|
||||
`energy_rating_current` from the corpus — the calculator will then
|
||||
produce values directly comparable to the cert. For new ratings or
|
||||
forward-looking calculations, use `domain.sap.tables.table_12` (SAP 10.2
|
||||
spec-correct, identical to SAP 10.3).
|
||||
|
||||
The values come verbatim from the prior
|
||||
`domain.ml.sap_efficiencies._FUEL_UNIT_PRICE` table that the legacy ML
|
||||
pipeline had been silently using; CO2 factors mirror the SAP 10.2
|
||||
spec since the bias regression is cost-driven, not emissions-driven.
|
||||
"""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
from typing import Final
|
||||
|
||||
|
||||
UNIT_PRICE_P_PER_KWH: Final[dict[int, float]] = {
|
||||
# Gas fuels
|
||||
1: 3.48, # mains gas
|
||||
2: 7.60, # bulk LPG
|
||||
3: 10.30, # bottled LPG (main)
|
||||
5: 3.48, # bottled LPG (secondary)
|
||||
9: 7.60, # LPG SC11F
|
||||
7: 0.0, # biogas
|
||||
# Liquid fuels
|
||||
4: 5.44, # heating oil
|
||||
71: 7.64, 73: 7.64, 75: 6.10, 76: 47.0,
|
||||
# Solid fuels
|
||||
11: 3.67, 15: 3.64, 12: 4.61, 20: 4.23, 22: 5.81, 23: 5.26,
|
||||
21: 3.07, 10: 3.99,
|
||||
# Electricity
|
||||
30: 13.19, # standard tariff
|
||||
32: 15.29, # 7h high
|
||||
31: 5.50, # 7h low (Economy-7 off-peak)
|
||||
34: 14.68, # 10h high
|
||||
33: 7.50, # 10h low
|
||||
38: 13.67, # 18h high
|
||||
40: 7.41, # 18h low
|
||||
35: 6.61, # 24h heating
|
||||
39: 13.19,
|
||||
60: 13.19,
|
||||
36: 13.19,
|
||||
# Heat networks
|
||||
51: 4.24, 52: 4.24, 53: 4.24, 54: 4.24, 55: 4.24, 56: 4.24,
|
||||
57: 4.24, 58: 4.24,
|
||||
41: 4.24, 42: 4.24, 43: 4.24, 44: 4.24,
|
||||
45: 2.97, 46: 2.97, 48: 2.97, 50: 0.0,
|
||||
47: 2.97, 49: 2.97,
|
||||
}
|
||||
_DEFAULT_P_PER_KWH: Final[float] = 3.48
|
||||
|
||||
|
||||
# Lifted from `domain.sap.tables.table_12.API_FUEL_TO_TABLE_12` since the
|
||||
# API enum → Table 12 code mapping is spec-stable.
|
||||
API_FUEL_TO_TABLE_12: Final[dict[int, int]] = {
|
||||
0: 30, 1: 1, 2: 2, 3: 3, 4: 4, 5: 15, 6: 20, 7: 23, 8: 21, 9: 10,
|
||||
10: 30, 11: 42, 12: 43, 13: 44, 14: 11, 15: 12, 16: 22, 17: 9,
|
||||
18: 75, 19: 76, 20: 51, 21: 52, 22: 53, 23: 55, 24: 54, 25: 41,
|
||||
26: 1, 27: 2, 28: 4, 29: 30,
|
||||
}
|
||||
|
||||
|
||||
def unit_price_p_per_kwh(fuel_code: int | None) -> float:
|
||||
"""Empirical cert-calibration unit price (p/kWh) for the given fuel
|
||||
code. Use only for parity validation; the SAP-spec answer is in
|
||||
`domain.sap.tables.table_12.unit_price_p_per_kwh`."""
|
||||
if fuel_code is None:
|
||||
return _DEFAULT_P_PER_KWH
|
||||
if fuel_code in UNIT_PRICE_P_PER_KWH:
|
||||
return UNIT_PRICE_P_PER_KWH[fuel_code]
|
||||
translated = API_FUEL_TO_TABLE_12.get(fuel_code)
|
||||
if translated is not None and translated in UNIT_PRICE_P_PER_KWH:
|
||||
return UNIT_PRICE_P_PER_KWH[translated]
|
||||
return _DEFAULT_P_PER_KWH
|
||||
|
||||
|
||||
# Economy-7 low-rate cert-calibration price — empirically matches what
|
||||
# the cert assessor software appears to charge on storage-heater
|
||||
# dwellings.
|
||||
E7_LOW_RATE_P_PER_KWH: Final[float] = 5.50
|
||||
STANDARD_ELECTRICITY_P_PER_KWH: Final[float] = 13.19
|
||||
|
||||
|
||||
def _build_cert_calibration_table():
|
||||
"""Lazy import to avoid the cert_to_inputs ↔ tables import cycle —
|
||||
the cert_to_inputs module defines `PriceTable`, but this module
|
||||
can't import from cert_to_inputs because cert_to_inputs imports the
|
||||
spec table_12. We expose a factory the caller uses to build the
|
||||
`PriceTable` value at validation-script init time."""
|
||||
from domain.sap.rdsap.cert_to_inputs import PriceTable
|
||||
|
||||
# Cert-calibration empirically extends the E7 off-peak set:
|
||||
# 191-196 direct-electric (boilers etc) — S-B11 finding
|
||||
# 401-409 electric storage heaters (spec-correct)
|
||||
# 421-425 high-heat-retention storage (spec-correct)
|
||||
# 691-696 electric room heaters — S-B14 finding (cert 0340-2394:
|
||||
# 73m² mid-floor flat, code 691, actual SAP 75, predicted
|
||||
# 56 before this; cert software applies off-peak to all-
|
||||
# electric dwellings regardless of heating typology).
|
||||
cert_calibration_e7_codes = frozenset(
|
||||
list(range(191, 197))
|
||||
+ list(range(401, 410))
|
||||
+ list(range(421, 426))
|
||||
+ list(range(691, 697))
|
||||
)
|
||||
return PriceTable(
|
||||
unit_price_p_per_kwh=unit_price_p_per_kwh,
|
||||
e7_low_rate_p_per_kwh=E7_LOW_RATE_P_PER_KWH,
|
||||
standard_electricity_p_per_kwh=STANDARD_ELECTRICITY_P_PER_KWH,
|
||||
e7_eligible_main_codes=cert_calibration_e7_codes,
|
||||
)
|
||||
|
||||
|
||||
def cert_calibration_prices():
|
||||
"""Returns a `PriceTable` populated with the empirical cert-
|
||||
calibration prices. Call from parity-validation scripts as
|
||||
`cert_to_inputs(epc, prices=cert_calibration_prices())`."""
|
||||
return _build_cert_calibration_table()
|
||||
Loading…
Add table
Reference in a new issue