Dictionary Schlüssel als Objekte

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.
Antworten
Hartmannsgruber
User
Beiträge: 89
Registriert: Mittwoch 15. Januar 2014, 22:30
Wohnort: Bad Kötzting
Kontaktdaten:

Servus Leute,

ist es möglich die Schlüssel eines Dictionary, zu Objekten einer Klasse zu machen.

In diesen Bsp. a und b:

Code: Alles auswählen

dictionary = {"a": {"aa": 1, "bb": 2}, "b": {"aa": 3, "bb": 4}}

for element in dictionary:
    element = Klasse(dictionary[element]["aa"], dictionary[element]["bb"])
Wenn ich die for-schleife in python3 ausführe passiert keine Fehlermeldung.
wenn ich aber nun eine Methode auf einen Wert anwende erscheint folgende Fehlermeldung:

Code: Alles auswählen

NameError: name 'a' is not defined
Ist das was ich hier versuche überhaupt möglich, bzw. wird das überhaupt so gemacht?
Bitte um Hilfe, Problem bringt mich um meinen Verstand :-(
Sirius3
User
Beiträge: 18335
Registriert: Sonntag 21. Oktober 2012, 17:20

@Hartmannsgruber: was willst Du wirklich machen? Aus Deinem Beispiel wird das mir überhaupt nicht klar. Dynamische Variablennamen kann man zwar erzeugen, in den meisten Fällen will man aber mit einem Dictionary arbeiten.
Benutzeravatar
pillmuncher
User
Beiträge: 1532
Registriert: Samstag 21. März 2009, 22:59
Wohnort: Pfaffenwinkel

Komisch, bei mir kommt ein anderer Fehler:

Code: Alles auswählen

>>> dictionary = {"a": {"aa": 1, "bb": 2}, "b": {"aa": 3, "bb": 4}}
>>>
... for element in dictionary:
...     element = Klasse(dictionary[element]["aa"], dictionary[element]["bb"])
...
Traceback (most recent call last):
  File "<stdin>", line 3, in <module>
NameError: name 'Klasse' is not defined
In specifications, Murphy's Law supersedes Ohm's.
BlackJack

@Hartmannsgruber: Für so etwas gibt es Dictionaries. Namen dynamisch erzeugen ist nicht üblich, in Funktionen/Methoden zumindest in CPython auch gar nicht möglich.
Benutzeravatar
MagBen
User
Beiträge: 799
Registriert: Freitag 6. Juni 2014, 05:56
Wohnort: Bremen
Kontaktdaten:

Hartmannsgruber hat geschrieben:ist es möglich die Schlüssel eines Dictionary, zu Objekten einer Klasse zu machen.
Ja
Hartmannsgruber hat geschrieben:Ist das was ich hier versuche überhaupt möglich, bzw. wird das überhaupt so gemacht?
Ja

Probier das mal

Code: Alles auswählen

class ObjectModel(object):
    def __init__(self, dictionary):
        for key, value in dictionary.items():
            if isinstance(value, dict):
                setattr(self, key, ObjectModel(value))
            else:
                setattr(self, key, value)

dictionary = {"a": {"aa": 1, "bb": 2}, "b": {"aa": 3, "bb": 4}} 
obj = ObjectModel(dictionary)
    
print(obj.a.bb)
print(obj.b.aa)
a fool with a tool is still a fool, www.magben.de, YouTube
jerch
User
Beiträge: 1669
Registriert: Mittwoch 4. März 2009, 14:19

@Hartmannsgruber:
Falls Du dabei die dictionary-Funktionalität nicht verlieren möchtest, kannst Du auch __getattr__/__getattribute__ in einer dict-Klasse so abwandeln, dass auch die Items zurückgegeben werden. Unterschied der beiden ist, dass __getattr__ nachrangig ist, d.h. die nativen Methoden Vorrang haben während __getattribute__ vorrangig ist und so den Items den Vorzug geben kann.
Hartmannsgruber
User
Beiträge: 89
Registriert: Mittwoch 15. Januar 2014, 22:30
Wohnort: Bad Kötzting
Kontaktdaten:

Vielen Dank an all eure Ratschläge.
@MagBen:
Funktioniert :-D
übrigens schicke Internetseite ;)

