Dictionaries in Liste durchsuchen

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Serpens66
User
Beiträge: 259
Registriert: Montag 15. Dezember 2014, 00:31

Ich habe folgende Liste:


Liste = [{'amountOpen': '0.01', 'price': 20000, 'id': 8552995, 'fund_name': 'BTCEUR', 'fund_id': 9, 'type': 'B', 'amountUnfilled
': '0.01', 'price_normalized': '200.00'}, {'amountOpen': '0.01', 'price': 30000, 'id': 8552997, 'fund_name': 'BTCEUR', '
fund_id': 9, 'type': 'S', 'amountUnfilled': '0.01', 'price_normalized': '300.00'}]

Diese Liste hat also 2 Elemente, welche Dictionaries sind. Je nach Umständen kann diese Liste deutlich länger werden.
Ich möchte nun genau das Listenelement erfassen, welches "'id': 8552997 " enthält.

Wie mache ich das? Ich weiß, dass ich Inhalte von Listen mit "a" in abc untersuchen kann. Dazu müsste ich hier aber das komplette dictionary angeben, um zu gucken ob es in der Liste enthalten ist, geht also nicht. Dictionaries kann ich mit der get() funktion auf inhalte überprüfen. Muss ich das beides kombinieren?
Mir würde nun einfallen:
Liste[0].get('id') == 8552997
zu prüfen und genauso für alle anderen Elemente der Liste. Eventuell in einer for Schleife, sodass alle Listenelemente durchgegangen werden. Aber das geht doch ganz bestimmt einfacher, richtig? :)
Sirius3
User
Beiträge: 17754
Registriert: Sonntag 21. Oktober 2012, 17:20

@Serpens66: genau so geht das. Du mußt jedes einzelne Element der Liste prüfen, ob «id» den gesuchten Wert hat.
BlackJack

@Serpens66: Die `get()`-Methode würde ich hier nur benutzen wenn es sein kann das dort Elemente ohne einen 'id'-Schlüssel enthalten sind. Das suggieriert die Methode dem Leser nämlich. Wenn jedes Element ganz sicher einen 'id'-Schlüssel hat, was bei dem Namen sehr naheliegt, dann wäre ein normaler Zugriff per ``[]``-Syntax irgendwie natürlicher.

Falls es nur *ein* Element mit dem gesuchten Wert gibt, was bei dem Schlüsselnamen `id` auch wieder naheliegend wäre, dann solltest Du Dir Generatorausdrücke und die `next()`-Funktion anschauen.
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

Man kann sich jetzt natürlich die Frage stellen, ob es nicht möglich und ggf. sinnvoller ist, die äußere Liste durch ein Dictionary zu ersetzen, welches die Id als Schlüssel nutzt. Auf diese Art und Weise hättest Du einen *direkten* Zugriff auf das gewünschte Objekt, was natürlich einfacher und vor allem deutlich effizienter ist.

Es kommt dabei natürlich darauf an, wie Du diese Struktur verwendest. Wenn die Reihenfolge wesentlich ist, der gewünschte Zugriff dagegen nur selten vorkommt, kann das im Endeffekt auch wieder teurer bezüglich der Zeitkomplexität werden...
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
BlackJack

@Hyperion: Das ist ein Rückgabewert von einer JSON-Web-API. Die Struktur ist also so erst einmal von aussen vorgegeben.
Benutzeravatar
/me
User
Beiträge: 3556
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

Um BlackJacks zweiten Vorschlag mal zu demonstrieren.

Code: Alles auswählen

Liste= [{'amountOpen': '0.01', 'price': 20000, 'id': 8552995, 'fund_name': 'BTCEUR',
          'fund_id': 9, 'type': 'B', 'amountUnfilled': '0.01',
          'price_normalized': '200.00'},
         {'amountOpen': '0.01', 'price': 30000, 'id': 8552997, 'fund_name': 'BTCEUR',
          'fund_id': 9, 'type': 'S', 'amountUnfilled': '0.01',
          'price_normalized': '300.00'}]

def find_entry(data, id_):
    return next((x for x in Liste if x['id'] == id_), None)

print(find_entry(Liste, 8552995))
print(find_entry(Liste, 8552996))
Serpens66
User
Beiträge: 259
Registriert: Montag 15. Dezember 2014, 00:31

@Hyperion: Wie BlackJack schon schreibt, bin ich nicht der Ersteller dieser Liste, ich lese sie lediglich aus^^ Andere Exchanges machen es tatsächlich so wie du schreibst, was dementsprechend leichter zu handhaben ist.

@BlackJack und /me:
Danke für diese mögliche Lösung und das Beispiel. Habe mich in Generatoren und next() eingelesen, aber nicht wirklich gesehen, wie mir "yield" bei dem Problem helfen könnte. Dass es so wie in /m's Beispiel geht, da wäre ich erstmal nicht drauf gekommen, vielen dank, vllt nutze ich das beim nächsten Problem :)

Ich habe es jetzt wie folgt gelöst, wobei "open_orders_rock" die erwähnte Liste ist:

Code: Alles auswählen

         
        i_OrderID_buyrock = 0
        length_buyrock = len(open_orders_rock)
        while i_OrderID_buyrock<length_buyrock:
            if open_orders_rock[i_OrderID_buyrock]['id'] == OrderID_buyrock:
                break
            else: 
                i_OrderID_buyrock+=1 
        # nun ist i_OrderID_buyrock die nummer des gesuchten Listenelements. wenn id nicht in liste, dann ist i = length
Da fällt mir die Frage ein:
Wie kommentiere ich am sinnvollsten. Wann verwende ich """kommentar""" und wann #kommentar.
Zurzeit bin ich ja noch viel am rumwerkeln, experiementieren usw. weshalb ich sehr viele #kommentare reinkritzel. Um meine wichtige von unwichtigen Kommentaren zu unterscheiden schreibe ich die wichtigen Kommentare aber auch in """ """.
Das Problem bei den """ """ ist nur, dass es öfter mal vorkommt, dass ich größere Blöcke zum testen auskommentieren muss, was natürlich am besten mit """ """ möglich ist. Wenn ich in diesem Block dann aber Kommentare mit diesen Zeichen habe, funktioniert das natürlich nicht wie gewollt, weshalb """ """- Kommentare meistens eher störend sind.

Kann ich in Notepad++ selbst Farben hinzunehmen? sodass manche #kommentare grün und andere #kommentare gelb oderso sind?
BlackJack

@Serpens66: Ich schrieb Generator*ausdruck* nicht Generator*funktion*. ``yield`` ist für eine Generatorfunktion. Den Generatorausdruck hat /me gezeigt.

Die Lösung ist nicht schön. Nicht nur das es einen besonderen Fehlerwert gibt, der ist auch noch vom gleichen Typ wie echte Werte und nicht einmal fest, also insgesamt sehr fehleranfällig.

Warum willst Du überhaupt den Index von dem Element wissen? Idiomatisches Python vermeidet Indizes in der Regel und arbeitet stattdessen direkt mit den Objekten. Den Index wirst Du dann doch sowieso nur wieder verwenden um das Objekt aus der Liste zu holen.

"""Kommentar""" verwendet man nie, denn das ist kein Kommentar sondern eine Zeichenkette. An bestimmten Stellen wird die zum DocString und enthält Dokumentation für denjenigen der das dokumentierte Objekt verwenden möchte. Während Kommentare für den Leser der Implementierung sind. In echte Kommentare kommen Sachen rein die zum Verständnis der konkreten Implementierung wichtig sind falls der Code dazu nicht ausreicht. Da gehört nichts rein was zum Verständnis der Schnittstelle wichtig ist. Ausnahme: Spezielle Kommentare für Dokumentationswerkzeuge die daraus API-Dokumentation erzeugen. Sphinx kennt zum Beispiel Kommentare die mit ``#:`` eingeleitet werden.

Auch zum Auskommentieren verwendet man ``#``. Jeder vernünftige Editor hat eine Funktion um damit auch markierte Zeilenblöcke ein- und auszukommentieren. Das ist also nicht komplizierter als """ """ zu verwenden und hat zusätzlich noch den Vorteil das man auch Code mit bereits auskommentierten Teilen, normalen Kommentaren, und Docstrings noch mal auskommentieren kann. Sogar beliebig oft. """ """ lassen sich dagegen nicht problemlos verschachteln/”stapeln”.
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

@BlackJack: Oops... habe ich also überlesen oder Du wusstest es "magisch" ;-)

