Objekt hat kein Attribut <hier Namen der Funktion einfügen>

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.
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Freitag 18. April 2014, 13:34

Liebe Pythongemeinde,

ich habe folgendes Problem:

Ich habe eine Klasse definiert, mit mehreren Funktionen.
Wenn ich eine bestimmte Funktion aus dieser Klasse anwende,
behandelt Python sie trotz Klammern dahinter, und einer passenden Anzahl an Attributen,
als Attribut der Klasse und gibt infolge dessen folgenden Fehler aus:

Traceback (most recent call last):
File "E:\Python32\Lösungsentwurf.py", line 15, in <module>
cube.turn(v)
AttributeError: 'Cube' object has no attribute 'turn'

Dabei sollte cube.turn(v) doch als Funktion anerkannt werden, wegen der Klammern dahinter?
Ich habe die Funktion in der Klasse nach weiter oben verschoben, umbenannt und groß-klein-schreibung geändert,
hat alles nicht geholfen. Ich habe noch eine in der Klasse die groß geschrieben ist, könnte das die Ursache sein?
Oder passt es Python einfach nicht, dass die Funktion cube.turn() in sich weiter Funktionen der Klasse aufruft(wie ich es auch gemacht habe)

Ich bekomme diesen Fehler auch bei anderen Programmen häufig, es wäre also gut, wenn ihr mir noch allgemein sagen könntet,
wodurch dieser Fehler ausgelöst wird

Danke im vorraus
BlackJack

Freitag 18. April 2014, 13:44

@Tobs: Vorweg: Funktionen in Klassen heissen Methoden. Und bei „einer passenden Anzahl an Attributen” meintest Du sicher „Argumente” und nicht „Attribute”.

Methoden werden als Attribute behandelt weil es Attribute sind. Das sind halt Attribute die man aufrufen kann, nach dem man sie vom Objekt abgefragt hat. Nur kommt es bei Dir ja gar nicht bis da hin, denn der Abfruf von `turn` schlägt schon fehl weil das `cube`-Objekt an der Stelle offenbar keine solche Methode hat.

Gross- und Kleinschreibung wird von Python unterschieden, also `turn` ist etwas anderes als `Turn`, oder `tUrN`, …, das sollte also bei der Definition und beim Ab-/Aufruf gleich geschrieben werden. Die Definition innerhalb der Klasse nach oben oder unten zu verschieben sollte keinen Unterschied machen. Das fällt unter die Kategorie, sinnloses, verzweifeltes Rumprobieren. ;-)

Bist Du sicher das hier der richtige `Cube`-Datentyp verwendet wird? Nicht vielleicht eine alte Version davon? Startest Du das Programm neu/frisch, oder vielleicht in einer IDE/Umgebung dir komische Sachen macht?
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Freitag 18. April 2014, 14:06

Erstmal wieder Danke für die Antwort.

Ja ich meine Methoden, und ja ich meine Argumente ;-)

Die Methode turn(anweisung) ist bei mir definitiv in einem anderen Modul vorhanden,
das ich mit from Cube import * importiert habe.

Ich weiß , dass Python Groß- und Kleinschreibung unterscheidet, und habe es
natürlich in beiden Skripten geändert. Ich dachte nur, dass die Groß - und Kleinschreibung vielleicht
eine Ursache für den Fehler gewesen sein könnte, genauso, wie der Name der Methode oder die Tatsache,
dass diese Methode andere Methoden der Klasse in sich aufruft(auf dasselbe Objekt bezogen).

Deshalb stell ich ja die Frage: Ich hab Syntaxgemäß alles richtig gemacht, warum erkennt Python es nicht als Funktion an?

Und wenn ich ein Objekt mit der __init__(self,bla1,bla2,...) initialisiere,
dann besitzt das Objekt doch alle Methoden die ich für dieses Klasse definiert habe?
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Freitag 18. April 2014, 14:16

Hab grade noch herausgefunden, dass auch keine andere Methode dieser Klasse in
meinem 2.Skript funktioniert
BlackJack

Freitag 18. April 2014, 14:43

@Tobs: Ob Du bei der Definition von der `Cube`-Klasse alles richtig gemacht hast, kann man ohne den Quelltext zu sehen schlecht sagen.

Wenn Du ein `Cube`-Exemplar erstellt hast, dann hat das Objekt alle Methoden die in der Klasse definiert sind.

Also stellen sich drei Fragen: 1. Hast Du die Methoden richtig definiert? 2. ist der `Cube`-Typ tatsächlich der aus dem richtigen Modul? 3. Tritt das Problem bei einem völlig frischen Programmablauf auf?
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Freitag 18. April 2014, 14:57

1. Ja:

Code: Alles auswählen

class Cube():

    def __init__(self,...,...):

        ...

    def turn(eingabe):

        if eingabe == xy:
            anderefunktionausderklasse()
        elif:
            nocheineanderefunktionausderklasse()
        ...
2. Ja von "Cube.py" müsste man mithilfe von "from Cube import *" , wenn es im selben Ordner ist doch Alles bekommen, oder?
3. Ja, ich hab alles nochmal geöffnet und gespeichert, in der Konsole und in IDLE ausgeführt: Jedes mal dieser Fehler