Also das was ich da versucht habe, ist nicht programmieruntypisch oder?
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

Hartmannsgruber hat geschrieben:Also das was ich da versucht habe, ist nicht programmieruntypisch oder?
In den meisten Fällen ist es untypisch und man möchte das Szenario vermeiden. Wenn du wirklich ständig zur Laufzeit Attribute erzeugen willst, dann ist der Ansatz die falsche Wahl. Wie Sirius3 schon schrieb, sollte dann gleich ein Dictionary verwendet werden. Das spart einige unnütze Schritte. Denn wenn du mit setattr immer dynamisch Attribute setzt, dann musst du diese auch mit getattr abfragen. Das ist aber mehr Schreibarbeit als ein einfacher Indexzugriff. Beschreibe doch mal was du genau machen willst. Wie sieht das konkrete Problem aus?
Das Leben ist wie ein Tennisball.
Hartmannsgruber
User
Beiträge: 89
Registriert: Mittwoch 15. Januar 2014, 22:30
Wohnort: Bad Kötzting
Kontaktdaten:

Ich sag es mal so, mein Programm funktioniert mit der Verwendung eines Dictionarys gut.
Ich habe dann gelesen, dass man Objektorientert Programmieren sollte, weil es übersichtlicher und sauberer ist.
Naja deshalb die Frage ob man das dic in Objekte umwandeln kann.

Mein Programm funktioniert im Grunde so:
1. Dateien aus der .CSV auslesen
2. formatieren und werte in ein dict. schreiben
3. mit dict. weiterarbeiten, etc.
Benutzeravatar
MagBen
User
Beiträge: 799
Registriert: Freitag 6. Juni 2014, 05:56
Wohnort: Bremen
Kontaktdaten:

Hartmannsgruber hat geschrieben:Also das was ich da versucht habe, ist nicht programmieruntypisch oder?
Nein, auf jeden fall nicht in Python. Ich kenne keine andere Script-Sprache die das so gut unterstützt wie Python. Mein ganzes Objektmodell basiert auf einer Baumstruktur, dessen Struktur zur Laufzeit mit __getattr__ und __setattr__ aufgebaut wird. Das ganze ist ein Ersatz für die guten alten Ini-Dateien. In Python braucht man sich keinen Parser für Ini-Dateien zu schreiben, da ja Python selbst ein Parser ist. In den Ini-, Config- oder Projektdateien steht deshalb Python-Code der solche Objektmodellbäume aufbaut.

Das könnte man auch alles mit Dictionary Objekten machen, die zu schachteln wird aber schnell unübersichtlich, außerdem nerven die ganzen Anführungszeichen.
Hartmannsgruber hat geschrieben:übrigens schicke Internetseite ;)
Dank php und YAML.
a fool with a tool is still a fool, www.magben.de, YouTube
BlackJack

@Hartmannsgruber: Objektorientierte Programmierung kann unter Umständen ein Programm übersichtlicher machen, aber das was MagBen da macht ist keine OOP, das ist einfach nur ein syntaktisch anderer Zugriff auf die Daten. Ob man nun Wörterbücher verschachtelt oder so eine supergenerische Klasse verwendet um den Zugriff einfach nur anders hinzuschreiben macht weder das Programm objektorientiert(er), noch tiefe Verschachtelungen übersichtlicher. Das ist einfach nur Kosmetik die bestenfalls das tippen etwas vereinfacht. Und das so zu machen ist soweit ich das sehe auch in Python untypisch. Nur weil das einfacher geht als in anderen Sprachen, heisst das ja nicht dass das eine gute Idee ist.
Sirius3
User
Beiträge: 18335
Registriert: Sonntag 21. Oktober 2012, 17:20

