Dateieinlesung während des Downloads

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.
Horst73
User
Beiträge: 15
Registriert: Dienstag 5. Juni 2018, 14:08

Hallo Liebe Community,

ich sitze vor einer Programmieraufgabe.

Ich soll ein Programm schreiben, welches eine Datei einliest und dann jedesmal wenn bestimmte Texte auftaucht diese Zählt.

Das habe ich auch soweit schon fertig. Das Problem ist nun, dass ich die Datei aktuell selber herunterlade und lokal speichere. Genau das ist aber nicht erwünscht.

Die Datei soll vom Programm selbst heruntergeladen werden und eingelesen werden. Dabei wäre es am besten, wenn es NICHT erst zu einem kompletten download kommt, dann die Datei abgearbeitet wird und anschließend wieder gelöscht wird. Perfekt wäre es also, wenn die Datei während des downloads prozessiert wird ohne dass sie auf der Festplatte gespeichert wird.

Die Datei ist in tausende Abschnitte unterteilt, welche durch wiederkehrende Sonderzeichen eindeutig voneinander getrennt sind.

Ich wäre dankbar für ein paar Tips, wie man dieses Problem angehen könnte.

Liebe Grüße

Horst
Benutzeravatar
sls
User
Beiträge: 480
Registriert: Mittwoch 13. Mai 2015, 23:52
Wohnort: Country country = new Zealand();

Dann verarbeite die Datei als Stream, Python stellt dir für diese Aufgabe io.BytesIO / io.StringIO zur Verfügung. So kannst du die Download-Datei in den RAM laden und musst keine temporäre Datei auf Platte schreiben.
When we say computer, we mean the electronic computer.
__deets__
User
Beiträge: 14493
Registriert: Mittwoch 14. Oktober 2015, 14:29

Wie laedst du die Datei denn runter?
Horst73
User
Beiträge: 15
Registriert: Dienstag 5. Juni 2018, 14:08

Naja, ich hab einen Link...

https://.....

Da kann ich dann die Datei normal runterladen...

Ich erwarte keine Fertig Lösung von euch, aber könnt ihr mir vielleicht ein bischen mehr helfen, wie das mit dem Stream funktioniert? Oder wisst ihr zufällig eine Seite, wo ich mir das gut anlesen könnte?

Das wäre echt super nett, wenn das möglich wäre ;)
Zuletzt geändert von Horst73 am Dienstag 5. Juni 2018, 17:21, insgesamt 1-mal geändert.
Benutzeravatar
sls
User
Beiträge: 480
Registriert: Mittwoch 13. Mai 2015, 23:52
Wohnort: Country country = new Zealand();

Dann benutze eine Library, mit welcher du die Ressource herunterladen kannst? Z.B. Requests. Da wird auch nichts automatisch lokal gespeichert sondern steht dir erstmal nur via Objekt in Python (RAM-Ressource) zur Verfügung.
When we say computer, we mean the electronic computer.
__deets__
User
Beiträge: 14493
Registriert: Mittwoch 14. Oktober 2015, 14:29

Zum herunterladen von HTTP-Dateien gibt es diverse Bibliotheken, angefangen von der eingebauten urllib bis zu komfortableren externen Modulen requests. Und etwas fortgeschritten https://aiohttp.readthedocs.io/en/stable/ fuer das asyncio-Framework in Python. Das brauchst du, wenn du nicht nur nicht speichern willst, sondern der Datenstrom auch zu gross fuer deinen Arbeitsspeicher wird.
Horst73
User
Beiträge: 15
Registriert: Dienstag 5. Juni 2018, 14:08

Also die Datei um welche es geht umfasst etwa 100mb... Ich schau mir das AIOHTTP jetzt mal an...
DasIch
User
Beiträge: 2718
Registriert: Montag 19. Mai 2008, 04:21
Wohnort: Berlin

100MB ist nicht groß, dass kann man problemlos komplett im Arbeitsspeicher halten.
__deets__
User
Beiträge: 14493
Registriert: Mittwoch 14. Oktober 2015, 14:29

Wuerde ich auch nicht mit aiohttp machen. 100MB passen problemlos in deinen Speicher.
Sirius3
User
Beiträge: 17710
Registriert: Sonntag 21. Oktober 2012, 17:20

@__deets__: auch für alle anderen Methoden kann man den Download als Stream behandeln, ohne dass man ihn komplett in den Arbeitsspeicher laden muß. Dafür ist aiohttp nicht nötig. Das hat nur Vorteile, wenn man viele Dateien parallel verarbeiten will.
__deets__
User
Beiträge: 14493
Registriert: Mittwoch 14. Oktober 2015, 14:29