@Serpens66: Deine Lösung ist aber nicht so gut und ziemlich unpythonisch!

Du kannst doch über ``open_orders_rock`` *direkt* iterieren! Wozu das umständliche Hantieren mit der ``while``-Schleife‽

Code: Alles auswählen

for order in open_orders_rock:
    # whatever
@/me: Wenn man *mehrfach* auf Elemente der Liste zugreifen will, dürfte es sich *schnell* lohnen, diese in ein Dictionary zu überführen ;-)
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
BlackJack

@Hyperion: Wissen aus einer vorherigen Frage/anderem Thema von Serpens66 das mein Gehirn erstaunlicherweise in dieses Jahr rüberretten konnte. :-)
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

@BlackJack: Ich wusste doch schon immer, dass Du hier der Obergott bist :mrgreen:
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
Benutzeravatar
/me
User
Beiträge: 3556
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

Hyperion hat geschrieben:@/me: Wenn man *mehrfach* auf Elemente der Liste zugreifen will, dürfte es sich *schnell* lohnen, diese in ein Dictionary zu überführen ;-)
Wenn die Suche dabei immer explizit nach der id erfolgt, dann ist das sicher sinnvoll. Wenn die Reihenfolge eine Rolle spielt, dann sollte man ein OrderedDict verwenden.
Serpens66
User
Beiträge: 259
Registriert: Montag 15. Dezember 2014, 00:31

