2012-03-16 16 views
1

したがって、このセンサーは、2つの(高および低)符号付きバイトを返すことによって-500〜500の間の符号付き値を返します。これらを使って実際の価値が何であるか把握するにはどうすればよいですか?私は2の補数を行う必要があることを知っていますが、私はどのようにしてよく分かりません。これは私が今持っているものです -2つの16ビット符号付きバイトから符号付き整数を取得しますか?

real_velocity = temp.values[0]; 
    if(temp.values[1] != -1) 
     real_velocity += temp.values[1]; 

    //if high byte > 1, negative number - take 2's compliment 
    if(temp.values[1] > 1) { 
     real_velocity = ~real_velocity; 
     real_velocity += 1; 
    } 

しかし、正の値を返すだけです。たとえば、-200はバイト255(高)と56(低)を返します。これらは311が追加されています。しかし、上記のコードを実行すると、-311と表示されます。何か助けてくれてありがとう。

+1

言語を指定します(最初の検索)してください。 –

+0

私は検索しましたが、私は約1バイトのものしか見つけず、2つを結合しません。 – Sterling

+0

タイトルには16ビットのバイトが含まれていますが、テキストには8ビットのバイトが含まれています。どちらですか? –

答えて

4
-200 in hex is 0xFF38, 

あなたはあなたのセンサーが2署名バイトを返すことはなく、単に高されていない彼らに

0xFF = 255, 
0x38 = 56 

を認識かもしれない小数にこれらのバックを変換する2バイトには0xFFと0x38、 を取得しています符号付き16ビット数の下位バイト。

ので、あなたの結果は、16ビット符号付き変数であること

value = (highbyte << 8) + lowbyte 

値です。 8ビット・バイトを

0
real_velocity = temp.values[0]; 
real_velocity = real_velocity << 8; 
real_velocity |= temp.values[1]; 
// And, assuming 32-bit integers 
real_velocity <<= 16; 
real_velocity >>= 16; 
0

、最初だけunsignedに変換:

typedef unsigned char Byte; 
unsigned const u = (Byte(temp.values[1]) << 8) | Byte(temp.values[0]); 

そしてそれは16ビットの2の補数の上限範囲よりも大きい場合、2 を減算:

int const i = int(u >= (1u << 15)? u - (1u << 16) : u); 

ビットレベルでトリックをすることはできますが、そこには何の問題もないと思います。

CHAR_BIT = 8とすると、unsignedは16ビット以上であり、マシンと望ましい結果は2の補数であることが前提です。あなたが与えた例に基づいて


#include <iostream> 
using namespace std; 

int main() 
{ 
    typedef unsigned char Byte; 
    struct { char values[2]; } const temp = { 56, 255 }; 

    unsigned const u = (Byte(temp.values[1]) << 8) | Byte(temp.values[0]); 
    int const  i = int(u >= (1u << 15)? u - (1u << 16) : u); 

    cout << i << endl; 
} 
2

、価値がすでに2の補数であることが表示されます。上位バイトを8ビット左にシフトし、値をORする必要があります。

real_velocity = (short) (temp.values[0] | (temp.values[1] << 8)); 
0

ビットをシフトして値をマスクすることができます。

int main() 
{ 
    char data[2]; 
    data[0] = 0xFF; //high 
    data[1] = 56; //low 
    int value = 0; 

    if (data[0] & 0x80) //sign 
     value = 0xFFFF8000; 

    value |= ((data[0] & 0x7F) << 8) | data[1]; 

    std::cout<<std::hex<<value<<std::endl; 
    std::cout<<std::dec<<value<<std::endl; 
    std::cin.get(); 
} 

出力:

ffffff38

-200

+0

余分なマスキングが必要とは思わない。高い値を 'unsigned char'として' unsigned short'にビットシフトし、次に低い値を 'unsigned char'として' OR 'してから、結果を 'signed short'として再解釈すると、結果は符号付き-200です。 –

関連する問題