Nur jede x.Zeile aus einer Textdatei auslesen

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

Hi,

ich habe vor kurzem angefangen ein Programm zu schreiben, dass sich Informationen aus eine Textdatei holt, damit ich es leichter mit neuen Informationen "füttern" kann.

Immer 3 Zeilen repräsentieren ein Objekt:

1.Objekt(1.Zeile,2.Zeile,3.Zeile)
2.Objekt(4.Zeile,5.Zeile,6.Zeile)
3.Objekt(7.Zeile,8.Zeile,9.Zeile)
...

Hat jemand eine Idee, wie ich das anstellen könnte?

(Ich weiß, dass ich es auch mit Sonderzeichen getrennt in eine Zeile schreiben könnte, aber das wäre dann beim "füttern" unübersichtlich)
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

Wie wäre es, wenn Du das ganze mit einem existierenden Format lösen würdest, etwa JSON, YAML oder XML? Wenn es wirklich nur auf das temporäre Serialisieren ankommt, wäre ``pickle`` auch noch eine Option.

Um aber auf die Frage (aus der Überschrift) zurück zu kommen: Du kannst ja über die Zeilen einer Textdatei einfach iterieren. Du könntest dazu einen Index erstellen (``enumerate``) und mittels Modulo-Berechnung prüfen, ob eine Zeile gelesen bzw. präziser weiterverarbeitet werden soll oder nicht.

Alternativ fiele mir noch ``itertools.cycle`` ein, um eine bestimmte, sich wiederholende Sequenz zu generieren.
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
Benutzeravatar
Balmung
User
Beiträge: 44
Registriert: Sonntag 17. März 2013, 18:36

Auch eine mögliche Antwort wäre mit zip() oder itertools.zip_longest() (oder itertools.izip_longest() wenn python2):

Code: Alles auswählen

with open('thefile', 'r') as f:
    for line1, line2, line3 in itertools.zip_longest(f, f, f):  # oder: itertools.zip_longest(*([f]*3))
        obj = Objekt(line1, line2, line3)
        # blah..
»Honk Honk«
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Okay, danke mit itertools hats geklappt, auch wenn ich noch nicht ganz verstanden habe warum.

Wisst ihr wo ich die itertools.py herbekomme, damit es jemand anderes auch importieren kann,
oder ist es egal, wo das Programm auf dem Computer ausgeführt wird?
Benutzeravatar
Balmung
User
Beiträge: 44
Registriert: Sonntag 17. März 2013, 18:36

itertools gehört zur standard library von Python. Hast du Python installiert, dann ist itertools auch vorhanden.
»Honk Honk«
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

Tobs hat geschrieben:Okay, danke mit itertools hats geklappt, ...
Ich möchte Dir noch mal meinen ersten Vorschlag ans Herz legen! :-)
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Mir fällt grad ein, dass ich ja auch 2 Zähler hätte nehmen können,
einen für die Zeilen, und einen von 1-3 der dann immer zurückgesetzt wird -,-
Aber die Lösung mit itertools sieht irgendwie besser aus...
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Ich kenn die ganzen Formate net :(

Kannst du sie mir mal kurz mit Eigenschaften, Vor- und Nachteilen aufzählen?
Tobs
User
Beiträge: 65
Registriert: Sonntag 29. September 2013, 11:11

Hast du mich gehackt :mrgreen: ? Jetzt sagt er dass itertools keine Attribut namens zip_longest hat :roll:
Benutzeravatar
/me
User
Beiträge: 3555
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

Tobs hat geschrieben:Jetzt sagt er dass itertools keine Attribut namens zip_longest hat :roll:
Und vorher ging es? Dann hast du vorher Python 3 verwendet und jetzt Python 2. Diese beiden Versionen sind (bewusst) nicht vollständig kompatibel.
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

Tobs hat geschrieben:Ich kenn die ganzen Formate net :(

Kannst du sie mir mal kurz mit Eigenschaften, Vor- und Nachteilen aufzählen?
Äh...nö ;-) Aber Du kannst dazu ja selber mal etwas recherchieren!

Primär ging es mir eher darum, dass Du das Rad nicht neu erfinden musst! Python hat bereits in Modul für das Verarbeiten von JSON mit an Bord: ``json``. Schau Dir dazu die Doku an; das Laden und Speichern geht extrem simpel. Du musst dann lediglich noch die gelesenen Daten nutzen, um Deine Objekte zu erzeugen.

Mal ein Beispiel:

Code: Alles auswählen

class User:
    def __init__(self, screenname, password):
        self.screenname = screenname
        self.password = password
    def __str__(self):
        return self.screenname

data = [
["Hyperion", "geheim"],
["Foo", "Bar"]
]

import json

s = json.dumps(data)

print(s)
> '[["Hyperion", "geheim"], ["Foo", "Bar"]]'

loaded_data = json.loads(s)

print(loaded_data)
> [['Hyperion', 'geheim'], ['Foo', 'Bar']]

users = [User(name, password) for name, password in loaded_data]

users
[<__main__.User at 0x48d8f98>, <__main__.User at 0x4995048>]

for user in users:
    print(user)

> Hyperion
> Foo

print(users[0].password)
> 'geheim'
JSON kann die Standard-Python Daten einfach serialisieren und deserialisieren. Du brauchst dann nur noch eine Fabrik-Funktion, die Dir aus solchen Datenobjekten (``data`` / ``loaded_data`` in diesem Beispiel) tatsächlich Deine Domänenobjekte (Objekte vom Typ ``User``) erstellt.

Ich habe mir das JSON natürlich durch Python generieren lassen; man kann es aber eben auch leicht von Hand schreiben.
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
Antworten