@BlackJack:
Zum Thema kommentieren: Dankesehr, habe die Funktion zum aus-/einkommentieren des Editors gesucht und gefunden, wusste nicht dass es sowas gibt :)
Aber eine möglichkeit einige Kommentare mehr hervorzuheben als anderen Kommentare (z.b überschriften vs genauere erklärung) gibt es nicht? Da ich ja in ein paar Wochen noch selbst verstehen will, was ich da verzapft habe, schreibe ich relativ ausführlich zu den einzelnen Teilen was wofür da ist usw. Da wäre dann also eine Hervorhebung von den wichtigen Textteilen sehr praktisch und übersichtsfördernd.


Zu meinem Code:
Ja stimmt, ich verwende den Index des Listenelements um dann letzlich auf den Wert von "amountUnfilled" zu kommen.

Wäre es dann so besser gelöst?

Code: Alles auswählen

for listenelement in open_orders_rock:
        if (listenelement["id"]==OrderID_buyrock):
		unfilled = listenelement["amountUnfilled"]
BlackJack

@Serpens66: Wie die Möglichkeiten bei Notepad++ aussehen weiss ich nicht. Als ich den Editor das letzte mal verwendet habe, da war die Definition von Syntaxhervorhebungen soweit ich mich erinnere auf Kommentare, Zeichenketten, und ein Satz an Schlüsselworten beschränkt. Kann sein das da heute mehr möglich ist. Die meisten guten Editoren haben mittlerweile Beschreibungsdateien wo die Syntax mit Hilfe von regulären Ausdrücken für die Token und Zustandsautomaten für die Grammatik an sich beschrieben werden kann.

Ansonsten kann man auch eine Auszeichnungsprache wie reStructuredText nehmen wo man Überschriften ja auch ohne spezielle Farben ganz gut erkennen kann.

Ich Frage mich allerdings ob Du wirklich so viele Kommentare brauchst beziehungsweise ob Du die nicht vielleicht auch brauchst weil der Code nicht so deutlich und verständlich beschreibt was passiert wie das sein sollte/könnte. Zum Beispiel nennt man normalerweise nichts `listenelement` ausser in generischen Beispielen wo es tatsächlich keinen besseren Namen gibt, und in der gleichen Funktion `OrderID_buyrock` und `i_OrderID_buyrock` ist auch nicht wirklich leicht auseinander zu halten.
Serpens66
User
Beiträge: 259
Registriert: Montag 15. Dezember 2014, 00:31

BlackJack hat geschrieben:@Serpens66: Wie die Möglichkeiten bei Notepad++ aussehen weiss ich nicht. Als ich den Editor das letzte mal verwendet habe, da war die Definition von Syntaxhervorhebungen soweit ich mich erinnere auf Kommentare, Zeichenketten, und ein Satz an Schlüsselworten beschränkt. Kann sein das da heute mehr möglich ist. Die meisten guten Editoren haben mittlerweile Beschreibungsdateien wo die Syntax mit Hilfe von regulären Ausdrücken für die Token und Zustandsautomaten für die Grammatik an sich beschrieben werden kann.

