Seite 1 von 1

Stringfehler

Verfasst: Montag 20. März 2017, 20:26
von TribbleX
Hallo,

ich möchte eine *.csv Datei mit fingierten Messwerten erstellen, die auch von einem Pi kommen könnten.
Bei meinen Datumberechungen benutze ich timedelta. Das funktioniert so weit auch. Hinter dem Datumswert werden aber noch beliebige Zeichen dargestellt. Die wollte ich mit Slice löschen, siehe datum_Z.
Aber egal, wie ich den String bearbeite und in die Liste übergebe, bekomme ich die Fehlermeldung, dass die Datei messwerte09.csv nicht geöffnet werden kann. Vielleicht sieht ja jemand meinen Fehler und kann mir helfen:

Code: Alles auswählen

import random
import sys
import time
import datetime

random.seed()

lt = time.localtime()
start = 0
n = 24

try:
    d = open("messwerte09.csv" , "w")
    d.write("Nummer" + ";" + "Uhrzeit" + ";" + "Datum" + ";" + "Temperatur" + ";" + "Luftfeuchtigkeit" + "\n")
    while start < n:
        start = start + 1

        nummer = start
        uhrzeit = time.strftime("%H:%M:%S", lt)

        now = datetime.datetime.now()
        datum_x = now + datetime.timedelta(days = nummer)
        datum_y = str(datum_x)
        datum_z = datum_y[:-6]
        datum = int(datum_z)
        
        temperatur = random.randint(20, 27)
        luftfeuchtigkeit = random.randint(35, 50)

        liste = [[nummer , uhrzeit, datum, temperatur , luftfeuchtigkeit]]
        for element in liste:
            d.write(str(element[0]) + ";" + str(element[1]) + ";" + str(element[2]) + ";" + str(element[3])  + ";" + str(element[4]) + "\n")
    d.close()

except:
    print("Datei kann nicht geöffnet werden")
    sys.exit()

Re: Stringfehler

Verfasst: Montag 20. März 2017, 20:47
von pillmuncher
@TribbleX: Gratulation! Du hast soeben den Grund dafür entdeckt, warum man nie ein nacktes except verwenden sollte.

Re: Stringfehler

