[FIX] Eindeutige IDs und korrekte ZUORDNUNG der verpackten Separatoren
Beim CSV-Export von Mubea trugen Gefaellestrecke/VF/Kreisel und die aus ihnen erzeugten Separator-Kopien dieselbe ID (26 Dubletten 0001-0026), und die ZUORDNUNG der Separatoren zeigte auf den falschen Carrier. ssg-id-check-all: neue Phase 0 ermittelt das globale Maximum der bereits vergebenen IDs, BEVOR die erste neue ID vergeben wird (ausgelagert nach ssg-id-max-in-ss, das auch ssg-id-max nutzt). Bisher wurde max-id erst waehrend Phase 1 mitgezogen (Start 0); da (ssget "X" ...) in BricsCAD die zuletzt erzeugten Entities zuerst liefert, standen die noch ID-losen Separator-Kopien ganz vorne und bekamen 0001, 0002, ... - genau die IDs der weiter hinten liegenden Wrapper-Bloecke. Phase 2 konnte das nicht heilen, weil frisch vergebene IDs nicht in id-map landen. ssg-collect-nested-inserts: fuehrt Position, Z-Drehung und Skalierung jetzt ueber alle Verschachtelungsebenen mit (Records statt nackter Entity-Namen). Vorher gab die Rekursion Entities tieferer Ebenen mit ihrer ROH-Position aus der Zwischen-Blockdefinition zurueck - zwei Separatoren an derselben lokalen Stelle in zwei verschieden platzierten Zwischenbloecken landeten dadurch auf exakt derselben Weltposition. csv:sep-proxies-erzeugen: die Kopie steht jetzt exakt auf Position/Drehung/ Skalierung ihres verpackten Vorbilds; der kosmetische Versatz von 500 mm ist weg (er kippte Separatoren am Kettenende in die Boundingbox des Nachbar- Carriers). Der vla-InsertBlock-Aufruf ist gekapselt, damit ein Sonderfall nur diese eine Kopie ausfallen laesst statt den ganzen Export abzubrechen. csv:sep-proxies-zuordnung-setzen (neu, laeuft NACH ssg-id-check-all, da ein frisch gebauter Wrapper vorher keine ID hat): fuer einen VERPACKTEN Separator ist der Carrier bekannt - es ist der Wrapper, in dem er steckt. ZUORDNUNG wird daher auf die Wrapper-ID gesetzt (Separator in VF 0010 -> ZUORDNUNG 0010) und ueber *cs-sep-fix-by-handle* festgenagelt: cs-zuordnung-lauf uebernimmt sie unveraendert statt sie geometrisch neu zu raten, und csv:block-to-json reicht sie als "zuordnung_fix" an export_csv.py durch. Ohne das ueberschrieb compute_sensor_zuordnung (Prioritaet GF > Foerderer > Kreiselhaelfte) den bekannten Wert - in der Mubea-Zeichnung landeten 26 in VF/GF verpackte Separatoren so bei einer Kreiselhaelfte. export_csv.py: respektiert "zuordnung_fix" und ersetzt eine vorhandene ZUORDNUNG nicht mehr durch "nicht zugeordnet" - nur ein echter Treffer ueberschreibt, wie im Docstring von compute_sensor_zuordnung beschrieben. tests/test_export_ids.py (neu): prueft je tests/output/*_export.csv, dass jede TeileId hoechstens einmal vorkommt und jede Sensor-Zuordnung auf eine existierende TeileId zeigt. Gegen die fehlerhafte Mubea-CSV schlaegt der Test mit allen 26 Dubletten an. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
+55
-4
@@ -60,6 +60,16 @@
|
||||
;;; Box, damit Sensoren knapp am Rand noch erfasst werden.
|
||||
;;; 6. Bei zugeordneten Sensoren wird die ID des Carriers (Attribut
|
||||
;;; "ID") in das Sensor-Attribut ZUORDNUNG geschrieben.
|
||||
;;; 6a. AUSNAHME zu 1-5: Separatoren, deren Entity-Handle in
|
||||
;;; *cs-sep-fix-by-handle* steht, werden NICHT geometrisch
|
||||
;;; zugeordnet, sondern dem dort genannten Carrier. Das sind die
|
||||
;;; temporaeren Kopien der in VF_n/GF_n/KREISEL_n VERPACKTEN
|
||||
;;; Separator_SP-Symbole (csv:sep-proxies-erzeugen/-zuordnung-
|
||||
;;; setzen, export.lsp): fuer sie ist der Carrier bekannt - es ist
|
||||
;;; der Wrapper-Block, in dem sie stecken -, und Raten per
|
||||
;;; Boundingbox waere schlechter als die bekannte Wahrheit (am
|
||||
;;; Kettenende ueberlappen sich Carrier-Boxen). Existiert der
|
||||
;;; genannte Carrier nicht (mehr), greifen wieder 1-5.
|
||||
;;; 7. Sensoren, zu denen ueberhaupt kein Carrier existiert (leere
|
||||
;;; Zeichnung), werden mit einem Kreis auf dem Layer *mark-layer*
|
||||
;;; markiert (zentriert auf den Sensor).
|
||||
@@ -92,6 +102,17 @@
|
||||
;; zugeordneten Carriers geschrieben wird.
|
||||
(setq *zuordnung-tag* "ZUORDNUNG")
|
||||
|
||||
;; Festgenagelte (nicht geometrisch zu ermittelnde) Separator-Zuordnungen:
|
||||
;; Assoc-Liste (entity-handle . carrier-id). Wird von csv:sep-proxies-
|
||||
;; zuordnung-setzen (export.lsp) fuer die temporaeren Kopien der in
|
||||
;; VF_n/GF_n/KREISEL_n VERPACKTEN Separator_SP-Symbole gefuellt - fuer die ist
|
||||
;; der Carrier bekannt (es ist der Wrapper, in dem sie stecken) und muss
|
||||
;; nicht ueber Boundingbox/Distanz geraten werden. Bei ueberlappenden
|
||||
;; Carrier-Boxen (Kettenende an einem Kreisel) wuerde die Geometrie sonst
|
||||
;; leicht den Nachbarn treffen. Leer = alles rein geometrisch (Normalfall
|
||||
;; beim interaktiven ZAEHLE_SEP_SCAN).
|
||||
(if (null *cs-sep-fix-by-handle*) (setq *cs-sep-fix-by-handle* nil))
|
||||
|
||||
;; Markierung von Sensoren ohne jeglichen Carrier: Kreis auf eigenem Layer.
|
||||
(setq *mark-layer* "S_SENSOR_UNZUGEORDNET")
|
||||
(setq *mark-color* 2) ;; 2 = Gelb
|
||||
@@ -362,6 +383,21 @@
|
||||
)
|
||||
)
|
||||
|
||||
;;; ------------------------------------------------------------
|
||||
;;; Carrier-Record ueber seine ID finden (siehe *cs-sep-fix-by-handle*).
|
||||
;;; carriers = Liste von Records (ename tagScan tagSep minx miny maxx
|
||||
;;; maxy cx cy id label), id an Position 9.
|
||||
;;; Rueckgabe: Record oder nil, wenn kein Carrier diese ID traegt.
|
||||
;;; ------------------------------------------------------------
|
||||
(defun cs-carrier-by-id (id carriers / rec treffer)
|
||||
(if (and id (/= id ""))
|
||||
(foreach rec carriers
|
||||
(if (and (null treffer) (= (nth 9 rec) id))
|
||||
(setq treffer rec)))
|
||||
)
|
||||
treffer
|
||||
)
|
||||
|
||||
;;; ------------------------------------------------------------
|
||||
;;; Zaehler in einer Assoc-Liste (Schluessel = ename) erhoehen.
|
||||
;;; ------------------------------------------------------------
|
||||
@@ -600,6 +636,7 @@
|
||||
scanCounts sepCounts n-scan-unassigned n-sep-unassigned
|
||||
n-strittig n-zuordnung-fehlt alt
|
||||
s sent spt res mode rec best-d second-rec second-d
|
||||
vorgabe-id vorgabe-rec
|
||||
scanner-id contested handle
|
||||
en nm2 ns nsep newS newP okS okP eintrag)
|
||||
(setq carriers nil scanlist nil seplist nil
|
||||
@@ -719,8 +756,19 @@
|
||||
;; ANZAHL_SEPARATOR-Summe auch bei Sonderfaellen stimmt). ---
|
||||
(foreach s seplist
|
||||
(setq sent (car s) spt (cadr s))
|
||||
(setq res (cs-resolve-sensor spt carriers grid))
|
||||
(setq mode (nth 0 res) rec (nth 1 res))
|
||||
;; Festgenagelte Zuordnung (verpackter Separator, Carrier bekannt -
|
||||
;; siehe *cs-sep-fix-by-handle*) hat Vorrang vor der Geometrie. Nur
|
||||
;; wenn der genannte Carrier gar nicht (mehr) existiert, wird
|
||||
;; geometrisch zugeordnet.
|
||||
(setq vorgabe-id (cdr (assoc (cdr (assoc 5 (entget sent))) *cs-sep-fix-by-handle*)))
|
||||
(setq vorgabe-rec (cs-carrier-by-id vorgabe-id carriers))
|
||||
(if vorgabe-rec
|
||||
(setq mode 'vorgabe rec vorgabe-rec)
|
||||
(progn
|
||||
(setq res (cs-resolve-sensor spt carriers grid))
|
||||
(setq mode (nth 0 res) rec (nth 1 res))
|
||||
)
|
||||
)
|
||||
(cond
|
||||
((eq mode 'none)
|
||||
(setq n-sep-unassigned (1+ n-sep-unassigned))
|
||||
@@ -728,12 +776,15 @@
|
||||
((null rec) nil) ;; Sicherheitsnetz - tritt bei bbox/distance nicht auf
|
||||
(t
|
||||
(setq sepCounts (cs-bump sepCounts (car rec)))
|
||||
;; Abweichung nur bei geometrischer Zuordnung als Korrektur melden -
|
||||
;; bei mode 'vorgabe ist der geschriebene Wert die Vorgabe selbst,
|
||||
;; keine Korrektur einer Fehl-Zuordnung.
|
||||
(setq alt (cs-get-att-str sent *zuordnung-tag*))
|
||||
(if (and alt (/= alt "") (/= alt (nth 9 rec)))
|
||||
(if (and (not (eq mode 'vorgabe)) alt (/= alt "") (/= alt (nth 9 rec)))
|
||||
(setq *cs-korrekturen*
|
||||
(cons (list "Separator" (cs-get-att-str sent "ID") alt (nth 9 rec))
|
||||
*cs-korrekturen*)))
|
||||
(if (member mode '(bbox distance))
|
||||
(if (member mode '(vorgabe bbox distance))
|
||||
(if (not (cs-set-att sent *zuordnung-tag* (nth 9 rec)))
|
||||
(setq n-zuordnung-fehlt (1+ n-zuordnung-fehlt))))
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user