Umwandeln der Daten in Byte oder Bit

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
inter
User
Beiträge: 13
Registriert: Dienstag 2. Februar 2016, 17:27

Hallo,

lese mit folgendem Code eine USB Schnittstelle aus.
[Codebox=python file=Unbenannt.py]

er = serial.Serial("/dev/ttyUSB0", 9600, timeout=1)
#ser.open()
print ("seropen")

Input = ""

Zeichen = ser.read(1000)
ser.close()
print (Zeichen)



#Zeichen.decode('utf-8')
#print (Zeichen)

Input = str(Zeichen)
[/Codebox]

Und schreibe die Daten dann in eine .txt Datei.

[Codebox=text file=Unbenannt.txt]b'\xaf\xc5MH5----eHZ-\xc500\xb2\xb8\xc5\x8d\n\x8d\n\xb1-0:0.0.0\xaa\xb255(\xb20\xb836\xb2\xb7\xb8\xa9\x8d\n\xb1-0:\xb1.\xb8.\xb1\xaa\xb255(0\xb10\xb760.\xb73\xb2\xb2\xa9\x8d\n\xb1-0:\xb2.\xb8.\xb1\xaa\xb255(0\xb239\xb4\xb2.\xb196\xb7\xa9\x8d\n\xb1-0:96.5.5\xaa\xb255(\xb8\xb2\xa9\x8d\n0-0:96.\xb1.\xb255\xaa\xb255(000\xb2\xb4\xb7\xb765\xb2\xa9\x8d\n!\x8d\n'
[/Codebox]

Um die Daten in der *.txt Datei beurteilen zu können, hätte ich diese gerne in Byte. Leider funktioniert es nicht mit Zeichen.decode('utf-X') in Byte umzuwandeln. Es erscheint folgende Fehlermeldung:
Traceback (most recent call last):
File "/home/pi/1602test.py", line 60, in <module>
Zeichen.decode('utf-8')
UnicodeDecodeError: 'utf-8' codec can't decode byte 0xaf in position 0: invalid start Byte

Um welchen Code handelt es sich? Wo ist der Fehler? Oder kann ich die Daten auch byteweise schon einlesen?

Viele Grüße
Inter
BlackJack

@inter: Was meinst Du wenn Du sagst Du willst die Daten in ”Byte”? Das ist ja bereits ein `bytes`-Objekt. Was Du da als zweites zeigst ist die Zeichenkettenrepräsentation von einem `bytes`-Objekt. Ich hoffe Du hast nicht das in die Datei geschrieben, sondern das `bytes`-Objekt selber, also ohne es mit `str()` in die gezeigte Repräsentation umgewandelt zu haben. Denn dann kannst Du die Datei mit einem geeigneten Programm öffnen. Einem Hexeditor oder einem Texteditor sofern der Binärdaten sinvoll darstellen kann, ähnlich wie ein Hexeditor.

Der Name `Zeichen` im Programm ist irreführend, weil es sich eben nicht um Zeichen(ketten) sondern um Bytes handelt.

Das umwandeln oder dekodieren in eine Zeichenkette macht auch keinen Sinn, denn es handelt sich nicht um Text sondern offenbar um ein Binärformat. Da muss es eine Spezifikation zu geben, wie man die Daten zu interpretieren hat, sonst wird das schwierig.
inter
User
Beiträge: 13
Registriert: Dienstag 2. Februar 2016, 17:27

Hallo,

wenn ich versuche die Bytes in die Datei direkt zu schreiben kommt eine Fehlermeldung bei folgendem Code:
[Codebox=python file=Unbenannt.py]

#Textdatei erzeugen
#fobj_out=open("ehz.csv","w")
# wenn Datei vorhanden
fobj_out=open("ehz.txt","a")

#Daten in Datei schreiben
fobj_out.write(Datum + " " + Uhrzeit + " " + Input +"\n")
#Datei schliessen
fobj_out.close()
[/Codebox]

Wie bekomme ich die Bytes direkt in diese Datei?
BlackJack

@inter: Es gibt einen Unterschied zwischen Bytes und Text und dementsprechend auch Dateien die für Bytes und solche die für Text geöffnet wurden. Du öffnest eine Textdatei und versuchst Bytes dort hinein zu schreiben. Wenn Du sie im Binärmodus öffnest, wirst Du Probleme bekommen den Text mit dem Datum zu schreiben, weil `write()` dann keinen Text sondern Bytes erwartet. Da müsstest Du den Text vor dem Schreiben selbst als Bytes kodieren. In eine Binärdatei, deren Format Du anscheinend nicht kennst, einfach so Text einzustreuen, ist aber sowieso keine gute Idee, denn wie willst Du das am Ende wieder auseinander halten?

Weder die Dateiendung CSV, noch die Endung TXT ist bei Binärdaten eine gute Wahl, denn bei beiden erwartet der Benutzer einen anderen Inhalt als das was Du da tatsächlich schreibst.
inter
User
Beiträge: 13
Registriert: Dienstag 2. Februar 2016, 17:27

Also ich hätte die Daten gerne Dezimal, Oktal oder Dezimal.
Da habe ich mich wohl falsch ausgedrückt.

Ist es möglich die serielle Schnittstelle so einzulesen?

Mein gewünschtes Format wäre z.B. 01 26 af

Im Terminal des Raspberry kann ich die Daten mit cat /dev/ttyUSB0 | od -tx1 in dieser Form empfangen.
BlackJack

@inter: So einlesen geht nicht, dann müsste die Gegenseite das ja schon so senden, aber natürlich kannst Du die Bytewerte in eine andere Darstellung als Text umwandeln. Iteriere mal über die einzelnen Werte in einem `bytes`-Objekt:

Code: Alles auswählen

In [2]: for x in b'\x00abc\r\n':
   ...:     print(x)
   ...: 
0
97
98
99
13
10
Mit `str()` kannst Du die Zahlen in Zeichenketten aus Dezimalziffern umwandeln, mit `hex()` in Hexadezimalziffern, und für Oktal gibt es auch eine Funktion, oder Du verwendest die `format()`-Funktion, dann kannst Du auch führende Nullen oder Leerzeichen erreichen, damit jede Zahl gleich lang dargestellt wird. Mit der `join()`-Methode auf Zeichenketten kannst Du die einzelnen Zeichenketten dann zu einer zusammensetzen. Um das schön kompakt ausdrücken zu können, schau Dir mal Generatorausdrücke an.

Falls Leerzeichen zwischen den Zahlen nicht wichtig sein sollten, kannst Du auch mal das `binascii`-Modul aus der Standardbibliothek anschauen.
inter
User
Beiträge: 13
Registriert: Dienstag 2. Februar 2016, 17:27

Das sieht super aus. Werde es später mal versuchen. Danke für deine Infos
Antworten