Hallo! Ich bin gerade dabei, mir mit Hilfe von Python als Anfänger das objektorientierte Programmieren etwas näher zu bringen. Neben dem Lesen von Büchern und zahlreichen Online-Hilfen, probiere ich mich an einem kleinen Server/Client Projekt. Was ich aktuell nicht ganz verstehe, ist der Unterschied zwischen folgenden zwei Definitionen:
class MyClass: x=1
def __init__(self): pass <<<
class MyClass:
klasse = MyClass()
def __init__(self): self.x=1 <<< Im ersten Fall wird x als Klassenattribut beschrieben, im zweiten Fall soll es ein Objektattribut sein? Aber kann nicht beides über print klasse.x <<< angesprochen werden? Für euch sicher eine Kleinigkeit, mir das mal kurz zu erklären. -- MfG Pascal Dreisbach _______________________________________________ python-de maillist - python-de@python.net http://python.net/mailman/listinfo/python-de
Hallo, Pascal Dreisbach schrieb:
Im ersten Fall wird x als Klassenattribut beschrieben, im zweiten Fall soll es ein Objektattribut sein?
klasse = MyClass()
Aber kann nicht beides über print klasse.x <<< angesprochen werden?
Das stimmt. Was aber nicht in beiden Fällen geht, ist der Zugriff auf x ohne eine Instanz von MyClass.
MyClass.x # geht nur im ersten Fall 1
Du siehst den Unterschied, wenn Du sowohl Klassen- als auch Instanz-Attribute gleichzeitig verwendest.
class MyClass: ... x = 1 # Klassen-Attribut ... def __init__(self): ... self.x = 2 # Instanz-Attribut ... instance = MyClass() instance.x, MyClass.x # Instanz-Attribut, Klassen-Attribut (2, 1)
Gruß Lutz _______________________________________________ python-de maillist - python-de@python.net http://python.net/mailman/listinfo/python-de
Pascal Dreisbach wrote:
Hallo!
Ich bin gerade dabei, mir mit Hilfe von Python als Anfänger das objektorientierte Programmieren etwas näher zu bringen.
Neben dem Lesen von Büchern und zahlreichen Online-Hilfen, probiere ich mich an einem kleinen Server/Client Projekt.
Was ich aktuell nicht ganz verstehe, ist der Unterschied zwischen folgenden zwei Definitionen:
class MyClass: x=1
def __init__(self): pass <<<
class MyClass:
def __init__(self): self.x=1 <<<
Im ersten Fall wird x als Klassenattribut beschrieben, im zweiten Fall soll es ein Objektattribut sein?
klasse = MyClass()
Aber kann nicht beides über print klasse.x <<< angesprochen werden?
Für euch sicher eine Kleinigkeit, mir das mal kurz zu erklären.
sowohl ein eine klasse als auch eine instanz haben (je) ein attibut __dict__ das alle klassen bzw instanzvariabeln speichert. beim zugriff auf ein attribut sucht python zuerst im __dict__ der instanz ob es fündig wird. du kannst das selbst überprüfen Python 2.3.5 (#3, Jun 7 2005, 06:49:54) [GCC 3.3.5 20050117 (prerelease) (SUSE Linux)] on linux2 Type "help", "copyright", "credits" or "license" for more information.
class C: ... classattr='classattr' ... C.__dict__ {'classattr': 'classattr', '__module__': '__main__', '__doc__': None} c=C() c.instanceattr='instanceattr' c.__dict__ {'instanceattr': 'instanceattr'} dir(c) ['__doc__', '__module__', 'classattr', 'instanceattr'] dir(C) ['__doc__', '__module__', 'classattr']
robert _______________________________________________ python-de maillist - python-de@python.net http://python.net/mailman/listinfo/python-de
Pascal Dreisbach:
Ich bin gerade dabei, mir mit Hilfe von Python als Anfänger das objektorientierte Programmieren etwas näher zu bringen.
Liest Du auch Sachen über OO ohne Bezug zu Python? Fällt vielleicht am Anfang leichter.
Was ich aktuell nicht ganz verstehe, ist der Unterschied zwischen folgenden zwei Definitionen: [ Zugriff auf Klassenattribute über Instanzen ]
Was Du siehst ist meiner Meinung nach eine kleine "Unsauberkeit" in Pythons Implementation von Objektorientierung. Du kannst zwar Klassenattribute von einer Instanz der Klasse aus /lesen/, aber nicht schreiben. Das muss in Python auch so sein, sonst hätten Instanzen nichtmal Methoden. :) Mit der "reinen Lehre" hat das aber nichts zu tun, das ist eher schmutzige (aber sehr interessante) Wirklichkeit. Das sind aber Implementierungsdetails, die Dich momentan wahrscheinlich eher verwirren, als weiterbringen. Falls es Dich doch genauer interessiert, wie Python mit Objekten und Klassen hinter den Kulissen arbeitet (und Du des Englischen mächtig bist), empfehle ich folgende zwei Artikel: http://cafepy.com/article/python_types_and_objects/ http://cafepy.com/article/python_attributes_and_methods/ Ich schreibe übrigens gerade eine kleine Hausarbeit zu dem Thema. Sobald ich damit fertig bin, werde ich das hier und/oder in de.comp.lang.python auch veröffentlichen. Wer ungeduldig ist, kann auch gern eine Vorabversion bekommen. J. -- I throw away plastics and think about the discoveries of future archeologists. [Agree] [Disagree] <http://www.slowlydownward.com/NODATA/data_enter2.html> _______________________________________________ python-de maillist - python-de@python.net http://python.net/mailman/listinfo/python-de
Pascal Dreisbach schrieb:
Ich bin gerade dabei, mir mit Hilfe von Python als Anfänger das objektorientierte Programmieren etwas näher zu bringen.
Neben dem Lesen von Büchern und zahlreichen Online-Hilfen, probiere ich mich an einem kleinen Server/Client Projekt.
Was ich aktuell nicht ganz verstehe, ist der Unterschied zwischen folgenden zwei Definitionen:
class MyClass: x=1
def __init__(self): pass <<<
class MyClass:
def __init__(self): self.x=1 <<<
Im ersten Fall wird x als Klassenattribut beschrieben, im zweiten Fall soll es ein Objektattribut sein?
klasse = MyClass()
Aber kann nicht beides über print klasse.x <<< angesprochen werden?
Ja, aber der wichtigste Unterschied liegt in der Benutzung. Im ersten Fall ist der Wert in der Klasse gespeichert, also für alle Instanzen der Klasse identisch. Im zweiten Fall ist der Wert Teil der Instanzen, also unabhängig. Also: class Klassenhalter: x = 1 class Objekthalter: def __init__(self): self.x = 1 c1 = Klassenhalter() c2 = Klassenhalter() c1.x = 2 print c2.x gibt dir 2 aus. Anders hier: o1 = Objekthalter() o2 = Objekthalter() o1.x = 2 print o2.x das gibt 1 aus und nicht 2. Wichtig ist, dass Instanzattribute (und Methoden) Klassenattribute überschreiben. Stell dir einfach vor, dass die Klasse zuerst da ist und alles, was in der Instanz hinzukommt, vorne angestellt wird, also zuerst sichtbar ist. Der Zugriff auf Klassenattribute ist immer über diesen Umweg möglich: c1.__class__.x denn c1.__class__ erlaubt dir den Zugriff auf die Klasse (oder, genauer gesagt, das Klassenobjekt). Vielleicht verwirrt es dich, dass Klassen in Python auch Objekte sind, eben Klassenobjekte, von denen Objektinstanzen abgeleitet werden können. Aber das ist in den "wahren" OO-Sprachen eigentlich immer der Fall. Alles ist ein Objekt. Nebenbei bemerkt, eigentlich ist es sogar eine sehr schöne Eigenschaft von Python, dass es keinen sichtbaren Unterschied zwischen der Verwendung von Klassenobjekten, aufrufbaren Objekten (Stichwort __call__) und Funktionen gibt. Du rufst sie auf und erhälst das Ergebnis zurück. Aber gut, danach war ja eigentlich gar nicht gefragt... Hoffe geholfen zu haben, Stefan _______________________________________________ python-de maillist - python-de@python.net http://python.net/mailman/listinfo/python-de
participants (5)
-
Jochen Schulz
-
Lutz Horn
-
Pascal Dreisbach
-
robert rottermann
-
Stefan Behnel