Konvertierung von Datentypen Zeichen in Zahlen

  • VB.NET

Es gibt 6 Antworten in diesem Thema. Der letzte Beitrag () ist von Dickschieder.

    Konvertierung von Datentypen Zeichen in Zahlen

    Hallo
    Ich bekomme über TCP Daten aus einer SPS geschickt. Diese sind allerdings im Datenformat der SPS.
    Zum Empfangen der Daten habe ich mich an das Ausführliches TCP und UDP Tutorial Tutorial gehalten.
    Herein kommen nun natürlich die Daten als String. Da ich mit den kryptischen Zeichen nichts anfangen kann, wollte ich sie wandeln. Allerdings weiß ich hier nicht genau wie, bzw mir fehlt der entsprechende Ansatz.
    Als Beispiel Float(32bit) aus der SPS 123.456 kommt bei mir dann an: B��y was
    Binär dem hier entspricht: 010000101111111111111101111111111111110101111001 bzw in Hex 42 F6 E9 79

    Wie bekomme ich das nun so gewandelt, dass ich am Ende Lesbar die 123,456 habe?

    Dickschieder schrieb:

    Herein kommen nun natürlich die Daten als String.
    Das ist ühaupt nicht natürlich.

    Ich kenne das Tut nur recht oberflächlich, aber bei TCP liegen die Daten zunächstmal als NetworkStream vor.
    Und die Kommunikation läuft so ab, dass man Daten in den Stream schreibt, und dann die Antwort wiederum ausliest.
    Ob die Daten nun Strings bedeuten (und in welchem Encoding sie verfasst sind), oder Fließkommazahlen oder sonstwas ist Sache des Kommunikations-Protokolls der Kommunikations-Partner - gibts da eine Doku der SPS?
    Der Kommunikationspartner bin ich. Die Idee ist, Zustände, Bitmuster, Variablen von der SPS so zu verschicken, dass man sie mit einem gewöhnlichen PC auswerten kann.
    Der erste Weg war, die Variablen in der SPS zu wandeln und jeweils Byteweise an den PC zu übertragen. Blöderweise ist eine SPS dafür nicht gedacht und es dauert recht lange die Daten in Ascii umzuwandeln. Gerade weil die Daten auch in unterschiedlichen Formaten vorliegen.
    Integer, Word, Bit, byte, DateTime, Float, ect.
    Ich müsste also für jede Auswertung Wandlung in der SPS überarbeiten.
    Da bin ich auf der Windowsebene flexibler. z.B. über Config Dateien.

    Auf der SPS Seite schreibe ich die Daten genauso in den Stream wie sie sind, also nicht gewandelt. Das Format ist in der Deklaration ähnlich einer Tabelle vorgegeben und werden im Stream alle aneinander gereiht.
    Ich möchte die Daten dann auf der PC Seite wieder interpretieren:
    ​Byte​Word​Integer​Integer​Float
    ​Byte1Byte2Byte3Byte4Byte5Byte6Byte7Byte8Byte9...
    also wie's aussieht kannst du einfach mit einem BinaryReader den Single aus dem Networkstream lesen.

    Halt wenn du sicher bist, dass auch ein Single an aktueller Position steht. Aber wo du ja der Kommunikationspartner bist, wirst du das sicher wissen ;) ...

    Oh - du hast Pech!
    Die Byte-Folge 42 F6 E9 79 muss umgedreht werden, um als .Net-Single 123.456 zu ergeben.

    Scheinbar ist die Sps BigEndian, weil .Net ist LittleEndian.

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „ErfinderDesRades“ ()

    Das heißt, ich muss die Reihenfolge der Bytes drehen?
    Ich hab verschiedene Formate im Stream. Ein Beispiel vom Aufbau in der SPS ist im Anhang. Das kann sich natürlich jederzeit ändern.
    Also den Stream komplett im BinaryReader einlesen, und dann?
    Ich muss das ja dann Byteweise ablegen, oder? Sonst hab ich ja keine Möglichkeit die Bytes zu drehen. Dann setzte ich mir aus den Bytes meine Längen zusammen die zu einem Format gehören und wandel sie dann in meine entsprechenden Formate um.
    Bilder
    • DatenBausteinStruktur.jpg

      65,15 kB, 1.011×256, 91 mal angesehen
    wie gesagt: es wird nervig. Normal hättest du mit dem BR immer einen Datenwert lesen können (ReadInt, ReadSingle,...)
    (den ganzen Stream zu lesen ist quatsch, ein Networkstream ist unendlich)

    Aber da die SPS BigEndian ist, musst du byteweise auslesen, und zwar immer so viele Bytes, wie der zu lesende Wert breit ist. Dann musst du die Bytes umdrehen, mit Array.Reverse, und dann kannstese in .Net-Werte konvertieren, etwa mitte BitConverter-Klasse.

    Vlt guckste als erstes, ob du die SPS iwie umstellen kannst auf LittleEndian.

    Oder du überprüfst nochmal deine Daten, vlt. hast du die ja falsch interpretiert. Weil eiglich müsste bei Endian-Inkompatiblität ja auch das Senden von SteuerSignalen voll daneben gehen.

    Hier - dieses ist mein Testcode:

    VB.NET-Quellcode

    1. Dim bytes As Byte() = {&H42, &HF6, &HE9, &H79}
    2. Dim sngl = BitConverter.ToSingle(bytes, 0)
    3. Array.Reverse(bytes)
    4. sngl = BitConverter.ToSingle(bytes, 0)
    Wenn du das im Einzelschritt durchgehst, stellst du fest, dass erst nachem Byte-Drehen der erwartete Single 123,456 bei rauskommt

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „ErfinderDesRades“ ()

    OK. Vielen Dank. Dann hab ich zumindest einen Ansatz.

    EDIT: Also es funktioniert mit dem Binary Reader. Und ich geb dir völlig Recht. Es ist sehr nervig. Auch meine Idee mit dem Variablen zusammenstellen der Formate über Config ist doch erheblich aufwendiger als ich es eingeschätzt hatte. Aber zumindest die Konvertierung funktioniert nun :)

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „Dickschieder“ ()