Variabler Dateiname

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.
Ned Nederlander
User
Beiträge: 13
Registriert: Montag 19. Oktober 2009, 13:39

Hallo,
hab eine klitzekleine Frage:

Ich schreibe gerade eine Klasse, die als Eingabe unter anderem einen Namen geliefert bekommt. Die Ausgabe der Klasse ist eine txt-Datei, die eben diesen Namen als Dateiname bekommen soll.

Code: Alles auswählen

class ausgabe:
    def __init__(self, Liste, Verfahren):
		self.Liste = Liste
		self.Verfahren = Verfahren
			
		
		fobj = open("Verfahren.txt", "w")

		.
                .
                .

			
		fobj.close()
hab einige Bücher und Tutorials befragt, allerdings kommt da immer nur ein Beispiel mit einem bestimmten Dateinamen.


Danke für Ratschläge!
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

Hallo.

Hier sind drei verschiedene Möglichkeiten:

Code: Alles auswählen

"%s.txt" % "Dateiname"
"{0}.txt".format("Dateiname")
"{name}.txt".format(name="Dateiname")
Edit: Schau dir doch noch einmal PEP 8 bezüglich der Namensgebung an. Klassen solltest du in "CamelCase" schreiben und Parameter "klein_und_getrennt_durch_unterstriche".

Vielleicht geht es in deinem Beispiel auch nur Unter, ab du solltest beim Öffnen von Dateien natürlich auch Fehler behandeln.
Zuletzt geändert von EyDu am Mittwoch 21. Oktober 2009, 14:30, insgesamt 1-mal geändert.
Das Leben ist wie ein Tennisball.
CM
User
Beiträge: 2464
Registriert: Sonntag 29. August 2004, 19:47
Kontaktdaten:

Hoi,

Wozu die Klasse, wenn Du in der Initialisierung rechnest?
Lies mal das offzielle Python Tutorial, ggf. auch auf Deutsch (für Dich passende Version beachten). Und bei Gelegenheit auch PEP8.

Und benenne Deine Klassen, Attribute, Funktionen und Objekte doch etwas deskriptiver. Was soll "Liste" z. B. enthalten? Wäre *das* nicht ein guter Name?

Zur Frage: Da reicht eine Funktion, der man den Dateinamen übergibt. Woher Du den bekommst? Entweder fest verdrahten ;-) oder per OptionParser oder per Configfile oder .... Da gibt es 1001 Möglichkeit. Mehr dazu im Tutorial und der Modulübersicht.

HTH
Christian
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

Ned Nederlander hat geschrieben: hab einige Bücher und Tutorials befragt, allerdings kommt da immer nur ein Beispiel mit einem bestimmten Dateinamen.
Ich muss mal gestehen, dass ich an dieser Frage seinerzeit auf dem C64 im Commodore Basic V2 auch verzeifelt bin. Ich hatte es einfach nicht gerafft, wie ich eine Variable beim "open" Befehl verwenden konnte. Mann mann mann :oops: Das waren noch Zeiten :lol:
Benutzeravatar
jbs
User
Beiträge: 953
Registriert: Mittwoch 24. Juni 2009, 13:13
Wohnort: Postdam

