Arrays unter Python

Python auf Einplatinencomputer wie Raspberry Pi, Banana Pi / Python für Micro-Controller
Antworten
CmdKeen42
User
Beiträge: 7
Registriert: Sonntag 28. April 2019, 22:28

Hallo liebe Community,

ich bin Python Anfänger und entschuldige mich schon mal für die Frage aber ich hänge seit über einer Woche an einem Problem.
Ich habe an einen Raspi einen DHT11 angeschlossen und möchte die Messwerte über einen längeren Zeitraum zunächst erstmal in eine Datei schreiben.
Alles andere später.
Nun hat es sich leider herausgestellt, dass der DHT einige Ausreißer-werte liefert. Diese möchte ich gerne ausfiltern. Dazu soll der zweite Wert auf Plausibilität verglichen werden und im Zweifelsfall aus den Werten 1 und 3 interpoliert werden. Das Programm ist bei weitem noch nicht fertig. Ich weiß, dass weder der erste noch der dritte Werte geprüft werden. Darum geht es aber nicht.
Meine Frage ist jetzt, wie ich es hin bekomme, ein Array zu basteln, was diese Aufgabe erfüllen kann. Bei den unten aufgeführten Programm bekomme ich die folgende Fehlermeldung:


======================= RESTART: /home/pi/temp_hum.py =======================
Traceback (most recent call last):
File "/home/pi/temp_hum.py", line 37, in <module>
lf = float(lf)
TypeError: 'float' object does not support item assignment
>>>

----------------------------------------------------------------------------------------------------------------------------------------------------
Der Programmcode lautet folgendermaßen:

Code: Alles auswählen

#!/usr/bin/python

import Adafruit_DHT, time, sys
import numpy as np


try:
    d = open("TempWerte0001.csv", "w")
except:
    print("Dateizugriff nicht möglich!")
    sys.exit(0)

d.close

sensor = Adafruit_DHT.DHT11
pin = 4
zaehler = 1
hz = 1 # Hilfszähler für die Liste.
lf1 = [0, 0, 0]
temp1 = [0, 0, 0]


while True:
     
    #Localtime
    lt = time.localtime()

    # 3 Werte, im Abstand von 10 sec. holen, in einer Liste mit Zähler speichern
    # und anschließend vergleichen
    
    lf = np.array([])
    temp = np.array ([])
    
    
    for i in range(3):
        lf, temp = Adafruit_DHT.read_retry(sensor, pin)
        lf[i] = float(lf)
        temp[i] = float(temp)
        print ("i =", i, "x =",lf[i], "y = ", temp[i])
        # 10 Sekunden warten
        time.sleep(10)
    
    # Mittleren Wert Wert vergleichen und bei plausiblen Werten in lf3, temp3 überführen und in Datei schreiben
    if lf[2] > 100.0:
        lf3 = lf[1] + lf[3] / 2
        temp3 = temp1[1] + temp[3] / 2
        lf[2] = lf[3]
        temp[2] = lf[3]
    else:
        lf3 = lf[2]
        temp3 = temp[2]
               
    # Ausgeben
    Datum = str(lt[2]) + "." + str(lt[1]) + "." + str(lt[0])
    Uhrzeit = str(lt[3]) + ":" + str(lt[4]) + ":" + str(lt[5])
    
    a =  str(zaehler) + ";" + Datum + ";" + Uhrzeit + ";" + str(temp3) + ";" + str(lf3)
    print (" ================= Werte welche in die Datei geschrieben werden ===============")
    print(a)
    print ("===============================================================================")
    # Werte in Datei schreiben
    d = open("TempWerte0001.csv", "a")
    d.write(str(zaehler) + ";" + str(Datum) + ";" + str(Uhrzeit) + ";" + str(temp3) + ";" + str(lf3) + str("\n"))
    d.close

    zaehler += 1
  
     # 10 Sekunden warten
    time.sleep(10)
Ich hoffe auf, bitte nicht zu komplizierte, Hilfe (bin VB und Perl geschädigt ;) ) und bedanke mich schon mal für Eure Hilfe.

Mfg
Keen
Benutzeravatar
sparrow
User
Beiträge: 4193
Registriert: Freitag 17. April 2009, 10:28

Was denkst du denn, was lf an der Stelle ist? Und was soll

Code: Alles auswählen

lf[i]
deiner Meinung nach tun?
An lf wird ja eine Zeile darüber etwas gebunden. Offensichtlich etwas vom Type "float" - sagt zumindest die Fehlermeldung.
__deets__
User
Beiträge: 14540
Registriert: Mittwoch 14. Oktober 2015, 14:29

