iOS 的 OC 语言:二进制数据处理与技巧

在 iOS 开发中,尤其是涉及蓝牙通信(BLE)Socket 数据传输设备指令解析 等场景时,处理二进制数据(NSData、十六进制字符串、大小端等)成为必备技能。

本篇文章将基于 Objective-C,深入介绍如何高效处理二进制数据,并配合实用示例和技巧,帮助你构建稳定可靠的底层数据通信逻辑。

应用场景举例

  • 蓝牙设备协议解析(如:<0x01 0x0A 0xFF>
  • Socket 数据封包解包
  • 物联网(IoT)设备指令转换
  • 图片/音频等二进制资源校验与处理

基础工具:NSData 与 NSString 互转

一、十六进制字符串 → NSData

objc 复制代码
/// 将十六进制字符串转换为 NSData
+ (NSData *)transToDataWithString:(NSString *)hexString {
    NSMutableData *data = [NSMutableData data];
    for (int i = 0; i < hexString.length; i += 2) {
        NSString *byteStr = [hexString substringWithRange:NSMakeRange(i, 2)];
        unsigned int byteValue;
        [[NSScanner scannerWithString:byteStr] scanHexInt:&byteValue];
        [data appendBytes:&byteValue length:1];
    }
    return data;
}

示例:

objc 复制代码
NSString *hex = @"aabbccdd";
NSData *data = [ParseDataTool transToDataWithString:hex];
NSLog(@"data: %@", data); // 输出:<aa bb cc dd>

二、NSData → 十六进制字符串

objc 复制代码
/// 将 NSData 转为十六进制字符串
+ (NSString *)transDataToHexString:(NSData *)data {
    const unsigned char *dataBuffer = (const unsigned char *)data.bytes;
    if (!dataBuffer) return @"";

    NSMutableString *hexString = [NSMutableString stringWithCapacity:data.length * 2];
    for (int i = 0; i < data.length; ++i) {
        [hexString appendFormat:@"%02x", dataBuffer[i]];
    }
    return [hexString copy];
}

进阶处理:大小端转换(Big Endian vs Little Endian)

为什么需要大小端?

在不同平台(如 iOS vs 嵌入式设备)之间传输数据时,字节顺序可能不同。一个整数 0x12345678

  • 大端(Big Endian):12 34 56 78
  • 小端(Little Endian):78 56 34 12

OC 示例:NSData 转整型(小端)

objc 复制代码
+ (NSInteger)transLittleEndianDataToInteger:(NSData *)data {
    NSInteger value = 0;
    for (NSInteger i = 0; i < data.length; i++) {
        value |= ((uint8_t *)data.bytes)[i] << (8 * i);
    }
    return value;
}

示例:

objc 复制代码
NSData *littleEndianData = [ParseDataTool transToDataWithString:@"78563412"];
NSInteger intValue = [ParseDataTool transLittleEndianDataToInteger:littleEndianData];
// 输出:0x12345678 -> 305419896

数据描述格式化:调试更方便

添加空格分隔(便于人眼阅读)

objc 复制代码
// "aabbcc" → "aa bb cc"
+ (NSString *)describeBlankFormatWithString:(NSString *)dataString {
    NSMutableArray *result = [NSMutableArray array];
    for (NSInteger i = 0; i < dataString.length; i += 2) {
        NSString *byte = [dataString substringWithRange:NSMakeRange(i, 2)];
        [result addObject:byte];
    }
    return [result componentsJoinedByString:@" "];
}

添加 0x 前缀(用于打印/调试)

objc 复制代码
// "aabbcc" → "0xaa, 0xbb, 0xcc"
+ (NSString *)describeBytesFormatWithString:(NSString *)dataString {
    NSMutableArray *result = [NSMutableArray array];
    for (NSInteger i = 0; i < dataString.length; i += 2) {
        NSString *byte = [dataString substringWithRange:NSMakeRange(i, 2)];
        [result addObject:[NSString stringWithFormat:@"0x%@", byte]];
    }
    return [result componentsJoinedByString:@", "];
}

字节倒序与逆序指令处理

在解析某些设备协议时,你可能需要将指令内容 倒序排列,如下:

objc 复制代码
// 输入:"a7000003" 输出:"030000a7"
+ (NSString *)invertedOrderWithStr:(NSString *)str {
    NSMutableString *result = [NSMutableString string];
    for (NSInteger i = str.length; i >= 2; i -= 2) {
        NSString *byte = [str substringWithRange:NSMakeRange(i - 2, 2)];
        [result appendString:byte];
    }
    return [result copy];
}

校验算法:XOR 异或校验

某些协议中结尾校验位采用 XOR 校验,即所有字节异或后得到校验值。

objc 复制代码
+ (NSString *)xorWithDataString:(NSString *)dataString {
    NSData *data = [self transToDataWithString:dataString];
    uint8_t result = 0;
    const uint8_t *bytes = (const uint8_t *)data.bytes;

    for (int i = 0; i < data.length; i++) {
        result ^= bytes[i];
    }
    return [NSString stringWithFormat:@"%02x", result];
}

示例:

objc 复制代码
NSString *xor = [ParseDataTool xorWithDataString:@"030a2713ea"];
NSLog(@"异或结果:%@", xor); // 输出:XX

实战案例:构造蓝牙写入命令

objc 复制代码
NSString *cmdHex = @"a10201"; // 指令 + 参数
NSString *xor = [ParseDataTool xorWithDataString:cmdHex];
NSString *finalHex = [cmdHex stringByAppendingString:xor]; // 拼接校验位
NSData *writeData = [ParseDataTool transToDataWithString:finalHex];
// 然后通过蓝牙 writeCharacteristic 发送

最后

本文深入介绍了我在iOS实际工作中使用 Objective-C 处理二进制数据的技巧与实战经验,包括:

  • NSDataNSString 的互转
  • 大小端整数转换
  • 指令格式化、倒序、校验
  • 真实通信场景中的构造与解析

这些内容在蓝牙、Socket、物联网等开发场景中具有广泛应用。如果你在实际开发中遇到数据解析难题,不妨将这些工具方法封装进自己的项目中,快速定位和解决问题。

如有说错的地方,烦请大家指正,谢谢~

相关推荐
北京自在科技2 小时前
Find My 修复定位 BUG,AirTag 安全再升级
ios·findmy·airtag
Digitally2 小时前
如何不用 USB 线将 iPhone 照片传到电脑?
ios·电脑·iphone
Sim148015 小时前
iPhone将内置本地大模型,手机端AI实现0 token成本时代来临?
人工智能·ios·智能手机·iphone
Digitally17 小时前
如何将 iPad 上的照片传输到 U 盘(4 种解决方案)
ios·ipad
报错小能手19 小时前
ios开发方向——swift并发进阶核心 @MainActor 与 DispatchQueue.main 解析
开发语言·ios·swift
LcGero19 小时前
Cocos Creator 业务与原生通信详解
android·ios·cocos creator·游戏开发·jsb
ii_best19 小时前
lua语言开发脚本基础、mql命令库开发、安卓/ios基础开发教程,按键精灵新手工具
android·ios·自动化·编辑器
用户223586218202 天前
WebKit WebPage API 的引入尝试与自研实现
ios
啦啦啦!2 天前
ChatGPT和Gemini的接入和封装
人工智能·ios·chatgpt
报错小能手2 天前
ios开发方向——swift并发进阶核心 async/await 详解
开发语言·ios·swift