Hartmannsgruber hat geschrieben:Ich habe dann gelesen, dass man Objektorientert Programmieren sollte, weil es übersichtlicher und sauberer ist.
Das ist Quatsch. So pauschal läßt sich das nicht sagen. Objektorientierung ist meistens aufwendiger und schwerer zu verstehen. Es gibt ein paar Ausnahmen, z.B. wenn auf einem klar abgegrenzten Datensatz spezifische Operationen ausgeführt werden sollen.

Ob in Deinem Fall Listen, Dictionaries oder Named-Tuples am sinnvollsten sind, hängt von den Daten und was Du damit machen willst ab. Beliebige dynamisch erzeugte Werte als Attribute in eine Klasse zu schreiben, nur um ein paar Anführungszeichen zu sparen, ist jedenfalls meiner Meinung nach ein unnötiger Zusatzschritt, der keine Übersichtlichkeit schafft.
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

MagBen hat geschrieben:außerdem nerven die ganzen Anführungszeichen.
Weil ``ini.key`` so viel leserlicher und kürzer als ``ini[KEY]`` mit einer Konstanten ``KEY = "key"`` ist?
Das Leben ist wie ein Tennisball.
Benutzeravatar
/me
User
Beiträge: 3561
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

Hartmannsgruber hat geschrieben:Ich habe dann gelesen, dass man Objektorientert Programmieren sollte, weil es übersichtlicher und sauberer ist.
Ein Dictionary ist ein Objekt und für diverse Anwendungsfälle viel praktischer als eine eigene Klasse.
Hartmannsgruber
User
Beiträge: 89
Registriert: Mittwoch 15. Januar 2014, 22:30
Wohnort: Bad Kötzting
Kontaktdaten:

Vielen Dank für eure Erklärungen, habe es jetzt kapiert und viel besser Verstanden :-D
Fettes Merci an euch
BlackJack

@Hartmannsgruber: Noch mal was zum OOP weil der letzte Beitrag von /me IMHO etwas missverständlich ist: objektorientierte Programmierung hat man nicht einfach nur weil man Objekte verwendet. Dann wäre *jedes* Python-Programm automatisch OOP, denn *alle* Werte in Python sind Objekte, und in Python ist vieles ein Wert, also Objekt, was in anderen, statischeren Sprachen kein Objekt zur Laufzeit ist (Module, Funktionen, Klassen, …). Darum ist ein Programm das Funktionen und verschachtelte Wörterbücher verwendet nicht OOP (obwohl es das sein könnte) und wenn man diese verschachtelten Wörterbücher durch MagBen's `ObjectModel`-Exemplare ersetzt hat sich nichts geändert als die Syntax mit der man auf die Daten zugreift. Das Programm ist danach noch genau so viel oder wenig objektorientiert wie mit den verschachtelten Wörterbüchern.

Was bei verschachtelten Wörterbüchern unübersichtlich werden kann sind die Verschachtelungen und das die einzelnen ”Arten” von Unterwörterbüchern keinen beschreibenenden Namen haben, der ihnen ”anhaftet”. Ausserdem geht mit solchen verschachtelten Strukturen oft einher, dass in Funktionen auch tief in die Struktur eingegriffen wird und die einzelnen Funktionen Wissen über den Aufbau und den Inhalt von grösseren Teilen der Struktur haben. Was dann auch der Programmierer haben muss wenn er die Funktion liest und verstehen will. Das kann man dann versuchen mit OOP zu verbessern. Der Ansatz fügt zwar etwas Komplexität hinzu, ermöglicht es aber Code und Daten so zu organisieren, dass man Teilausschnitte besser nachvollziehen kann, weil zusammengehörige Daten einen Namen bekommen und nicht nur eine Ansammlung von Schlüssel/Wert-Paaren sind, und weil man ihnen Funktionen zuordnet, die auf diese Daten beschränkt sind und sich nicht über mehrere Ebenen der Gesamtdatenstruktur erstrecken.
Antworten