Bitweise Operatoren



  • Hallo,

    ich muss zur Zeit systemnah programmieren und würde gerne eure Meinung zu meinem Problem hören.

    Ich habe zwei Werte 6 und 4. Beide müssen nun in ein unsigned short.

    unsigned short ui1 = 6;
    unsigned short ui2 = 4; 
    
    unsigned short uiResult = (ui1 << 4);
    uiResult |= ui2;
    

    Danach ist der Wert 100. Beim Herauslesen benutzte ich folgende Möglichkeit

    unsigned short uiResult = 100;
    
    unsigned short ui1 = (uiResult >> 4)
    unsigned short ui2 = (uiResult & 0x000F)
    

    Gibt es Alternativen?

    Gruß
    Markus



  • Unions?

    union Word
    {
        unsigned char bytes[2];
        unsigned short value;
    };
    

    Funktioniert natürlich nur wenn 2 * sizeof(char) == sizeof(short).

    Gruß
    Don06



  • Was bezwechst du damit, die beiden halb-bytes in den short "reinzustopfen" und danach wieder rauszufummeln? Koennte man die Werte nicht genauso getrennt behandeln? Des weiteren kann uiresult zumindest in deinem Beispiel auch ein unsigned char sein. Wenn du mehrere solche Aktionen machen musst, bietet es sich evtl an, das hin-und hershiften in einer Klasse zu kapseln.
    (@Don: da er hier mit 4Bit-Werten hantiert und auch nur um 4 bits shiftet ist der Ansatz mit den bytes leider nicht unbedingt anwendbar)



  • pumuckl schrieb:

    Was bezwechst du damit, die beiden halb-bytes in den short "reinzustopfen" und danach wieder rauszufummeln?

    Synchronistation! 😃

    In diesem Fall sende ich an die Gegenstelle zwei Bytes. Einmal ein Zahl (Subframe) bis 10 (4 Bit) und eine Zahl (System Frame Number) bis 4095 (12 Bit) - also 16 Bits. Es gibt Schnittstellen, das zählt jedes Bit, z. Bsp. Mobilfunk (was ich vorher aber auch nicht wußte). 😉



  • Lies mal was über bitfields in deinem Buch.



  • dann würde ich etwa folgendes als Ansatz nehmen:

    struct Frames {
      unsigned char bytes[2]; //2 bytes reichen auch bei systemen mit sizeof(short) != 2
      void SetSubframe(unsigned short sf)
      {
        assert(sf < 11);
        bytes[1] |= sf;
      }
      unsigned short GetSubframe()
      {
        return bytes[2] & 0x0F;
      }
    
      void SetSysframe(unsigned short sf)
      {
        assert(sf < 4096);
        bytes[0] = sf >> 4; //die ersten 8 bit
        bytes[1] |= (sf % 0x000F) << 4; //die letzten 4 bit, geshiftet
      }
      unsigned short GetSysframe()
      {
        unsigned short sf = bytes[0];
        return (sf << 4) | (bytes[1] >> 4);
      }
    };
    

    Die Gurus mögen mir verzeihen, wenn ich unsinn verzapfe. Bei den Zuweisungen von short an char sollten nur die letzten 8 bit belegt sein. Die struct müsstest du auch über eine C-API verschicken können, da das Layout in C das selbe ist (dort ohne die methoden definiert), wenn man keine virtuellen Methoden, keine Basisklasse und nur POD-member hat.



  • eine kleine schönheitskorrektur für little endian systeme 🙂

    void SetSubframe(unsigned short sf)
      {
         bytes[0] |= sf;
      }
    
      void SetSysframe(unsigned short sf)
      {
         bytes[1] = sf >> 4; //die ersten 8 bit
         bytes[0] |= (sf & 0x000F) << 4; //die letzten 4 bit, geshiftet
      }
    

Anmelden zum Antworten