Problem mit lokaler Variable

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
Chivas
User
Beiträge: 14
Registriert: Dienstag 16. Juni 2009, 10:14
Wohnort: München

Hallo zusammen,

Ich bin ganz neu hier im Forum und auch ganz neu in der Python-Welt. Und ganz zufällig hat sich ein Problem aufgetan :D
Ich möchte eine xml-Datei auslesen und daraus ein Dictionary erstellen. Soweit so gut, aber ich bekomme schon beim Auslesen folgende Fehlermeldung:
local variable 'schiff' referenced before assignment

Code: Alles auswählen

def Schiffkosten (schiffkosten):
	d={}
	baum=dom.parse(schiffkosten)
	for tag in baum.firstChild.childNodes:
		if tag.nodeName =="schiff":
							
			for schiff in tag.childNodes:
				print schiff.nodeName
				if schiff.nodeName =="id":
					sid = int(_knoten_auslesen(schiff))
				elif schiff.nodeName =="name":
					sname = _knoten_auslesen(schiff)	
                elif schiff.nodeName =="kosten":
                    pass
Wenn ich die letzten beiden Zeilen des Codes auskommentiere, funktioniert alles bis dahin.

Hier noch einen Ausschnitt aus der xml:

Code: Alles auswählen

<struktur>
<schiff>
    <id>13</id>
    <name>Sonde X11</name>
    <kosten>
        <ressource>
            <id>1</id>
            <anzahl>0</anzahl>
        </ressource>
...
    </kosten>
</schiff>
</struktur>
Ich bin mir absolut im unklaren darüber, wo der Fehler liegt. Denn wie gesagt, würde ich die letzten beiden Zeilen auslassen, dann funktioniert alles bis dahin.
Ich hoffe ihr könnt mir da helfen.
Ich bin ein blutiger Python-Anfänger und bitte um Rücksicht.
Benutzeravatar
Dill
User
Beiträge: 470
Registriert: Mittwoch 10. Januar 2007, 14:52
Wohnort: Köln

in dem code-teil den du hier gepostet hast dürfte dieser fehler nicht auftreten.

schau dir das mal an:
http://www.python.org/dev/peps/pep-0008/
kannst das gelaber am anfang überspringen, irgendwann wirds sehr substanziös.

und benutze lxml:
http://codespeak.net/lxml/
das ist viel angenehmer als dom, welches imo schande über die wundervolle py-std-lib bringt.
http://www.kinderpornos.info
Chivas
User
Beiträge: 14
Registriert: Dienstag 16. Juni 2009, 10:14
Wohnort: München

Dill hat geschrieben:in dem code-teil den du hier gepostet hast dürfte dieser fehler nicht auftreten
Jo, das hab ich mir auch gedacht. Aber leider tritt dieser Fehler auf. Woran kann es dann liegen? Evtl. an der Zeile davor? Glaub ich aber nicht...

Code: Alles auswählen

def _knoten_auslesen(knoten):
	return knoten.firstChild.data.strip()
Dieses lxml werd ich mir mal anschauen. Danke für den Hinweis.
Ich bin ein blutiger Python-Anfänger und bitte um Rücksicht.
Benutzeravatar
Dill
User
Beiträge: 470
Registriert: Mittwoch 10. Januar 2007, 14:52
Wohnort: Köln

poste mal mehr code und die ganze fehlermeldung.

wenn der code sehr lang ist pack ihn in ein pastebin, zb hier:
http://python.pastebin.com/

(das forum verkraftet lange code-blöcke nicht)
http://www.kinderpornos.info
Chivas
User
Beiträge: 14
Registriert: Dienstag 16. Juni 2009, 10:14
Wohnort: München

Code: Alles auswählen

import xml.dom.minidom as dom
schiffkosten = open ("schiffkosten.xml")

def _knoten_auslesen(knoten):
	return knoten.firstChild.data.strip()

def Schiffkosten (schiffkosten):
	d={}
	baum=dom.parse(schiffkosten)
	for tag in baum.firstChild.childNodes:
		if tag.nodeName =="schiff":
							
			for schiff in tag.childNodes:
				print schiff.nodeName
				if schiff.nodeName =="id":
					sid = int(_knoten_auslesen(schiff))
				elif schiff.nodeName =="name":
					sname = _knoten_auslesen(schiff)	
                elif schiff.nodeName =="kosten":
                    pass
	return 0				
	
