- 운반표를 만든 한 곳(Router_Earthwork)에서 암 줄을 흙깎기와 같은 구성비(_split_by_rock)·갈래별 시공법으로 가름 → 운반거리·토공집계 운반 줄·인계·사토가 한 값 - 구성비가 비면 「암」 한 줄로 막음(깎기와 같은 사유) · 시공법 안 고른 갈래만 막음 · 무대(내역 밖) 줄은 안 막음 - 유토곡선 거리·다짐 부피는 그대로(몫대로 나눔 · 검산 차이 0) — C 까지 구성비로 맞추는 것은 (나) 차례 - 936be972: 구성비 없음 → 운반·적재·사토 암 전부 입력 사유(종전 리핑암 금액 섬) · 연암 60 리핑/보통암 40 발파 → 흙깎기 2,060.043/1,373.362 · 도자 38.123/25.416 · 덤프 112.195/74.797 · 사토 28.858/19.238 같은 몫 · 되돌림 Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016VBGFXB9AbJBwXP19z75Qq
111 lines
4.6 KiB
Python
111 lines
4.6 KiB
Python
"""암 운반량을 **구성비로 가르기** — ㉱ (가) (2026-09-14 브레인 판정 · 8-1 사용자 확정).
|
|
|
|
B06 의 암은 **한 종류 자리표시**다 — 토사 토글을 끄면 저장값이 `ripping_rock` 이 되지만 그 뜻은
|
|
「암」이고 「갈라 넣는 것은 설계내역 몫」(`B06_Section_UI_Cross_Design.ts` 머리 주석). 그런데 운반표·사토가
|
|
그 이름(리핑암)을 **값처럼** 넘겨, 깎기 암은 구성비가 비어 막히는데 운반 암은 금액이 섰다.
|
|
|
|
⇒ 운반표를 만든 **한 곳**(`Router_Earthwork`)에서 암 줄을 흙깎기와 **같은 구성비**(`_split_by_rock`)와
|
|
갈래별 시공법으로 가른다. 운반거리 탭·토공집계 운반 줄·인계·사토가 모두 이 표를 읽어 한 값이 된다.
|
|
⚠ 유토곡선 거리·다짐 부피는 그대로(자리표시 C 로 쌓은 값) — 부피를 몫대로 나눌 뿐이라 검산이 안 흔들림.
|
|
C 까지 구성비로 맞추는 것은 (나) 차례.
|
|
⚠ 구성비가 비면 「암」 한 줄로 **막는다** — 깎기와 같은 사유(지어낸 갈래로 금액을 세우지 않음).
|
|
"""
|
|
|
|
from __future__ import annotations
|
|
|
|
from typing import Any, Iterable
|
|
|
|
from B08_Quantity.B08_Quantity_Engine_EarthworkSummary import SummaryInput, _split_by_rock
|
|
from B08_Quantity.B08_Quantity_Engine_Handoff_Mapping import (
|
|
BLOCKED_INPUT_MISSING,
|
|
METHOD_TO_GROUND,
|
|
NOTE_METHOD_MISSING,
|
|
NOTE_ROCK_RATIO_MISSING,
|
|
)
|
|
|
|
#: 유토곡선이 넘기는 암 이름 — 둘 다 자리표시로 본다(옛 자료 `blasting_rock` 도 「암」).
|
|
ROCK_GROUNDS = ("리핑암", "발파암")
|
|
#: 몫대로 나누는 수량 칸 — 운반표 줄(`HaulSummary.build_table`).
|
|
SHARED_KEYS = ("volume_m3", "natural_m3", "work_m3m")
|
|
|
|
|
|
def rock_shares(
|
|
classes: Iterable[str], ratios_pct: dict[str, Any], methods: dict[str, str | None]
|
|
) -> list[dict[str, Any]]:
|
|
"""갈래별 몫 — `{rock_class, fraction, ground, blocked_reason, note}`. 흙깎기와 같은 안분."""
|
|
source = SummaryInput(rock_classes=list(classes), rock_ratios_pct=dict(ratios_pct or {}))
|
|
shares = []
|
|
for name, fraction, note in _split_by_rock(1.0, source):
|
|
ground = "암" if name == "암" else METHOD_TO_GROUND.get(methods.get(name) or "")
|
|
if name == "암":
|
|
reason = NOTE_ROCK_RATIO_MISSING
|
|
else:
|
|
reason = "" if ground else NOTE_METHOD_MISSING
|
|
shares.append(
|
|
{
|
|
"rock_class": name,
|
|
"fraction": fraction,
|
|
"ground": ground or name,
|
|
"blocked_reason": reason,
|
|
"note": note,
|
|
}
|
|
)
|
|
return shares
|
|
|
|
|
|
def split_rows(
|
|
rows: Iterable[dict[str, Any]], shares: list[dict[str, Any]]
|
|
) -> list[dict[str, Any]]:
|
|
"""암 줄을 몫마다 한 줄로 — 토사 줄은 그대로."""
|
|
out: list[dict[str, Any]] = []
|
|
for row in rows:
|
|
if row.get("ground") not in ROCK_GROUNDS:
|
|
out.append(row)
|
|
continue
|
|
for share in shares:
|
|
numbers = {
|
|
key: row[key] * share["fraction"]
|
|
for key in SHARED_KEYS
|
|
if isinstance(row.get(key), (int, float))
|
|
}
|
|
out.append(
|
|
{
|
|
**row,
|
|
**numbers,
|
|
"ground": share["ground"],
|
|
"rock_class": share["rock_class"],
|
|
"rock_split_note": share["note"],
|
|
"blocked_kind": BLOCKED_INPUT_MISSING if share["blocked_reason"] else None,
|
|
"blocked_reason": share["blocked_reason"],
|
|
}
|
|
)
|
|
return out
|
|
|
|
|
|
def split_amounts(
|
|
by_ground: dict[str, float], shares: list[dict[str, Any]] | None
|
|
) -> list[tuple[str, float, str, str | None, str]]:
|
|
"""갈래별 물량(사토) → `(갈래, 물량, 막힘 사유, 암 갈래, 원래 이름)`. 몫이 없으면 그대로."""
|
|
out = []
|
|
for label, amount in sorted(by_ground.items()):
|
|
if shares and label in ROCK_GROUNDS:
|
|
out.extend(
|
|
(s["ground"], amount * s["fraction"], s["blocked_reason"], s["rock_class"], label)
|
|
for s in shares
|
|
)
|
|
else:
|
|
out.append((label, amount, "", None, label))
|
|
return out
|
|
|
|
|
|
def apply_rock_split(
|
|
haul: dict[str, Any],
|
|
classes: Iterable[str],
|
|
ratios_pct: dict[str, Any],
|
|
methods: dict[str, str | None],
|
|
) -> None:
|
|
"""운반표(`rows`)를 자리에서 가르고 사토가 같은 몫을 쓰게 `rock_shares` 를 싣는다."""
|
|
shares = rock_shares(classes, ratios_pct, methods)
|
|
haul["rows"] = split_rows(haul.get("rows") or [], shares)
|
|
haul["rock_shares"] = shares
|