【问题标题】:Converting HEX NSString To NSData将 HEX NSString 转换为 NSData
【发布时间】:2011-11-11 04:24:54
【问题描述】:

我正在尝试将十六进制 NSString 转换为 NSData(我正在使用以下附加代码)。以下是输出:

<00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000>

这看起来与我完全无关。关于哪里出错的任何想法/建议?

NSString *strData = @"72ff63cea198b3edba8f7e0c23acc345050187a0cde5a9872cbab091ab73e553";

NSLog(@"string Data length is %d",[strData length]);

NSMutableData *commandToSend= [[NSMutableData alloc] init];
unsigned char whole_byte;
char byte_chars[2];
int i;
for (i=0; i < [strData length]/2; i++) {

    byte_chars[0] = [strData characterAtIndex:i*2];
    byte_chars[1] = [strData characterAtIndex:i*2+1];
    whole_byte = strtol(byte_chars, NULL, [strData length]);
    [commandToSend appendBytes:&whole_byte length:1]; 
}
NSLog(@"%@", commandToSend);    

【问题讨论】:

  • 不应该将 16 传递给 strtol 吗?

标签: iphone objective-c ios nsstring nsdata


【解决方案1】:

我看到一些解决方案已经发布,只能转换长度均匀的字符串。

所以这是我的解决方案,如果字符串像这样的奇数长度,它也能够返回正确的数据“DBA”变成这样的数据“\x0D\xBA”

+ (NSData *)dataFromHexString:(NSString *) string {
    if([string length] % 2 == 1){
        string = [@"0"stringByAppendingString:string];
    }

    const char *chars = [string UTF8String];
    int i = 0, len = (int)[string length];

    NSMutableData *data = [NSMutableData dataWithCapacity:len / 2];
    char byteChars[3] = {'\0','\0','\0'};
    unsigned long wholeByte;

    while (i < len) {
        byteChars[0] = chars[i++];
        byteChars[1] = chars[i++];
        wholeByte = strtoul(byteChars, NULL, 16);
        [data appendBytes:&wholeByte length:1];
    }
    return data;

}

【讨论】:

    【解决方案2】:

    这可能更有用,Apple 共享了一个 NSData 类别。

    NSData+HexString.m

    代码是:

    @implementation NSData (HexString)
    
    // Not efficent
    +(id)dataWithHexString:(NSString *)hex
    {
        char buf[3];
        buf[2] = '\0';
        NSAssert(0 == [hex length] % 2, @"Hex strings should have an even number of digits (%@)", hex);
        unsigned char *bytes = malloc([hex length]/2);
        unsigned char *bp = bytes;
        for (CFIndex i = 0; i < [hex length]; i += 2) {
            buf[0] = [hex characterAtIndex:i];
            buf[1] = [hex characterAtIndex:i+1];
            char *b2 = NULL;
            *bp++ = strtol(buf, &b2, 16);
            NSAssert(b2 == buf + 2, @"String should be all hex digits: %@ (bad digit around %d)", hex, i);
        }
    
        return [NSData dataWithBytesNoCopy:bytes length:[hex length]/2 freeWhenDone:YES];
    }
    
    @end
    

    【讨论】:

    • 通过调用malloc() at ...动态分配的内存在...之后无法访问。 > return [NSData dataWithBytesNoCopy:bytes length:[hex length]/2 freeWhenDone:YES];
    【解决方案3】:

    这是另一种方法,它也处理前导 &lt;、尾随 &gt; 和嵌入空格,例如

    <9dc69faf a7434ba9 aef57f5c 365d571f 4c3753c4 ae13db42 57d184ca e00246c5>
    

    代码:

    + (NSData *)dataFromHexString:(NSString *)string
    {
        string = [string lowercaseString];
        NSMutableData *data= [NSMutableData new];
        unsigned char whole_byte;
        char byte_chars[3] = {'\0','\0','\0'};
        int i = 0;
        int length = string.length;
        while (i < length-1) {
            char c = [string characterAtIndex:i++];
            if (c < '0' || (c > '9' && c < 'a') || c > 'f')
                continue;
            byte_chars[0] = c;
            byte_chars[1] = [string characterAtIndex:i++];
            whole_byte = strtol(byte_chars, NULL, 16);
            [data appendBytes:&whole_byte length:1];
        }
        return data;
    }
    

    这是基于@Nikunj R. Jadav 的回答

    【讨论】:

      【解决方案4】:
      NSString *command = @"72ff63cea198b3edba8f7e0c23acc345050187a0cde5a9872cbab091ab73e553";
      
      command = [command stringByReplacingOccurrencesOfString:@" " withString:@""];
      NSMutableData *commandToSend= [[NSMutableData alloc] init];
      unsigned char whole_byte;
      char byte_chars[3] = {'\0','\0','\0'};
      int i;
      for (i=0; i < [command length]/2; i++) {
          byte_chars[0] = [command characterAtIndex:i*2];
          byte_chars[1] = [command characterAtIndex:i*2+1];
          whole_byte = strtol(byte_chars, NULL, 16);
          [commandToSend appendBytes:&whole_byte length:1]; 
      }
      NSLog(@"%@", commandToSend);
      

      【讨论】:

      • 你得到的输出是什么?
      • 它的回报
      • 还有一个问题 whole_byte = strtol(byte_chars, NULL, 16);为什么第三个参数作为 16 常量传递?
      • 不错的答案。用于将 NSData deviceToken 描述转换回 NSData。
      • 在答案中我们得到的答案与我们给出的要转换的字符串相同。 ?但是如何将该字符串数据转换为信息量大的数据呢?我的意思是在扫描 BLE 设备后,我得到了类似 `kCBAdvDataManufacturerData = 的广告数据; `这个。所以现在从这个,如何转换,才能访问它的数据。我应该从这个给定的数据中找出 Major Minor TxPower ,。我们应该怎么做 ? @NikunjJadav
      猜你喜欢
      • 2012-11-09
      • 2015-10-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多