Ansonsten kann man auch eine Auszeichnungsprache wie reStructuredText nehmen wo man Überschriften ja auch ohne spezielle Farben ganz gut erkennen kann.

Ich Frage mich allerdings ob Du wirklich so viele Kommentare brauchst beziehungsweise ob Du die nicht vielleicht auch brauchst weil der Code nicht so deutlich und verständlich beschreibt was passiert wie das sein sollte/könnte. Zum Beispiel nennt man normalerweise nichts `listenelement` ausser in generischen Beispielen wo es tatsächlich keinen besseren Namen gibt, und in der gleichen Funktion `OrderID_buyrock` und `i_OrderID_buyrock` ist auch nicht wirklich leicht auseinander zu halten.
okay, danke.

ich verteile meine Bennenungen möglichst so, dass ich sofort anhand des variablen Namen sehe, was darin gespeichert ist und ich nicht ständig nachschauen muss, was darin gespeichert ist. "listenelement" habe ich jetzt verwendet, weil mir auf den ersten Blick nicht klar war, dass "order" im Skript von Hyperion nun ein Listenelement darstellt. Hatte eine Weile überlegen müssen, wie ich nun weitermache, bis mir eben aufgefallen ist, dass das nun nichts anderes als ein listenelement ist, womit ich wieterarbeiten kann :)
(im vorherigen Testskript hatte ich tatsächlich alles noch durchnummeriert mit, also quasi "var1" , "var2" usw usw, weshalb ich ständig nachschauen musste, wo nun was drin steckt :D )
Zu `OrderID_buyrock` und `i_OrderID_buyrock`: ursprünglich hatte ich das zweite es nur "i" genannt, weil das glaube ich die standardbezeichnung für laufende Indizes ist. Ich wollte es aber natürlich auch von 'i_OrderID_sellrock` unterscheiden können, deswegen der Zusatz. Die Bezeichnung der Variablen ist aktuell also kein Problem, da steige ich ganz gut durch :)

Die meisten Kommentare entstehen, wenn mir während des Schreibens noch was einfällt, ich aber den akteullen Code/Gedanken erst zuende führen muss. Dann schreibe ich meine Gedanken kurz auf, in der Form "#hier noch dran denken dies und jenes zu machen, damit das und das aufgeht". Und solche "nicht vergessen" Kommentare vermischen sich dann mit Überschriften und Erklärungen.
Meine Erklärungen beziehen sich tatsächlich meistens auf das Vorgehen an sich. also z.b "hier wird nun kontrolle() aufgerufen, da dies und jenes geprüft werden muss und dann passiert das und das" Es geht also nicht nur um Erklärung des Codes, sondern auch darum, warum ich etwas so schreibe, wie es es tue, um es später nachvollziehen zu können.
Lieber zuviele erklärende Kommentare als zu wenig :)


Achso, also ist mein Code jetzt richtig und auch sinnvoll um auf den amountUnfilled des entsprechenden Trades zu kommen?
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

Serpens66 hat geschrieben: "listenelement" habe ich jetzt verwendet, weil mir auf den ersten Blick nicht klar war, dass "order" im Skript von Hyperion nun ein Listenelement darstellt. Hatte eine Weile überlegen müssen, wie ich nun weitermache, bis mir eben aufgefallen ist, dass das nun nichts anderes als ein listenelement ist, womit ich wieterarbeiten kann :)
Öh... und ``listenelement`` sagt Dir jetzt ernsthaft *besser*, *worum* es sich bei einem solchen handelt‽ :shock:

Mit welchem Code könntest Du jetzt mehr anfangen

Code: Alles auswählen

# Alternative 1
for listenelement in enten:
    listenelement.quack()
    listenelement.flieg()

# Alternative 2
for ente in enten:
    ente.quack()
    ente.flieg()
?
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
BlackJack

