From c1a8c27bc1aa8b03c77d877fe1ed0954d67ff16e Mon Sep 17 00:00:00 2001 From: Khalim Conn-Kowlessar Date: Tue, 7 Jul 2026 22:06:30 +0000 Subject: [PATCH] =?UTF-8?q?Sub-Ladder=20rungs=20fill=20from=20the=20highes?= =?UTF-8?q?t-yield=20segment=20first=20=F0=9F=9F=A9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-Authored-By: Claude Fable 5 --- .../modelling/generators/solar_recommendation.py | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/domain/modelling/generators/solar_recommendation.py b/domain/modelling/generators/solar_recommendation.py index c344d0447..6b5b18f4a 100644 --- a/domain/modelling/generators/solar_recommendation.py +++ b/domain/modelling/generators/solar_recommendation.py @@ -195,13 +195,19 @@ _MIN_SUB_LADDER_PANELS = 2 def _resized_to( config: SolarPanelConfiguration, panels: int ) -> SolarPanelConfiguration: - """A copy of ``config`` filled to ``panels`` panels, each kept segment's - yearly energy scaled pro-rata (conservative: Google places panels - best-first within a segment, so the kept panels' true yield is at least - the pro-rata figure).""" + """A copy of ``config`` filled to ``panels`` panels — taken from the + highest per-panel-yield segments first (the ADR-0038 fill-by-generation + precedent) — each kept segment's yearly energy scaled pro-rata + (conservative: Google places panels best-first within a segment, so the + kept panels' true yield is at least the pro-rata figure).""" + by_yield: list[SolarRoofSegment] = sorted( + config.segments, + key=lambda s: s.yearly_energy_dc_kwh / s.panels_count, + reverse=True, + ) kept: list[SolarRoofSegment] = [] remaining: int = panels - for segment in config.segments: + for segment in by_yield: if remaining <= 0: break take: int = min(segment.panels_count, remaining)