Bitte zeige in Zukunft die passende Fehlermeldung zum Code, und nicht etwas paraphrasiertes. Du hast eine solche Zeile wie im Stacktrace gezeigt gar nicht im Code.

Und nun zu deinem Vorgehen/Problem: du gehts *VIEL* zu kompliziert vor. Die Nutzung von schlecht benamten und globalen Variablen macht das Ganze dann noch unuebersichtlicher, und du verhedderst dich.

Schreib dir eine Funktion, die einen guten Messwert zurueckliefert. Diese Funktion sampelt abhaengig von einem Parameter n mal, und gibt einfach den Median der sortierten Ergebnisse zurueck.

Code: Alles auswählen

def acquire_measurement(repetitions=3, pause=.1):
       results = []
       for _ in range(repetitions):
              result.append(...) # hier Messwert ermitteln, inklusive Konvertierung zu float.
              time.sleep(pause)
       return sorted(result)[len(result)//2]
Zuletzt geändert von __deets__ am Montag 29. April 2019, 13:43, insgesamt 1-mal geändert.
Grund: fehlende pause eingefuegt
Benutzeravatar
__blackjack__
User
Beiträge: 13110
Registriert: Samstag 2. Juni 2018, 10:21
Wohnort: 127.0.0.1
Kontaktdaten:

Die ”gezeigte” Zeile gibt's schon im Code, nur wandelt das Forum den Indexzugriff mit einem `i` zu „ab hier kursiver Text“ um, wenn man den Stacktrace nicht auch in Code-Tags setzt.
„All religions are the same: religion is basically guilt, with different holidays.” — Cathy Ladman
__deets__
User
Beiträge: 14540
Registriert: Mittwoch 14. Oktober 2015, 14:29

Ahhhhh. Ok. Die restlichen Anmerkungen bleiben bestehen :)
CmdKeen42
User
Beiträge: 7
Registriert: Sonntag 28. April 2019, 22:28

Vielen Dank erstmal für die schnellen und zahlreichen Antworten.

Da ich aber , wie geschrieben, blutiger Anfäbger in Python bin, habe ich so einige Probleme mit Euren Antworten.

@sparrow
lf, soll die Werte in einer Schleife von 1-3 von lf speichern.

@__deets__
Ich habe genau die Fehlermeldung kopiert welche mir der Debugger auch zurückliefert. Echt.
Wenn Du mir den Rest Deines Posts mal ins deutsche übersetzt wäre ich echt dankbar. Nicht böse gemeint.

Ich will mal mein Problem etwas vereinfachen. Zur Veranschaulichung in an Python angelehnten "PSEUDOCODE".

Code: Alles auswählen

a= DIM(:3)
for i  in range (3):
    a[i] = i

for i in range(:3)
   print (a[i]), " ")
Die letzte Ausgabe sollte 1, 2, 3 erzeugen.
Das wünsch ich mir.

Nochmals Danke für Eure Hilfe und

MfG
Keen
__deets__
User
Beiträge: 14540
Registriert: Mittwoch 14. Oktober 2015, 14:29

Was an meinem Code ist dir nicht klar? Hast du damit mal rumgespielt?

In Python dimensioniert man keine Listen vor. Sondern hängt einfach Werte an eine leere Liste an. Wie von mir gezeigt.
CmdKeen42
User
Beiträge: 7
Registriert: Sonntag 28. April 2019, 22:28

__deets__ hat geschrieben: Montag 29. April 2019, 22:33 Was an meinem Code ist dir nicht klar? Hast du damit mal rumgespielt?

In Python dimensioniert man keine Listen vor. Sondern hängt einfach Werte an eine leere Liste an. Wie von mir gezeigt.
Ja, aber mit diesen kann ich nicht rechnen und da liegt mein Problem. Ich bekomme dann immer die Fehlermeldung, dass die Werte nicht "subscriptable" sind.
__deets__
User
Beiträge: 14540
Registriert: Mittwoch 14. Oktober 2015, 14:29

Das ist so unsinnig. Ob eine Liste vordimensioniert ist oder nicht ist nicht von Belang dafür, wie man sie weiter verarbeitet. Das hat also eine andere Ursache.

Es klingt eher danach, als ob du dich in deinen kryptisch kurzen Namen verheddert hast, und nur denkst du arbeitest mit einer Liste.
CmdKeen42
User
Beiträge: 7
Registriert: Sonntag 28. April 2019, 22:28