@Serpens66: Das ist genau die falsche ”Richtung” bei der Benennung, das interessante an der Laufvariablen ist ja das der Wert eine `order` repräsentiert und nicht das es ein `listenelement` ist. Es kommt aus dem Objekt das der Ausdruck nach dem ``in`` beschreibt, also ist es grundsätzlich ein Element von irgendwas iterierbaren, das weiss jeder der Code liest. Und ob das nun aus einer Liste, einem Tupel, einem Generator/Iterator oder aus irgendeinem anderen Datentyp kommt ist doch völlig egal. Und kann sich auch im Laufe der Programmentwicklung mal ändern. Wichtig ist für den Leser doch was der Wert im Kontext *dieses* konkreten Programms bedeutet und so etwas völlig allgemeines, nichtssagends und offensichtliches wie `listenelement`. Und eventuell Falsches sollte man da mal keine Liste sondern etwas anderes iterierbares mit `order`-Elementen übergeben.

Und bei Namen wie `OrderID_buyrock` und `i_OrderID_sellrock` habe ich nicht den Eindruck als wenn Du das im Griff hast. Die sind komisch, und entweder redundant oder deuten darauf hin das Du zu viel Code in einer Funktion hast. Zum Beispiel das `rock` wofür steht das? Kommen die `order_id`\s zum kaufen und verkaufen tatsächlich zusammen im gleichen Namensraum vor?

Heisst die Funktion tatsächlich `kontrolle()`? Das wäre dann ein Fall von Code den man erklären muss weil der Code selber nicht verständlich genug geschrieben ist. Und warum steht das was die Funktion macht und warum beim Aufruf und nicht als Dokumentation bei der Funktion?

Kommentare für Sachen die noch getan werden müssen werden oft mit ``TODO``, ``XXX``, oder ``FIXME`` eingeleitet und einige Syntaxhervorhebungen kennen diese ”Schlüsselworte” und heben sie hervor. Es gibt auch Editoren und IDEs beziehungsweise Plugins dafür, die aus solchen Kommentaren automatisch Listen zusammenstellen können, damit man einen Überblick über die ”offenen Baustellen” im Code erhalten kann. Die meisten Dokumentationswerkzeuge kennen auch Syntax um ToDo-Punkte auszuzeichnen und die dann alle gesammelt an einer Stelle der Dokumentation auszugeben.
Serpens66
User
Beiträge: 259
Registriert: Montag 15. Dezember 2014, 00:31

Hyperion hat geschrieben:
Serpens66 hat geschrieben: "listenelement" habe ich jetzt verwendet, weil mir auf den ersten Blick nicht klar war, dass "order" im Skript von Hyperion nun ein Listenelement darstellt. Hatte eine Weile überlegen müssen, wie ich nun weitermache, bis mir eben aufgefallen ist, dass das nun nichts anderes als ein listenelement ist, womit ich wieterarbeiten kann :)
Öh... und ``listenelement`` sagt Dir jetzt ernsthaft *besser*, *worum* es sich bei einem solchen handelt‽ :shock:

Mit welchem Code könntest Du jetzt mehr anfangen

Code: Alles auswählen

# Alternative 1
for listenelement in enten:
    listenelement.quack()
    listenelement.flieg()

# Alternative 2
for ente in enten:
    ente.quack()
    ente.flieg()
?
natürlich würde ich "listenelement", wenn ich denn eine Bestätigung bekomme, dass es nun das tut, was es soll und das auch effektiv, so nicht in meinem Skript nutzen. Wie gesagt habe ich den Namen hier nur deswegen gewählt, um das ganze nochmal durch "sehen" zu lernen und zu verinnerlichen, dass es sich dabei um ein Listenelement handelt, damit ich sowas in zukunft sofort sehe ;)
Im skript würde ich aufjedenfall noch den zusatz rocksell/ bzw rockbuy dranhängen. Wie ich den Teil davor dann aber nennen soll.. da fällt mir aktuell kein hilfreicher Name ein.
Serpens66
User
Beiträge: 259
Registriert: Montag 15. Dezember 2014, 00:31

