Synchrone Abfrage verschiedener Sensoren

  • Hallo zusammen,

    Nachdem meine Ersteinrichtung mit dem Raspberry Pi 4b 4GB gut geklappt hat, habe ich mich gleich ins Python3-getümmel und an das Thema Sensorik herangenwagt.

    Es klappt auch schon einzeln alles super, jedoch hänge ich an einem wichtigen punkt, nämlich dem Zusammenfassen der einzelnen Abfragen in einem einzelnen Programm.


    Zum Aufbau:

    Über die seriellen Pins des GPIO (TXD, RXD) wird ein TFMini Plus Lidarsensor angesteuert. Dieser arbeitet mit rund 100Hz


    Weiterhin sind noch zwei HX711 Wägezellenverstärker angeschlossen über normale Pins am GPIO


    Programmziel: Ich möchte gerne direkt hintereinander die Werte der Sensoren synchron abfragen und den die gemessenen Werte mit einem identischen Zeitstempel versehen. Abschließend sollen die Werte in eine TXT geschrieben werden.


    Aktueller stand: Die Wägezellen als auch den Lidar kann ich in einzelnen Programmen abfragen, und auch die Sache mit dem Zeitstempel und das Schreiben in eine Datei klappt schon wunderbar.


    Problemstellung: Der Lidar arbeitet mit rund 100HZ, die Wägezellen aktuell mit 12Hz (für 80Hz muss ich noch was umlöten). Lasse ich das nachfolgende Programm laufen passiert folgendes:

    Es kommt keine Fehlermeldung. Das Programm läuft dann mit der Frequenz der Wägezellen. Der Lidar bildet seine Werte auch ab, jedoch stark Zeitverzögert. Es scheint so als würden alle Werte des Lidarsensors weiterhin mit 100hz erfasst, in einen Speicher geschrieben. Diese Werte allerdings nur mit 12Hz abgefragt und dann in die Datei geschrieben werden.


    Vielleicht kennt jemand ja eine mögliche Lösung für diese Herausforderung :) Ich würde mich sehr über konstruktive Hilfe und Kritik freuen. Ich bin noch nicht so lange beim programmieren dabei ;)

    Hier noch der Programmcode:


  • Hallo,


    die Bytes die du am Anfang in deinem Code setzt, ist das notwendig? Ich kennen den Sensor nicht, habe aber dazu auf Github eine Anleitung mit Code für Python3 gefunden.

    Eventuell kannst du mal die verwendete Bibliothek verlinken.


    Das Folgende wird dein Problem nicht lösen, aber ich halte es für sinnvoll das von Anfang an zu beachten.

    Wenn du 'GPIO' nicht nutzt, dann musst du es nicht importieren und das Unterdrücken der Warnungen (das sollte man eh nicht machen) kann auch weg.

    Was verbiergt sich zwischen 'HX711' und 'HX711_2' ? So wie ich dich verstanden habe sind es zwei gleiche Wägezellen? Dann reicht es, die Bibliothek einmal zu importieren.

    Die Einrückungen in deinem Code stimmen nicht, darauf musst du achten, das ist sehr wichtig bei Python. Sonst wird dein Code falsch übersetzt. Namen in Python sollten aussagekräftig sein, so das man den Code einfach lesen kann und nicht nebenher noch Abkürzungen lernen muss. Du könntest dir gleich angewöhnen dein Programm in Funktionen zu unterteilen. Dabei steht das Hauptprogramm immer in der 'main'-Funktion. Von dort aus werden weitere Funktionen aufgerufen.

    Kommentare verwendet man um zu erklären warum eine Code-Zeile / Block etwas macht. Offensichtliches wird nicht kommentiert. Dazu gehört alles was man aus dem Code oder der Dokumentation lesen kann. Allerdings habe ich auch schon für mich selbst viel offensichtliches kommentiert, weil man da den Überblick besser behält (Bin kein Programmierer).

    Anstatt ’zaehler = zaehler + 1' kannst du einfacher 'zaehler += 1' schreiben.

    'if' - Abfragen benötigen keine Klammern und Strings erzeugt man nicht mehr mit '+' sondern mit f-Strings oder der Format-Methode.

    Aus

    Code
    str(zaehler)+"   "+str(round(testtime,2)) +"   "+ str(Dist_Total) + '\n'

    wird

    Code
    f"{zaehler} {round(testtime, 2}  {Dist_Total} \n"

    Dein Code etwas strukturiert könnte dann wie folgt aussehen. Ich habe keine Möglichkeit Ihn zu testen, vermutlich wird er so nicht funktionieren, möchte dir nur zeigen was ich mit Funktionen gemeint habe:

    Grüße

    Dennis

    🎵🎸Die Nordsee schlägt dir ins Gesicht, trotzdem hast du verloren, du bist nicht weit gekommen, du läufst weiter nach vorn 🎵🎸

  • Vielen Dank schon einmal, das hilft mir enorm mein Grundverständnis zu verbessern und mir einen besseren Stil anzueignen :thumbup:

    Ich werde mein Programm dahingehend angleichen so, dass es dann auch funktioniert und nochmal hier einstellen

    Vielleicht findet sich ja noch jemand der eine Idee zu der funktionellen Problematik hat :)


    Vielen Dank schon einmal an Dennis89 und das tolle Forum :!:

  • Das Grundproblem ist simpel: der LIDAR produziert seine Daten kontinuierlich. Wenn du den Code also so schreibst, das er die beiden Sensoren abwechselnd liest, buffert der also im Hintergrund. Beziehungsweise der Kernel tut das für dich.


    Um das zu lösen, musst du die Daten, die an der seriellen Schnittstelle Anliegen, leer lesen, bevor du weitermachst mit einer Wägezellen-Operation.


    Du kannst von der seriellen Schnittstelle erfragen, wieviele Daten da gerade Anliegen. Geteilt durch 9 ergibt das die Anzahl deiner Leseoperationen. Entsprechend oft liest du, verarbeitest die Daten. Dann liest du wieder die Wägezelle.

  • Ah okay, du hast die Fragestellung echt gut aufgegriffen, also existiert so ein Pufferspeicher also. Habe gerade einmal versucht nach so einer Buffer-lösch Funktion der Serial Bibliothek zu suchen. Dabei bin ich auf folgende Funktion gestoßen: reset_output_buffer()

    Hat jemand schonmal damit gearbeitet?

  • Wo habe ich denn geschrieben, dass etwas gelöscht werden soll? Und du liest doch Dinge EIN, was soll den OUTPUT buffer löschen bringen, selbst wenn löschen der richtige Weg wäre. Was es nicht ist.


    Denn wenn du einfach Stumpf Daten löschst, dann kann es sein, dass der LIDAR gerade ein halbes Datagramm geschrieben hat, du das weglöschst, und deine Daten danach verschoben eingelesen werden. Dich da wieder drauf zu synchronisieren ist sowohl aufwändig, als auch unnötig.

  • Oh, Fehler meinerseits entschuldige. Natürlich INPUT. Also es scheint damit zu gehen.


    Aber natürlich wirst du recht haben, das dein Weg den Datenverlust eben ausschließt. Dann forsche ich mal weiter nach einer Abfragemöglichkeit der Anzahl der Werte.