__deets__ hat geschrieben: Montag 29. April 2019, 22:51 Das ist so unsinnig. Ob eine Liste vordimensioniert ist oder nicht ist nicht von Belang dafür, wie man sie weiter verarbeitet. Das hat also eine andere Ursache.

Es klingt eher danach, als ob du dich in deinen kryptisch kurzen Namen verheddert hast, und nur denkst du arbeitest mit einer Liste.

Code: Alles auswählen

Ok, mag durchaus sein. Wie würde denn ein Programm Deiner Meinung aussehen welches flg. Forderungen erfüllt.
a[1] = 2
a[2] = 4
a[3] = 3
Ermittle, in einer Schleife, bei Beibehaltung der Variablenindizes, den Mittelwert im Wert x.

MfG
Kenn
__deets__
User
Beiträge: 14540
Registriert: Mittwoch 14. Oktober 2015, 14:29

Ich habe diese Programm oben gepostet. Es löst dein Problem. Schonmal probiert?
__deets__
User
Beiträge: 14540
Registriert: Mittwoch 14. Oktober 2015, 14:29

Hier zum Spielen mit simulierter Sensorabfrage und mit repariertem Namen:

Code: Alles auswählen

import random
import time
def read_sensor():
    return random.random()
        
def acquire_measurement(repetitions=3, pause=.1):
       results = []
       for _ in range(repetitions):
              results.append(read_sensor()) # hier Messwert ermitteln, inklusive Konvertierung zu float.
              time.sleep(pause)
       return sorted(results)[len(results)//2], results
       
for _ in range(10):
    print(acquire_measurement())
CmdKeen42
User
Beiträge: 7
Registriert: Sonntag 28. April 2019, 22:28

__deets__ hat geschrieben: Montag 29. April 2019, 23:10 Ich habe diese Programm oben gepostet. Es löst dein Problem. Schonmal probiert?
Nein, habe ich nicht weil ich es nicht verstehe. Du hast eine Funktion gepostet, allerdings weiß ich damit leider nichts anzufangen. Echt Sorry, aber ich habe geschrieben, dass ich blutiger Anfänger bin. Wenn ich wenigstens die MEINE Rüchgabe Variablen wiederfinden würde, könnte es sein, dass ich durchsehe.

Aber vielen Dank für Deine Bemühungen.

MfG
Keen
CmdKeen42
User
Beiträge: 7
Registriert: Sonntag 28. April 2019, 22:28

__deets__ hat geschrieben: Montag 29. April 2019, 23:17 Hier zum Spielen mit simulierter Sensorabfrage und mit repariertem Namen:

Code: Alles auswählen

import random
import time
def read_sensor():
    return random.random()
        
def acquire_measurement(repetitions=3, pause=.1):
       results = []
       for _ in range(repetitions):
              results.append(read_sensor()) # hier Messwert ermitteln, inklusive Konvertierung zu float.
              time.sleep(pause)
       return sorted(results)[len(results)//2], results
       
for _ in range(10):
    print(acquire_measurement())
Vielen Dank dafür. Ich werde das testen und berichten. Ein Bienchen hast Du Dir auf jeden Fall schon mal verdient. Danke für die schnellen Antworten!

MfG
Keen.
Benutzeravatar
sparrow
User
Beiträge: 4193
Registriert: Freitag 17. April 2009, 10:28

CmdKeen42 hat geschrieben: Montag 29. April 2019, 23:19Wenn ich wenigstens die MEINE Rüchgabe Variablen wiederfinden würde, könnte es sein, dass ich durchsehe.
Das ist ja das Problem. Du vertust dich mit den Namen DEINER Variablen. Deshalb sind sie nicht das, was du denkst, das sie sind. Benutze lange, sprechende Namen, die dir und jedem anderen sagen, was sie darstellen sollen. Dann fällt dir auch auf, wenn der Inhalt nicht stimmt.

Schau dir in deinem Code mal an, wann du etwas an den Namen "lf" bindest. Das passiert mehrmals - und hat nicht immer den selben Typ.

Ich sehe im Moment auch noch nicht, dass du hierfür numpy brauchst. Eine Liste aus Python sollte hier auch reichen.
CmdKeen42
User
Beiträge: 7
Registriert: Sonntag 28. April 2019, 22:28

Danke nochmal für Deine Bemühungen und Dein Geduld. Leider bin ich noch nicht dazu gekommen, das umzusetzen. Sobald ich Zeit habe werde ich es testen und berichten. <Joke> Wenn Du Pech hast poste ich das komplette Listing mit allen Kontrollvariablen. </Joke>
Antworten