Char in Integer mit Vorzeichen



  • Hallo,

    ich versuche gerade aus einem Array mit char-Werten Integerwerte zu erzeugen.
    Bei positiven Werten klappt das auch, Jedoch bei negativen Werten scheint das Vorzeichen nicht beachtet zu werden.

    unsigned char testData[10];
    testData[0] = 246; 
    testData[1] = 194;
    int testD = (testData[0] << 8) + testData[1];
    printf("testData : %d\n",testD);
    

    Als Ergebnis bekomme ich "63170", jedoch sollte eigentlich ein negativer Wert rauskommen.

    Integer ist doch eigentlich mit Vorzeichen?



  • Dein int ist 32-bittig, nicht 16.



  • Wieso was Negatives?

    246 = 11110110 // Die Nullen vorne dran lass ich mal weg.

    Dann << 8

    Ergibt: 1111011000000000 = 62976 // Die Nullen vorne dran lass ich mal weg.

    Dann 62976 + 194 = 63170

    Dein int hat halt auf jeden Fall min. 32 bit.



  • Ah, vielen Dank. 🙂


  • Mod

    246 * 256 + 194 ist nun einmal genau 63170 und nichts negatives. Das ist genau, was du hier ausgerechnet hast. Du willst anscheinend irgendwas mit der internen Zahlendarstellung des Computers machen. Dann musst du das auch tun und darfst nicht selber rechnen. Also ist irgendetwas mit reinterpret_cast angesagt. Wie volkard schon sagte, musst du dann aber besser aufpassen, ob deine Vorstellungen vom internen Format auch zur Realität passen.



  • Mein Fehler war, das die Daten von einer 16 Bit Maschine kommen und da Integer nur 16 Bit lang sind.



  • Du musst dann halt das Vorzeichenbit einzeln behandeln und an die richtige Stelle im Zielwert kopieren.



  • Die Lösung war einfach, nachdem ich meinen Fehler verstanden hab:

    Hab statt dem Typ Integer einfach den Typ Short genommen.
    Jetzt passt es.

    Danke für die Hilfe


  • Mod

    magic-andy schrieb:

    Die Lösung war einfach, nachdem ich meinen Fehler verstanden hab:

    Hab statt dem Typ Integer einfach den Typ Short genommen.

    Dann hast du deinen Fehler nicht verstanden. Diese Lösung funktioniert zwar, aber aus ganz anderen Gründen, als du denkst. Außerdem ist es prinzipiell undefiniertes Verhalten.



  • Mit C++ hab ich mich noch nicht soviel beschäftigt.
    In meinem Buch heisst es INT "mindestens" 32 Bit und Short "mindestens" 16 Bit.
    In Wikibooks steht es auch nur so 😕
    Meinst du das mit undefiniert?
    Wär dann der Typ int16_t besser?

    Aber ich hab dann nichts anderes gefunden, wo das mehr gewesen wären.
    Und wenn ich die Werte alle als Byte-Array (verschiedene Datentypen gemischt) habe, muss ich die die Bytes doch wieder in die richtige Reihenfolge und das richtige Format bringen.
    Die 16 Bit-Integer landen somit in einem Short
    Was hab ich dann nicht verstanden? Ich muss die Bits wieder an die richtigen Stellen schieben und das Vorzeichenbit muss wieder an der höchstwertigen Stelle sein, damit es richtig interpretiert wird. 😕


  • Mod

    magic-andy schrieb:

    Mit C++ hab ich mich noch nicht soviel beschäftigt.
    In meinem Buch heisst es INT "mindestens" 32 Bit und Short "mindestens" 16 Bit.
    In Wikibooks steht es auch nur so 😕
    Meinst du das mit undefiniert?

    Wo du es erwähnst: Auch das kann ein Problem werden. Aber ich meinte eher, dass du dich derzeit auf einen vorzeichenbehafteten Integerüberlauf verlässt. Das ist aber undefiniertes Verhalten.

    Was hab ich dann nicht verstanden? Ich muss die Bits wieder an die richtigen Stellen schieben und das Vorzeichenbit muss wieder an der höchstwertigen Stelle sein, damit es richtig interpretiert wird. 😕

    Du wirfst hier alles durcheinander. Entweder schiebst du die Bytes an die richtige Stelle, unter der Annahme, dass das interne Format kompatibel ist (wahrscheinlich ist es das) oder du rechnest den korrekten Wert selber aus. Derzeit rechnest du den falschen Wert selber aus und hast Glück, dass aufgrund des internen Formats des dabei entstehenden Überlaufs am Ende trotzdem das richtige raus kommt.



  • Ach jetzt versteh ich was du meinst.

    Dann werd ich den Code nochmal überarbeiten.

    Vielen Dank


Anmelden zum Antworten