Hyperion hat geschrieben:
Ned Nederlander hat geschrieben: hab einige Bücher und Tutorials befragt, allerdings kommt da immer nur ein Beispiel mit einem bestimmten Dateinamen.
Ich muss mal gestehen, dass ich an dieser Frage seinerzeit auf dem C64 im Commodore Basic V2 auch verzeifelt bin. Ich hatte es einfach nicht gerafft, wie ich eine Variable beim "open" Befehl verwenden konnte. Mann mann mann :oops: Das waren noch Zeiten :lol:
Ned, aus dir kann also noch was werden :)!
[url=http://wiki.python-forum.de/PEP%208%20%28%C3%9Cbersetzung%29]PEP 8[/url] - Quak!
[url=http://tutorial.pocoo.org/index.html]Tutorial in Deutsch[/url]
Ned Nederlander
User
Beiträge: 13
Registriert: Montag 19. Oktober 2009, 13:39

vielen dank erstmal, funktioniert wunderbar!

gibts auch ne möglichkeit, in den dateinamen noch ne fortlaufende nummer einzubauen? die klasse wird in einer for-schleife aufgerufen, und erhält auf diesem weg die fortlaufenden nummern. ich verzweifel nur gerade daran, die zahl in den dateinamen einzufügen :-(

Code: Alles auswählen

class Ausgabe:
    def __init__(self, Liste, Dateiname, Nummer):
        self.Liste = Liste
        self.Dateiname = Dateiname
        self.Nummer = Nummer

			
        fobj = open("%s.txt" % Dateiname, "w") 
		
..............
			
        fobj.close()


Danke!
Benutzeravatar
jbs
User
Beiträge: 953
Registriert: Mittwoch 24. Juni 2009, 13:13
Wohnort: Postdam

Code: Alles auswählen

'%s' %name+str(nummer)
'%s%s' %(name,nummer)
'{name}_{nummer}'.format(name=name, nummer=nummer)'
oder wie auch immer :)


aber schau dir doch das Tutorial einmal an
[url=http://wiki.python-forum.de/PEP%208%20%28%C3%9Cbersetzung%29]PEP 8[/url] - Quak!
[url=http://tutorial.pocoo.org/index.html]Tutorial in Deutsch[/url]
Benutzeravatar
cofi
Python-Forum Veteran
Beiträge: 4432
Registriert: Sonntag 30. März 2008, 04:16
Wohnort: RGFybXN0YWR0

Ja das geht. Mit der gleichen Methodik ;) Das Rausfinden/Doku lesen ueberlasse ich mal dir, sonst is das nich so lehrreich.

Aber: Bei dem Klassennamen `Ausgabe` ahne ich schlimmes .. kann es sein, das sich die Klasse nur um die Ausgabe kuemmert, d.h. eigtl nur eine Funktion ist?

Ausserdem sollte man `open` mindestens in ein `try ... finally` einpacken oder noch besser in ein `with`:

Code: Alles auswählen

try:
    fobj = open(fname)
    do_stuff()
finally:
    fobj.close()

with open(fname) as fobj:
    do_stuff()
Und natuerlich der obligatorische Hinweis auf PEP8.
Benutzeravatar
str1442
User
Beiträge: 520
Registriert: Samstag 31. Mai 2008, 21:13

Man sollte do_stuff() in ein try-finally packen und nicht open(), sonst gibts bei fobj nen Name- oder AttributeError. Wenn open() fehlschlägt muss man nichts schließen und dann hat man sowieso einen EnvironmentError rumfliegen.
Benutzeravatar
cofi
Python-Forum Veteran
Beiträge: 4432
Registriert: Sonntag 30. März 2008, 04:16
Wohnort: RGFybXN0YWR0

Das ist wahr, allerdings ist das im `else` Zweig IMHO besser aufgehoben

Code: Alles auswählen

try:
    fobj = open(fname)
else:
    do_stuff()
finally:
    fobj.close()
Zap
User
Beiträge: 533
Registriert: Freitag 13. Oktober 2006, 10:56

cofi hat geschrieben:

Code: Alles auswählen

try:
    fobj = open(fname)
else:
    do_stuff()
finally:
    fobj.close()
Das ist doch immer noch verkehrt. Wenn open fehlschlägt existiert kein name "fobj". Also kann im finally Block auch kein close() ausgeführt werden.

Das hier wären zwei Möglichkeiten:

Code: Alles auswählen

# since python3.x or "from __future__ import with_statement"
with open(fname) as fobj:
    do_stuff()

# pyhton2.x
fob = open(fname)
try:
    do_stuff()
finally:
    fobj.close()
Zuletzt geändert von Zap am Donnerstag 22. Oktober 2009, 09:26, insgesamt 1-mal geändert.
BlackJack

@cofi: Seit wann gibt's da einen ``else``-Zweig?
Benutzeravatar
cofi
Python-Forum Veteran
Beiträge: 4432
Registriert: Sonntag 30. März 2008, 04:16
Wohnort: RGFybXN0YWR0

BlackJack hat geschrieben:@cofi: Seit wann gibt's da einen ``else``-Zweig?
Ich hab das jetzt bis 2.0 zurueckverfolgt, ob das der gleichen Semantik folgt, kann ich jetzt nicht sagen.

@Zap: Du hast da auch einen echten `NameError`. Abseits davon is das auch nich richtig, weil dir ein `OSError` entgegenfliegen kann.

Code: Alles auswählen

try:
    fobj = open(fname)
    try:
        do_stuff()
    finally:
        fobj.close()
except OSError, e:
    pass
Zap
User
Beiträge: 533
Registriert: Freitag 13. Oktober 2006, 10:56

cofi hat geschrieben:@Zap: Du hast da auch einen echten `NameError`. Abseits davon is das auch nich richtig, weil dir ein `OSError` entgegenfliegen kann.
Wo sollte denn ein NameError herkommen? (Jetzt sag nicht bei "fname")
By einem try->finally sowie einem with Konstrukt fliegen einem alle Exceptions ungesehen um die Ohren. Es geht hier ja darum das eine Datei wieder sauber "geclosed" wird. Egal was bei der Verabeitung damit passiert.
BlackJack

@cofi: Also ich habe ein 2.5 und da kann man das ``else`` nicht ohne ``except`` verwenden, auf dass es sich bezieht.
Benutzeravatar
cofi
Python-Forum Veteran
Beiträge: 4432
Registriert: Sonntag 30. März 2008, 04:16
Wohnort: RGFybXN0YWR0

Ah ok, das kann sein. Hatte das nicht getestet.

Code: Alles auswählen

try:
    fobj = open(fname)
except OSError, e:
    print "Oh Oh, going down"
else:
    do_foo()
finally:
    fobj.close()
Nu aber ;)

@Zap: Weil dir ein `j` fehlt ;) Um das sauber zu schliessen, muesste es existieren, bei dir tritt das Problem nicht auf, weil dir das gleich beim oeffnen um die Ohren fliegt, wenn es ein Problem gibt.
Dass es bei `with` und `try ... finally` genauso scheitert, ist richtig, dass du das aber in Code aenderst, der dir sowieso um die Ohren fliegt, wenn was falsch laeuft macht ihn nicht richtiger, nur weil du das Problem verlagerst.
Benutzeravatar
HWK
User
Beiträge: 1295
Registriert: Mittwoch 7. Juni 2006, 20:44

Code: Alles auswählen

IDLE 2.6.2      
>>> try: 
    fobj = open('MichGibtEsNicht') 
except OSError, e: 
    print "Oh Oh, going down" 
else: 
    do_foo() 
finally: 
    fobj.close()

Traceback (most recent call last):
  File "<pyshell#1>", line 8, in <module>
    fobj.close()
NameError: name 'fobj' is not defined
Dein letzter Vorschlag war besser.
MfG
HWK
jerch
User
Beiträge: 1669
Registriert: Mittwoch 4. März 2009, 14:19

Ich nutzte seinerzeit ohne try/except/finally-Konstrukt gelegentlich ein c-ähnliches handling, falls die Ausnahmebehandlungen zu unübersichtlich wurden:

Code: Alles auswählen

fobj = None
try:
    fobj = open(...)
    code_mit_weiteren_ausnahmen()
finally:
    if fobj:
        fobj.close()
    else:
        # pseudo-exception
Hatte den Vorteil, daß "übersehene" Ausnahmen im Inneren trotzdem zum Vorschein kamen während das Dateiobjekt richtig behandelt wurde. Ist mit try/except/finally und with heutzutage viel einfacher.
Zap
User
Beiträge: 533
Registriert: Freitag 13. Oktober 2006, 10:56

Dann lieber so:

Code: Alles auswählen

try:
    fobj = open(fname)
    do_stuff(fobj)
except OSError, e: # ergänzt, damit cofi auch glücklich ist ;)
    print "Oh Oh, going down" 
finally:
    try:
        fobj.close()
    except NameError:
        pass
Ich bin allerdings der Meinung, dass das Öffnen einer Datei die Grundvorausausetzung für die weitere Bearbeitung ist und somit nicht in den selben try-Block gehört.
jerch
User
Beiträge: 1669
Registriert: Mittwoch 4. März 2009, 14:19

War man nur am Abfangen der Dateiaktionen interessiert, ging es nach altem Muster auch so:

Code: Alles auswählen

try:
    fobj = open(...)
    try:
        weiterer_dateikram()
    finally:
        fobj.close()
except IOError, e:
    print e # oder was auch immer
Soweit nicht von weiterer_dateikram() behandelt, wurden hier allerdings alle IOErrors abgefangen.
Antworten