BlackJack hat geschrieben:@Serpens66: Das ist genau die falsche ”Richtung” bei der Benennung, das interessante an der Laufvariablen ist ja das der Wert eine `order` repräsentiert und nicht das es ein `listenelement` ist. Es kommt aus dem Objekt das der Ausdruck nach dem ``in`` beschreibt, also ist es grundsätzlich ein Element von irgendwas iterierbaren, das weiss jeder der Code liest. Und ob das nun aus einer Liste, einem Tupel, einem Generator/Iterator oder aus irgendeinem anderen Datentyp kommt ist doch völlig egal. Und kann sich auch im Laufe der Programmentwicklung mal ändern. Wichtig ist für den Leser doch was der Wert im Kontext *dieses* konkreten Programms bedeutet und so etwas völlig allgemeines, nichtssagends und offensichtliches wie `listenelement`. Und eventuell Falsches sollte man da mal keine Liste sondern etwas anderes iterierbares mit `order`-Elementen übergeben.
ah okay, jetzt verstehe ich wirauf du hinaus willst. Ja das stimmt natürlich. Bei allen anderen Namen habe ich das aber berücksichtigt.
BlackJack hat geschrieben: Und bei Namen wie `OrderID_buyrock` und `i_OrderID_sellrock` habe ich nicht den Eindruck als wenn Du das im Griff hast. Die sind komisch, und entweder redundant oder deuten darauf hin das Du zu viel Code in einer Funktion hast. Zum Beispiel das `rock` wofür steht das? Kommen die `order_id`\s zum kaufen und verkaufen tatsächlich zusammen im gleichen Namensraum vor?
"rock" steht dafür, dass es von der Website "therock" abgefragt wurde. In derselben Funktion werden noch Orders von anderen Börsen verwendet, welche in Berechnungen miteinander verglichen werden.
Aber stimmt, ich neige noch dazu, soviel wie geht in einer einzigen Funktion zu erledigen. In meinem jetzigen Skript schaue ich aber jetzt schon nach, was ich am besten in eine neue defintion auslagere, damit es übersichtlicher wird. Das einzige Problem dabei sind dann nur immer die variablen. Die in einer defintion abgefragten Werte brauche ich auch in fast allen anderen Defintionen, das heißt ich muss sie ständig alle als Parameter weiterreichen. Da ist es zumeist einfacher bei einer Definition zu bleiben. Habt ihr dazu einen Tipp, wie ich das ständige weitergeben der Variablen vereinfachen kann? Stattdessen Variablen einer höheren Stufe verwenden?
BlackJack hat geschrieben: Heisst die Funktion tatsächlich `kontrolle()`? Das wäre dann ein Fall von Code den man erklären muss weil der Code selber nicht verständlich genug geschrieben ist. Und warum steht das was die Funktion macht und warum beim Aufruf und nicht als Dokumentation bei der Funktion?
ja noch sind die Funktionsnamen so spartanisch, also "suchen()" "reaktion()" und "kontrolle()".
Das liegt aber daran, dass ich ja noch am schreiben bin. Ich wüsste aber ehrlich gesagt auch keine Namen, die mehr über die Verwendung aussagen würden. Die aktuelle Namensvergebung beschreibt es schon recht gut. Aber dennoch ist eine zusätzliche Beschreibung nötig, was auch bei jedem anderen Namen der Fall wäre.

Wie ihr ja schon deutlich merkt, bin ich kein Mensch, der sich gerne Konventionen unterwirft. Ich trage z.b auch ungerne Anzüge. Ich hasse es, dass sowas zb in Büros Pflicht ist, weil die Dinger einfach nur unbequem und unpraktisch sind. Genauso fühlen sich für mich diese Python Konventionen an. Ich denke mir halt "ist doch egal wie ich das nenne, hauptsache ich verstehe es".
Ich vermute das liegt daran, dass ich nicht immer sofort sehe, wo die Vorteile der Konventionen liegen. Ich höre meist halt nur "das macht man einfach so weil es Konvention ist!" Aber das ist für mich kein Grund :D
Dagegen ist deine Begründung, dass es bei schlechter Namensgebung einfach nicht selbsterklärend ist und man den Code noch lange erklären muss, eine gute Begründung die ich nachvollziehen, akzeptieren und anwenden kann.
BlackJack hat geschrieben: Kommentare für Sachen die noch getan werden müssen werden oft mit ``TODO``, ``XXX``, oder ``FIXME`` eingeleitet und einige Syntaxhervorhebungen kennen diese ”Schlüsselworte” und heben sie hervor. Es gibt auch Editoren und IDEs beziehungsweise Plugins dafür, die aus solchen Kommentaren automatisch Listen zusammenstellen können, damit man einen Überblick über die ”offenen Baustellen” im Code erhalten kann. Die meisten Dokumentationswerkzeuge kennen auch Syntax um ToDo-Punkte auszuzeichnen und die dann alle gesammelt an einer Stelle der Dokumentation auszugeben.
Hast du eine Infoseite diesbezüglich parat? die drei von dir genannten Schlüsselworte klappen jedenfalls standardmäßig nicht in notepad++. Naja, ein riesen Aufwand das nun iwo umzustellen oder ein Tool zu besorgen lohnt vermutlich nicht. Ists halt ein wenig unübersichtlich, solange es noch nicht fertig ist. Die Todo's sind im fertigen Zustand ja nicht mehr drin.
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