Verfasst: Montag 20. März 2017, 21:03
von TribbleX
Das Slice-Problem habe ich jetzt gelöst.
Aber ich kann den Wert noch nicht in die Liste übernehmen.
Da bekomme ich noch leider int oder str Fehler :(

Re: Stringfehler

Verfasst: Montag 20. März 2017, 21:20
von TribbleX
Ich habe es hinbekommen:

Code: Alles auswählen

import random
import sys
import time
import datetime

random.seed()

lt = time.localtime()
start = 0
n = 24

try:
    d = open("messwerte10.csv" , "w")
    d.write("Nummer" + ";" + "Uhrzeit" + ";" + "Datum" + ";" + "Temperatur" + ";" + "Luftfeuchtigkeit" + "\n")
    while start < n:
        start = start + 1

        nummer = start
        uhrzeit = time.strftime("%H:%M:%S", lt)

        now = datetime.datetime.now()
        datum_x = now + datetime.timedelta(days = nummer)
        datum_y = str(datum_x)
        datum = datum_y[:-16]

        temperatur = random.randint(20, 27)
        luftfeuchtigkeit = random.randint(35, 50)

        liste = [[nummer , uhrzeit, temperatur , luftfeuchtigkeit]]
        for element in liste:
            d.write(str(element[0]) + ";" + str(element[1]) + ";" + datum + ";" + str(element[2]) + ";" + str(element[3]) + "\n")
    d.close()

except:
   print("Datei kann nicht geöffnet werden")
   sys.exit()

Re: Stringfehler

Verfasst: Montag 20. März 2017, 21:40
von Üpsilon
Mag sein, aber ich würde dir raten, dein Programm folgendermaßen umzugestalten:

Code: Alles auswählen

try:
    d = open(...)
except OSError:
    print("Datei konnte nicht geöffnet werden")
else:
    ... # der ganze Rest, der im try-Block stand
Weil: Jetzt werden nur Fehler, die in der Zeile mit dem open entstehen, die von der Sorte OSError sind, abgefangen. Also nur die Fehler, die tatsächlich bedeuten, dass die Datei nicht geöffnet werden kann. Das hat den Vorteil, dass keine Programmierfehler mehr verschleiert werden, die im langen try-Block evtl vorkommen. Das ist schätzungsweise auch das, was pillmuncher meinte.

Re: Stringfehler

Verfasst: Montag 20. März 2017, 22:24
von pillmuncher
Bei so einem Programm würde ich gar keine Fehlerbehandlung einbauen, sondern auf Exception + Traceback vertrauen. Außerdem würde ich Pythons Sprachmittel & Standard-Bibliothek intensiver nutzen:

Code: Alles auswählen

#!/usr/bin/python
# coding: utf-8

import csv
import datetime
import random

FILE_NAME = 'messwerte10.csv'
CSV_DELIM = ';'
CSV_FIELDS = 'Nummer', 'Uhrzeit', 'Datum', 'Temperatur', 'Luftfeuchtigkeit'
DATE_FORMAT = '%Y-%m-%d'
TIME_FORMAT = '%H:%M:%S'
FROM_NUM = 1
TO_NUM = 25
LO_TEMPERATURE = 20
HI_TEMPERATURE = 27
LO_HUMIDITY = 35
HI_HUMIDITY = 50

def make_random_row(n):
    now = datetime.datetime.now()
    cur_time = now.time()
    cur_date = now.date() + datetime.timedelta(days=n)
    return dict(
        Nummer=n,
        Uhrzeit=cur_time.strftime(TIME_FORMAT),
        Datum=cur_date.strftime(DATE_FORMAT),
        Temperatur=random.randint(LO_TEMPERATURE, HI_TEMPERATURE),
        Luftfeuchtigkeit=random.randint(LO_HUMIDITY, HI_HUMIDITY),
    )

def main():
    with open(FILE_NAME, 'w') as csv_file:
        csv_writer = csv.DictWriter(csv_file, CSV_FIELDS, delimiter=CSV_DELIM)
        csv_writer.writeheader()
        for i in range(FROM_NUM, TO_NUM):
            csv_writer.writerow(make_random_row(i))

if __name__ == '__main__':
    main()
Ergebnis:

Code: Alles auswählen

Nummer;Uhrzeit;Datum;Temperatur;Luftfeuchtigkeit
1;22:20:11;2017-03-21;20;42
2;22:20:11;2017-03-22;26;47
3;22:20:11;2017-03-23;21;35
4;22:20:11;2017-03-24;23;36
5;22:20:11;2017-03-25;24;36
6;22:20:11;2017-03-26;25;50
7;22:20:11;2017-03-27;25;36
8;22:20:11;2017-03-28;27;43
9;22:20:11;2017-03-29;21;42
10;22:20:11;2017-03-30;25;47
11;22:20:11;2017-03-31;21;35
12;22:20:11;2017-04-01;23;38
13;22:20:11;2017-04-02;26;48
14;22:20:11;2017-04-03;27;39
15;22:20:11;2017-04-04;23;36
16;22:20:11;2017-04-05;24;40
17;22:20:11;2017-04-06;23;47
18;22:20:11;2017-04-07;27;39
19;22:20:11;2017-04-08;23;36
20;22:20:11;2017-04-09;25;45
21;22:20:11;2017-04-10;20;37
22;22:20:11;2017-04-11;20;49
23;22:20:11;2017-04-12;25;47
24;22:20:11;2017-04-13;24;48

Re: Stringfehler

Verfasst: Dienstag 21. März 2017, 09:01
von Sirius3
@TribbleX: random.seed ist unnötig und sorgt im besten Fall für weniger Zufall, als beabsichtigt. Dateien sollten mit dem with-Statement geöffnet werden, Listen werden nicht händisch per + zusammengestückelt sondern per ";".join. Wenn die Anzahl der Durchläufe bekannt ist, nimmt man statt while- eine for-Schleife. Ist es Absicht, dass manche Tage zufällig ausgelassen werden, wenn das Programm um Mitternacht ausgeführt wird? Wenn Du eine bestimmte Datumsformatierung haben willst, gibst Du sie explizit an und bearbeitest nicht das Standardformat mit String-Indexierung. Eine einelementige Liste zu erzeugen um danach per for-Schleife sie abzuarbeiten ist unnötig kompliziert. Da kannst Du die Liste gleich weg lassen.

Code: Alles auswählen

import random
import datetime

COLUMN_NAMES = ["Nummer", "Uhrzeit", "Datum", "Temperatur", "Luftfeuchtigkeit"]

now = datetime.datetime.now()
with open("messwerte10.csv" , "w") as output
    output.write("{}\n".format(";".join(COLUMN_NAMES))
    for nummer in range(24):
        datum = now + datetime.timedelta(days=nummer)
        temperatur = random.randint(20, 27)
        luftfeuchtigkeit = random.randint(35, 50)
        elements = [str(nummer),
            datum.strftime("%H:%M:%S"), datum.strftime("%Y-%m-%d"),
            str(temperatur), str(luftfeuchtigkeit),
        ]
        output.write("{}\n".format(";".join(elements))
Wenn Du etwas am Datenformat ändern kannst, packe Datum und Uhrzeit in eine Spalte, denn die gehören zusammen.

Re: Stringfehler

Verfasst: Dienstag 21. März 2017, 19:53
von TribbleX
DANKE für die Tipps und Tricks.
Im Moment ist das aber noch zu schwer und zu viel für mich.
Werde mich da langsam rein arbeiten.