| |
 | Gut zu wissen: Hilfreiche Tipps und Tricks aus der Praxis prägnant, und auf den Punkt gebracht für Autodesk Produkte |
[an error occurred while processing this directive]
Autor
|
Thema: Grosse Listen wegen Performance zerteilen (96 mal gelesen)
|
Peter2 Ehrenmitglied V.I.P. h.c.

 Beiträge: 3880 Registriert: 15.10.2003 Win 10 bzw. 11 / 64 Pro AutoCAD MAP 3D 2023 BricsCAD 24
|
erstellt am: 31. Mrz. 2025 13:21 <-- editieren / zitieren --> Unities abgeben:         
Ich habe aus dem Einlesen von Textdateien manchmal Listen, die 700.000 - 900.000 Einträge (hier: Textzeilen haben). Die muss ich von 0 bis 900.000 der Reihe nach durchgehen. Jetzt frage ich mich, ob es einen Geschwindigkeitszugriff bringen kann, die Liste in Teillisten von ca. 300.000 zu zerlegen und dann jeweils dreimal von 1-300000 zu arbeiten. Natürlich kostet das Zerlegen Zeit und es ist auch nicht klar, ob der Befehl (nth 900000 liste) länger braucht als (nth 30 liste). Ich weiss es nicht - weiss es jemand von euch? Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
Brischke Moderator CAD on demand GmbH
       

 Beiträge: 4193 Registriert: 17.05.2001 AutoCAD 20XX, defun-tools (d-tools.eu)
|
erstellt am: 31. Mrz. 2025 13:24 <-- editieren / zitieren --> Unities abgeben:          Nur für Peter2
|
Peter2 Ehrenmitglied V.I.P. h.c.

 Beiträge: 3880 Registriert: 15.10.2003 Win 10 bzw. 11 / 64 Pro AutoCAD MAP 3D 2023 BricsCAD 24
|
erstellt am: 31. Mrz. 2025 13:29 <-- editieren / zitieren --> Unities abgeben:         
|
archtools Mitglied
  
 Beiträge: 991 Registriert: 09.10.2004 Entwickler für AutoCAD, BricsCAD u.a., alle Systeme
|
erstellt am: 31. Mrz. 2025 13:46 <-- editieren / zitieren --> Unities abgeben:          Nur für Peter2
Zitat: Original erstellt von Peter2: mit (setq akt_wert (nth zaehler grossliste)).Ein foreach oder gar ein mapcar gehen sich nicht aus, weil ich den Zähler aus verschiedenen Subroutinen weiterzähle und aufrufe.
Warum probierst Du es denn nicht selbst aus? So eine Liste zu konstruieren dauert doch nicht länger als die Frage hier zu formulieren. IMO dürfte das Aufbau der Liste hier der Performance-Flaschenhals sein. Wenn Du das mit APPEND machst, ist das um Zehnerpotenzen langsamer als CONS. Ich würde dann auch noch ausprobieren, der Liste ein führendes Indexelement mitzugeben, und mit ASSOC darauf zuzugreifen. Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
archtools Mitglied
  
 Beiträge: 991 Registriert: 09.10.2004 Entwickler für AutoCAD, BricsCAD u.a., alle Systeme
|
erstellt am: 31. Mrz. 2025 13:59 <-- editieren / zitieren --> Unities abgeben:          Nur für Peter2
Zitat: Original erstellt von archtools:
Wenn Du das mit APPEND machst, ist das um Zehnerpotenzen langsamer als CONS.
Das bedarf vielleicht noch einer näheren Erläuterung, die Du Dir für Perfomance-Gewinne nutzbar machen kannst. Eine Liste wird in Lisp als ein Pointer (ein Zeiger auf eine Speicheradresse) auf das erste Listenelement gespeichert. Und ein Listenelement besteht immer aus zwei Daten, die genau wg dieser Speicheradressen als CAR und als CDR bezeichnet werden. Das CAR ist der gespeicherte Wert (der selbst wieder alles mögliche inkl einer Liste sein kann), und einem Pointer auf das Folgeelement. Am Ende der Liste ist der Wert des Pointers auf das Folgelement NIL. Wenn Du mit CONS eine Liste konstruierst, dann muss nur der Pointer auf das erste Listenelement geändert werden, womit das bisher erste Element zum zweiten wird usw.. Das geht also extrem schnell, weil es den Computer nicht interessiert, wie viele Elemente die Liste schon hat. Er hängt einfach ein Element vorne dran. Bei APPEND ist das anders: Da wird eine neue Liste konstruiert, und dazu muss der Lisp-Interpreter alle Listenelemente der ersten Liste durchgehen. Erst am Ende der ersten Liste wird dann der ursprüngliche Pointer auf NIL durch einen Pointer auf das erste Listenelement der zweiten Liste ersetzt. Bei der Performance der Bearbeitung sehr langer Listen geht es also immer darum, möglichst zu vermeiden, dass die Liste für die Operation neu aufgebaut werden muss. Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
Brischke Moderator CAD on demand GmbH
       

 Beiträge: 4193 Registriert: 17.05.2001 AutoCAD 20XX, defun-tools (d-tools.eu)
