docs: classify meldet auf Wunsch den Anteil unbekannter Pixel
Aufgabe 6 braucht den Anteil für den Abbruch über 5 Prozent; die Signatur in Aufgabe 3 kannte ihn bisher nicht. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
1 parent
a94c09e279
commit
d40d96a800
1 file changed
+15
-3
@@ -534,6 +534,13 @@ def test_unknown_pixels_are_filled_from_neighbours():
|
||||
labels = classify(img)
|
||||
assert (labels == CLASSES["stadt"]).all()
|
||||
|
||||
def test_reports_the_share_of_unknown_pixels():
|
||||
img = block(PALETTE["stadt"], 16)
|
||||
img[7:9, 7:9] = (255, 0, 255) # 4 von 256 Pixeln passen zu keiner Farbe
|
||||
labels, share = classify(img, report_unknown=True)
|
||||
assert (labels == CLASSES["stadt"]).all()
|
||||
assert abs(share - 4 / 256) < 1e-9
|
||||
|
||||
def test_shares_sum_to_one():
|
||||
img = np.concatenate([block(PALETTE["wasser"], 8), block(PALETTE["land"], 8)], axis=1)
|
||||
shares = class_shares(classify(img))
|
||||
@@ -569,18 +576,23 @@ UNKNOWN = 255
|
||||
MAX_DELTA_E = 14.0 # darüber gilt ein Pixel als unbekannt (Beschriftung, Icon, Kante)
|
||||
|
||||
|
||||
def classify(rgb: np.ndarray) -> np.ndarray:
|
||||
"""Ordnet jedes Pixel der nächsten Palettenfarbe zu; Ausreißer werden aufgefüllt."""
|
||||
def classify(rgb: np.ndarray, report_unknown: bool = False):
|
||||
"""Ordnet jedes Pixel der nächsten Palettenfarbe zu; Ausreißer werden aufgefüllt.
|
||||
|
||||
Mit report_unknown=True kommt zusätzlich der Anteil der Pixel zurück, die vor dem
|
||||
Auffüllen zu keiner Legendenfarbe passten. Aufgabe 6 bricht darüber bei über 5 % ab.
|
||||
"""
|
||||
lab = rgb2lab(rgb.astype(np.float32) / 255.0)
|
||||
ref = rgb2lab(np.array([list(PALETTE.values())], dtype=np.float32) / 255.0)[0]
|
||||
dist = np.linalg.norm(lab[:, :, None, :] - ref[None, None, :, :], axis=3)
|
||||
labels = dist.argmin(axis=2).astype(np.uint8)
|
||||
unknown = dist.min(axis=2) > MAX_DELTA_E
|
||||
share = float(unknown.mean())
|
||||
if unknown.any():
|
||||
# Nächstes bekanntes Pixel übernehmen.
|
||||
idx = ndi.distance_transform_edt(unknown, return_distances=False, return_indices=True)
|
||||
labels = labels[tuple(idx)]
|
||||
return labels
|
||||
return (labels, share) if report_unknown else labels
|
||||
|
||||
|
||||
def class_shares(labels: np.ndarray) -> dict[str, float]:
|
||||
|
||||
Reference in new issue
Block a user