Ah. Um so besser. Ich kannte da bisher nur fix und fertige response Pakete. Aber das mag auch einfach der 99%-Fall gewesen sein.
Benutzeravatar
DeaD_EyE
User
Beiträge: 1012
Registriert: Sonntag 19. September 2010, 13:45
Wohnort: Hagen
Kontaktdaten:

Mit asyncio würde ich noch etwas warten. Erst, wenn du Python verstehst, solltest du dich auf asyncio stürzen.

Code: Alles auswählen

import requests

# vorher mit pip installieren
# pip3 install requests --user

req = requests.get('addresse')
# ab hier hat das zurückgelieferte Objekt bereits den Inhalt
inhalt = req.content # Bytes
text = req.text # Str
Um mit einem Stream zu arbeiten, muss man das etwas anders machen. Das geht mit requests sicherlich auch.
Jedenfalls lädt requests.get() den kompletten Inhalt in den RAM.

Bei sehr großen Dateien kann sich das bemerkbar machen. Erst muss der komplette Inhalt im RAM sein, bevor dann letztendlich die Auswertung kommt.
Wenn man mit einem Datenstrom arbeitet, bekommt man die Daten auf gesplittet in gleich große Teile.

Hier wird beschrieben, wie man mit einem Datenstrom arbeitet: http://docs.python-requests.org/en/mast ... t-workflow

Code: Alles auswählen

with requests.get('http://httpbin.org/get', stream=True) as r:
    for line in r.iter_lines():
        # code zur Auswertung
Innerhalb der for Schleife kannst du dann mit line arbeiten.
sourceserver.info - sourceserver.info/wiki/ - ausgestorbener Support für HL2-Server
Horst73
User
Beiträge: 15
Registriert: Dienstag 5. Juni 2018, 14:08

Vielen vielen Dank an DeaD_EyE! Habs mit deiner Hilfe jetzt hin bekommen. Funktioniert einwandfrei das Programm. Genau wie gewünscht.

Jetzt sind nur noch eine Kleinigkeit. Während des downloads blinkt der curser einfach nur und man sieht keinen Fortschritt. Kann man den auf einfache Art und Wiese darstellen?
__deets__
User
Beiträge: 14493
Registriert: Mittwoch 14. Oktober 2015, 14:29

print statements in der inneren Schleife?
Horst73
User
Beiträge: 15
Registriert: Dienstag 5. Juni 2018, 14:08

ne,

Code: Alles auswählen

print statements
geht nicht
Benutzeravatar
__blackjack__
User
Beiträge: 13003
Registriert: Samstag 2. Juni 2018, 10:21
Wohnort: 127.0.0.1
Kontaktdaten:

Warum nicht?
“Most people find the concept of programming obvious, but the doing impossible.” — Alan J. Perlis
Horst73
User
Beiträge: 15
Registriert: Dienstag 5. Juni 2018, 14:08

SyntaxError

Missing parentheses in call to print Did you mean print(statements)? Antowrt: Nein, natürlich nicht... Will ja nicht eine 0 dort stehen haben...
Sirius3
User
Beiträge: 17710
Registriert: Sonntag 21. Oktober 2012, 17:20

Du sollst natürlich das Ausgeben, was Du für sinnvoll hältst. Was das ist, kannst nur Du wissen.
Horst73
User
Beiträge: 15
Registriert: Dienstag 5. Juni 2018, 14:08

Ah, ok.

Ja jetzt weiß ich wie du das meinst. Also die Datei wird zeilenweise eingelesen und abgearbeitet. Gibt es denn einen Befehl, mit dem ich vorab die Anzahl der Zeilen in der datei abfragen kann? Dann könnte ich natürlich problemlos den Fortschritt berechnen... ;)

Ich hätte noch eine Frage: Gibt es eine Möglichkeit, die url in einer varriablen zu speichern? Mit sicherheit, denke ich. Kann mir einer die Syntax dafür sagen? Also in etwa so nur als korrekten Code...

Code: Alles auswählen

url="http://mein-server.de/datei.dat
with requests.get('url', stream=True) as r:
Ich bin euch bisher unendlich dankbar, wie ihr mir bisher geholfen habt ;)

Lg Horst
Sirius3
User
Beiträge: 17710
Registriert: Sonntag 21. Oktober 2012, 17:20

nein, die Anzahl der Zeilen kannst Du nur herausfinden, wenn Du die ganze Datei gelesen hast. Was geht, ist die Größe der Datei in Bytes aus dem Header Content-Length zu lesen, falls der Server sie mitschickt.

Variablen kann man so benutzen, wie man sie immer benutzt, nicht als String.
Antworten