Das Problem ist auch anderen Programmieren passiert. Manche sagen, dass das vom "Programm zum Python Programmieren falsch verstanden wird"

Ich glaub ich installiere einfach mal Python neu und schau, ob sich was geändert hat...
Zuletzt geändert von Anonymous am Freitag 18. April 2014, 15:04, insgesamt 1-mal geändert.
Grund: Quelltext in Python-Code-Tags gesetzt.
Sirius3
User
Beiträge: 11556
Registriert: Sonntag 21. Oktober 2012, 17:20

Freitag 18. April 2014, 15:00

@Tobs: wie hast Du eigentlich die Instanz »cube« der Klasse »Cube« erzeugt? Hast Du dazwischen »cube« mit irgendeinem anderen Objekt überschrieben? Wenn Du vor dem Attributzugriff Dir die Variable »cube« mit print ausgeben läßt, was erscheint auf dem Bildschirm?

Und noch was: wie sind die Einrückungen. Kann man ja nicht sehen, weil Du die python-Umgebung im Forum nicht benutzt. Wenn »turn« eine Methode sein soll, fehlt zudem »self« als erstes Argument.
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Freitag 18. April 2014, 15:05

Jetzt hab ich beide Dateien vom Desktop runter und in den Python32 ordner gesteckt,
und jetzt kommt gleich in Zeile 1 bei "from Cube import *" der Fehler, dass ihm eine Datei namens
PyShell.py in den idlelibs nicht passt, obwohl die in einem try-block steht -,-
BlackJack

Freitag 18. April 2014, 15:09

@Tobs: Es fehlt nicht nur `self` als Argument der Methode, sondern wenn das andere da drin auch Methoden von `Cube` sind, dann musst Du die natürlich über `self` referenzieren.

Ad 2.: Das kommt drauf an ob beides in einem Package definiert ist und wie das Arbeitsverzeichnis des Prozesses lautet, und ob im Suchpfad für Module nicht eventuell noch ein anderes `Cube`-Modul vorher gefunden wird.

In den Python-Ordner sollte man nichts kopieren. Da kann man sich wenn's blöd läuft die Installation mit kaputt machen.
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Freitag 18. April 2014, 15:19

Ok, das mit dem Pythonordner merk ich mir, das mit dem "self" stimmt natürlich,
hab ich auch so gemacht, habs aber vergessen hinzuschreiben. Auf der neuen Python-version(3.4)
läuft mein Skript einwandfrei BIS AUF EINE AUSNAHME :roll: :

Die Methode sucht nach einer Lösung. Wenn sie diese gefunden hat, soll sie diese einer globalen Variable zuweisen. Das passiert nicht.
Die Methode soll die Lösung mit print() in der Konsole ausgeben. Das passiert nicht. Alle anderen print-anweisungen funktionieren.

HÄ?
BlackJack

Freitag 18. April 2014, 15:22

@Tobs: Ohne den Code zu sehen kann man da nicht viel zu sagen. Wobei globale Variablen keine gute Idee sind.
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Freitag 18. April 2014, 15:23

Der Suchzeit nach zu urteilen findet die Funktion auch die richtige Lösung, aber die Methode druckt halt nichts aus
und irgendwie ändert sie auch an der globalen Variable Loesung nichts...
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Freitag 18. April 2014, 15:30

Der Aufbau der Methode ist so:

Code: Alles auswählen

def Funktion(self,arg1,...):

    global Loesung

    <hier wird arg1 verändert>

    if len(arg1) < len(Loesung):       #Das funktioniert nicht :-(
        Loesung = arg1
        print(arg1)
BlackJack

Freitag 18. April 2014, 15:35

@Tobs: Was heisst „funktioniert nicht”? Es wird ganz einfach die Länge von `arg1` nicht kleiner als die Länge von `Lösung` sein. Mehr kann man da so nicht zu sagen. Lass Dir doch beides mal vor dem ``if`` ausgeben, dann siehst Du ja was für Werte das zu dem Zeitpunkt sind.

Und nochmal: ``global`` sollte man vermeiden. Insbesondere in einer Methode ist das IMHO nicht mehr eine Stilfrage sondern schlicht falsch. Denn ``global`` wird man in der Regel durch objektorientierte Programmierung los. Wenn man das also in einer Methode verwendet, dann stimmt etwas mit dem Entwurf nicht.
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Freitag 18. April 2014, 15:57

Okay, danke. Jetzt gibt es nur noch dieses eine Problem, das mich in den Wahnsinn treibt:

Der If-Block wird ausgeführt, die globale Variable ist oben definiert, aber wenn er die globale Variable
am Ende ausdruckt hat sie wieder den selben Wert wie vor der Funktion (Ist das ein Gesetzt in Python?)

Da du mir von globalen Variablen abrätst, (auch wenn die Funktion 14 Ebenen tief geschachtelt sind)
wie würdest du das Problem lokal lösen. Als Python-Neuling hab ich da keinen Durchblick wie soetwas anderweitig zu bewerkstelligen wäre...
Antworten