u = Schiffkosten(schiffkosten)
Traceback (most recent call last):
File "pythprob.py", line 23, in <module>
u = Schiffkosten(schiffkosten)
File "pythprob.py", line 19, in Schiffkosten
elif schiff.nodeName =="kosten":
UnboundLocalError: local variable 'schiff' referenced before assignment
Ganzer Code und ganze Fehlermeldung.
Ich bin ein blutiger Python-Anfänger und bitte um Rücksicht.
Benutzeravatar
Dill
User
Beiträge: 470
Registriert: Mittwoch 10. Januar 2007, 14:52
Wohnort: Köln

das kann nicht sein.
du scheinst eine andere datei auszuführen, stelle mal sicher, dass du wirklich diesen code ausführst. pack mal ein print "ich bins wirklich" rein...
http://www.kinderpornos.info
Chivas
User
Beiträge: 14
Registriert: Dienstag 16. Juni 2009, 10:14
Wohnort: München

Ich bins wirklich
Traceback (most recent call last):
File "pythprob.py", line 24, in <module>
u = Schiffkosten(schiffkosten)
File "pythprob.py", line 19, in Schiffkosten
elif schiff.nodeName =="kosten":
UnboundLocalError: local variable 'schiff' referenced before assignment
Endlich verstehst du mein Problem^^
Ich bin ein blutiger Python-Anfänger und bitte um Rücksicht.
Benutzeravatar
Dill
User
Beiträge: 470
Registriert: Mittwoch 10. Januar 2007, 14:52
Wohnort: Köln

dann gehört zeile 19 nicht zu dem for-block, sondern zu dem if-block vorher.
checke deine einrückung. mischst du tabs und spaces? hast du einen editor der dir whitespace anzeigen kann?

wahscheinlich sowas in der art:

Code: Alles auswählen

for tag in baum.firstChild.childNodes: 
        if tag.nodeName =="schiff": 
                            
            for schiff in tag.childNodes: 
                print schiff.nodeName 
                if schiff.nodeName =="id": 
                    sid = int(_knoten_auslesen(schiff)) 
                elif schiff.nodeName =="name": 
                    sname = _knoten_auslesen(schiff)    
        elif schiff.nodeName =="kosten": 
            pass 
ist normal, dass man da in der ersten zeit mit py probleme hat.
Zuletzt geändert von Dill am Dienstag 16. Juni 2009, 11:17, insgesamt 1-mal geändert.
http://www.kinderpornos.info
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

Was passiert denn bei dem Code:

Code: Alles auswählen

def Schiffkosten (schiffkosten):
    d={}
    baum=dom.parse(schiffkosten)
    for tag in baum.firstChild.childNodes:
        name = tag.nodeName
        if tag.nodeName =="schiff":
            for schiff in tag.childNodes:
                name = schiff.nodeName
                print name
                if name =="id":
                    sid = int(_knoten_auslesen(schiff))
                elif name =="name":
                    sname = _knoten_auslesen(schiff)   
                elif name =="kosten":
                    pass
Edit: @Dill: hatte ich auch vermutet, aber die Einrückung sieht bis auf Zeile 12 ganz in Ordnung aus.
Das Leben ist wie ein Tennisball.
Chivas
User
Beiträge: 14
Registriert: Dienstag 16. Juni 2009, 10:14
Wohnort: München

Boa ey, das wars wirklich. Ich hab erst mit DrPython gearbeitet. Der gefiel mir aber irgendwie nicht, also hab ich einen Einfachen Texteditor genommen. Bei dem war eingestellt, dass er Tabs mit 4 Leerzeichen ersetzen soll...
Da wär ich wahrscheinlich niemals draufgekommen...
Vielen dank für die Hilfe
Ich bin ein blutiger Python-Anfänger und bitte um Rücksicht.
Benutzeravatar
Dill
User
Beiträge: 470
Registriert: Mittwoch 10. Januar 2007, 14:52
Wohnort: Köln

die probleme hat wohl jeder am anfang.

hier mal dein code mit lxml.objectify

Code: Alles auswählen

>>> from lxml import objectify
>>> f = open("schiffkosten.xml")
>>> otree = objectify.parse(f)
>>> schiffe = otree.xpath("//schiff")
>>> schiffe
[<Element schiff at 15ccf60>]
>>> for schiff in schiffe:
...     print schiff.id
...     print schiff.name
...
13
Sonde X11
http://www.kinderpornos.info
Benutzeravatar
cofi
Python-Forum Veteran
Beiträge: 4432
Registriert: Sonntag 30. März 2008, 04:16
Wohnort: RGFybXN0YWR0

lxml ist zwar wirklich ein feines Stück Software, aber vielleicht tut es auch ElementTree in der StdLib ?
Antworten