Target related hard-negative contexts
GeoIntel release gates / Compile, test, contracts and builds (push) Canceled after 0s
GeoIntel release gates / Python and npm vulnerability policy (push) Canceled after 0s
GeoIntel release gates / GIS image, SBOM and container scan (push) Canceled after 0s

This commit is contained in:
Jens
2026-07-29 18:27:54 +02:00
parent a56df8b1ed
commit cfce3e64ec
4 changed files with 70 additions and 2 deletions
+27 -2
View File
@@ -12,6 +12,15 @@ from pathlib import Path
from typing import Any
PRECISION_NEGATIVE_CONTEXTS = {
"coastal-urban": {"port-hard-negative", "dunes-negative"},
"industrial": {"industrial-hard-negative", "rail-hard-negative", "port-hard-negative"},
"ribbon-development": {"farmland-hard-negative", "forest-hard-negative"},
"rural-town": {"farmland-hard-negative", "forest-hard-negative", "quarry-hard-negative"},
"regional-architecture": {"forest-hard-negative", "quarry-hard-negative"},
}
def file_sha256(path: Path) -> str:
digest = hashlib.sha256()
with path.open("rb") as stream:
@@ -94,6 +103,12 @@ def build_sampling(
and metrics["precision"] < gates["min_region_precision"]
):
weak_precision_contexts.add(key)
targeted_negative_contexts = set(weak_precision_contexts)
for region, context in weak_precision_contexts:
targeted_negative_contexts.update(
(region, related)
for related in PRECISION_NEGATIVE_CONTEXTS.get(context, set())
)
base_paths_by_region: dict[str, list[str]] = {}
extra_paths_by_region: dict[str, list[str]] = {}
@@ -120,12 +135,19 @@ def build_sampling(
if tile["label_count"] == 0 and (background_failed or region in weak_precision_regions):
repeat = (
context_negative_repeat
if context_key in weak_precision_contexts
if context_key in targeted_negative_contexts
else negative_repeat
)
path = str(Path(tile["image_path"]).resolve())
base_paths_by_region.setdefault(region, []).append(path)
extra_paths_by_region.setdefault(region, []).extend([path] * (repeat - 1))
extras = extra_paths_by_region.setdefault(region, [])
repeated = [path] * (repeat - 1)
if tile["label_count"] == 0 and context_key in targeted_negative_contexts:
# Preserve the most diagnostic hard-negative repeats when the
# regional cap has to remove lower-priority repetition.
extras[:0] = repeated
else:
extras.extend(repeated)
selected_samples.add(tile["sample_slug"])
pre_cap_counts = Counter({
@@ -163,6 +185,9 @@ def build_sampling(
"weak_precision_regions": sorted(weak_precision_regions),
"weak_recall_contexts": [f"{region}:{context}" for region, context in sorted(weak_recall_contexts)],
"weak_precision_contexts": [f"{region}:{context}" for region, context in sorted(weak_precision_contexts)],
"targeted_negative_contexts": [
f"{region}:{context}" for region, context in sorted(targeted_negative_contexts)
],
"background_gate_failed": background_failed,
"positive_repeat": positive_repeat,
"negative_repeat": negative_repeat,