Ich glaube dann hast Du das Konzept von Objekten noch nicht verstanden! BlackJack hat Dir das eigentlich ganz schön aufgeschrieben, so dass ich nicht weiß, ob ich es noch anschaulicher darstellen kann.

Ich versuche es noch einmal anhand meines Beispiels:
Anhand der Syntax einer ``for``-Schleife ist sofort klar, welcher Name semantisch die Sammlung darstellt und welcher das jeweils das einzelne Objekt repräsentiert, welches sich bei jedem Durchlauf der Schleife ändert. Direkt nach dem ``for`` steht der Name des einzelnen Objekts, nach dem ``in`` der Name, der das Objekt der Sammlung (also eine Liste, eines Sets, Tupels, Dictionaries oder allgmein ein ``Iterable``) repräsentiert.

Wenn meine Sammlung ``enten`` heißt, so lässt sich vermuten, dass darin lauter Enten-Objekte gespeichert sind. Wenn das einzelne Objekt dann ``ente`` heißt, wird sofort klar, dass es sich dabei um *ein* Enten-Objekt handelt. Auf deutsch übersetzt könnte man das (fast) flüssig lesen: "Für jedes Ente-Objekt in der Enten-Sammlung".

Es gibt keinen speziellen Typen für Elemente einer Sammlung! Ich kann ein Entenobjekt in eine Liste, ein Tupel, ein Set usw. stecken. Ich kann auch eine eigene Sammlung bauen, in der ein solches Objekt stecken kann. Der Name ``listenelement`` sagt also nichts aus, er ist viel zu allgemein. Innerhalb des Schleifenrumpfs ist das auch nur ein quasi beliebiger Name, an den ein Objekt aus der Sammlung gebunden ist. Es ist im Schleifenrumpf überhaupt kein besonderes Objekt, es hat keine besonderen Eigenschaften oder so. Sehe ich jedoch den Namen ``ente``, so erscheinen die Methoden ``.flieg`` oder ``.quack`` gleich sehr passend zu sein. Beides zusammen bildet eine Einheit! Ich könnte natürlich auch folgendes schreiben:

Code: Alles auswählen

for yxAbcD45Ef1299 in enten
Dann müsste ich in der Schleife eben Aufrufe a la ``yxAbcD45Ef1299.flieg()`` - offensichtlich, dass sich das nicht gut liest!

``listenelement`` ist insofern aber noch schlimmer, als es sich bei der Sammlung ja gar nicht um eine Liste handeln muss! Du codierst also den (vermeindlichen) Typen in den Namen hinein... was machst Du, wenn aus der Liste ein Dictionary wird? Änderst Du dann den Namen auch um? Denkst Du daran? Wirklich bei allen Code-Stellen? Ich antworte mal für Dich: Nein! ;-) Alles, woran man als Entwickler selbständig denken muss, vergisst man früher oder später! Und das hat zur Folge, dass Dein Code lügt! Du könntest versucht sein Dinge zu tun, die nur bei Listen klappen; und das führt dann zu einem Fehler...

Ein Name sollte "intention revealing" sein, also die Intention des Autors vermitteln. Du würdest den Namen für die Sammlung ja auch eher ``enten`` nennen, als ``Liste``, oder? Wieso also beim Namen für das einzelne Objekt dann ``Listenelement``? Semantisch macht es keinen Unterschied... aber ``Liste`` sagt eben nicht viel aus; im Gegenteil wäre auch da wieder der Typ codiert. Aber selbst wenn ich ``Sammlung`` nähme, wüsste man immer noch nicht, *was* da eigentlich für Objekte in der Sammlung stecken. Und im Schleifenrumpf will man doch genau mit diesen etwas anstellen - da ist es hilfreich zu wissen, *womit* man es zu tun hat. *Dass* diese aus einer Sammlung (oder einem Iterable) stammen, ist doch automatisch durch die Schleife klar!
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
Antworten