来自NSData的objective-c sscanf

来自NSData的objective-c sscanf,objective-c,bit-shift,scanf,Objective C,Bit Shift,Scanf,我有一个BTLE设备,它正在向我发送字节,其中一些字节我需要合成成32位有符号整数,移位,然后解释。我使用的是xcode 6.1 我遇到的问题是使用sscanf将字节转换为int32\t,sscanf有时有效,有时无效。我不是obj-c专家,也不确定这是否是正确的方法,因为我使用的是strtol,同样也不起作用 整个功能如下: - (double) parseMV2: (NSData*) data { NSData* slicedData = [data subdataWithRange:N

我有一个BTLE设备,它正在向我发送字节,其中一些字节我需要合成成32位有符号整数,移位,然后解释。我使用的是xcode 6.1

我遇到的问题是使用sscanf将字节转换为int32\t,sscanf有时有效,有时无效。我不是obj-c专家,也不确定这是否是正确的方法,因为我使用的是strtol,同样也不起作用

整个功能如下:

- (double) parseMV2: (NSData*) data {
  NSData* slicedData = [data subdataWithRange:NSMakeRange(2, 4)];
  const char *bytes = [slicedData bytes];
  int32_t value;
  double mV = 0;

  int sscanf_result = sscanf(bytes, "%4x", &value);

  if (1 == sscanf_result) {
    value <<= 3; // discard the 3 most significant bits as they are not part of the value this also brings the sign bit to the most significant bit position.
    value >>= 8; // discard the 5 least significant bits as they are below the noise levels.
    mV = ((double)value)*2048.0/16777216.0; // Convert to mV
  } else {
    NSLog(@"Using 
sscanf
is for reading from a C-string but you don't have a C-string. You have a sequence of bytes.

Try it this way:

NSData* slicedData = [data subdataWithRange:NSMakeRange(2, 4)];
const uint8_t *bytes = [slicedData bytes];
int32_t value;
memcpy(&value, bytes, 4);
-双解析MV2:NSData*数据{ NSData*slicedData=[data subdataWithRange:NSMakeRange2,4]; 常量字符*字节=[slicedData字节]; int32_t值; 双mV=0; int sscanf_result=sscanfbytes,%4x,&value; 如果1==sscanf\U结果{ value=8;//丢弃5个最低有效位,因为它们低于噪声级。 mV=doublevalue*2048.0/16777216.0;//转换为mV }否则{ NSLog@使用sscanf是为了从C字符串中读取数据,但您没有C字符串。您有一个字节序列

试着这样做:

int32_t value;
[data getBytes:&value range:NSMakeRange(2, 4)];
正如Ken指出的,更简单的方法是:

value = CFSwapInt32BigToHost(value); // or CFSwapInt32LittleToHost
根据数据的创建方式,您可能还需要考虑字节顺序。您可能需要添加:

使用sscanf是为了读取C字符串,但您没有C字符串。您有一个字节序列

试着这样做:

int32_t value;
[data getBytes:&value range:NSMakeRange(2, 4)];
正如Ken指出的,更简单的方法是:

value = CFSwapInt32BigToHost(value); // or CFSwapInt32LittleToHost
根据数据的创建方式,您可能还需要考虑字节顺序。您可能需要添加:


看起来您并没有返回文本。在这种情况下,您不需要scanf吗?另外,切换到符号位是未定义的行为。首先NSLog接收到的数据。没有理由使用scan,只需使用指针进入数据、强制转换和访问即可。@paramagneticscroissant您的意思就是这样做这是:int32_t value=int32_t bytes;我原以为字节是十六进制编码的,但现在我不确定,我认为发送方只是将一个int切分为字节,然后将它们发送过来,所以您可能是对的。@eagsoo不,这将把指针转换为整数,而您希望整数驻留在该地址。@paramagneticCroissant类似于这?int32_t value=int32_t&bytes;看起来您并没有返回文本。在这种情况下,您不需要scanf就可以获得原始数据吗?此外,转换到符号位是未定义的行为。首先NSLog接收到的数据。没有理由使用scan,只需使用指向数据的指针、强制转换和访问。@TheParamagneticCroissant您的意思是这样做:int32_t value=int32_t bytes;我原以为字节是十六进制编码的,但现在我不确定,我认为发送方只是将一个int分割成字节并发送给您,所以您可能是对的。@eagsoo不,这会将指针转换为整数,而您希望整数驻留在t地址。@TheParamagneticCroissant像这样?int32\u t value=int32\u t&bytes;这大致是正确的方法,但为什么不使用-[NSData getBytes:range:]而不是制作一个切片,然后使用memcpy?[data getBytes:&value range:NSMakerRange2,4]@Kenthomass很好。我忽略了那个更直接的方法。我更新了答案,加入了那个解决方案。谢谢。这大致是正确的方法,但为什么不使用-[NSData getBytes:range:]而不是制作一个切片,然后使用memcpy?[data getBytes:&value range:NSMakerRange2,4]@Kenthomass很好。我忽略了那个更直接的方法。我更新了我的答案以包含那个解决方案。谢谢。