|
erstellt am: 31. Mrz. 2025 14:32 <-- editieren / zitieren --> Unities abgeben:          Nur für Peter2
Kannst ja selber mal ausprobieren, wie die Performance bei den verschiedenen Arten des Listenzugriffs ist: Code:
(defun _test (anzahl / liste counter start end start2 end2 start3 end3 start4 end4 PrincTimediff) (defun PrincTimediff (start end message) (princ (strcat "\n" message ": "(rtos (/ (- end start)1000.0) 2 2))) ) (setq liste (list) counter 0 ) (repeat anzahl (setq liste (cons counter liste) counter (1+ counter) ) ) (setq counter 0) (princ "\nV1----------------------------------\n") (setq start (getvar "MILLISECS")) (while (< counter anzahl) (1+ (nth counter liste)) (setq counter (1+ counter)) ) (setq end (getvar "MILLISECS")) (princ "\nV2----------------------------------\n") (setq start2 (getvar "MILLISECS")) (mapcar '(lambda (X) (1+ X) ) liste ) (setq end2 (getvar "MILLISECS")) (princ "\nV3----------------------------------\n") (setq start3 (getvar "MILLISECS")) (foreach X liste (1+ X) ) (setq end3 (getvar "MILLISECS")) (princ "\nV4----------------------------------\n") (setq start4 (getvar "MILLISECS")) (while liste (1+ (car liste)) (setq liste (cdr liste)) ) (setq end4 (getvar "MILLISECS")) (PrincTimediff start end "V1") (PrincTimediff start2 end2 "V2") (PrincTimediff start3 end3 "V3") (PrincTimediff start4 end4 "V4") (princ) ) (_test 10000)
Grüße! Holger ------------------ Holger Brischke CAD on demand GmbH Individuelle Lösungen von Heute auf Morgen.
 defun-tools Das Download-Portal für AutoCAD-Zusatzprogramme!

Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |

| |
Peter2 Ehrenmitglied V.I.P. h.c.

 Beiträge: 3880 Registriert: 15.10.2003 Win 10 bzw. 11 / 64 Pro AutoCAD MAP 3D 2023 BricsCAD 24
|
erstellt am: 31. Mrz. 2025 14:59 <-- editieren / zitieren --> Unities abgeben:         
Danke für die Hinweise, in der Zwischenzeit habe ich auch was weitergebracht. Aufbau der Listen: Das Thema CONS und APPEND sind - vor allem bei so Monsterlisten - sicher sehr wichtig, aber im konkreten Fall lese ich das mit einem Befehl von DosLib aus einer Textdatei ein und da ist es schon fertig. Zugriffsgeschwindigkeit von NTH: Die hängt nicht von der Grösse der Liste ab, sondern dort wo ich hinziele. Habe ich eine Liste mit 10.000 Einträgen und eine mit 500.000, dann ist der Zugriff mit NTH bei mit (repeat 2000 von 7000-9000) bei beiden Listen gleich schnell. "NTH 540.000-542.000" sind zwar auch 2000 Zugriffe, aber massiv langsamer als der "vordere Zugriff". Zähler versus Listenkürzung: Durch den Hinweis von archtools habe ich mein Programm nun umgebaut. Statt
Code: "zähle 1, 2, 3 - gehe zu 1,2,3"
habe ich nun Code: "nimm mit CAR den ersten Wert der Liste - lösche den ersten Wert - nimm den ersten Wert"
. Bei Listen mit 20 oder 200 Einträgen ist das wahrscheinlich irrelevant, aber hier habe ich jetzt ein Beschleunigung um den Faktor 4. Für mich sowiet nun alles klar - danke nochmals. Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |