Имейте в виду, что любое решение String(format: ...)
будет очень медленным (для больших данных)
NSData *data = ...;
NSUInteger capacity = data.length * 2;
NSMutableString *sbuf = [NSMutableString stringWithCapacity:capacity];
const unsigned char *buf = data.bytes;
NSInteger i;
for (i=0; i<data.length; ++i) {
[sbuf appendFormat:@"%02X", (NSUInteger)buf[i]];
}
Если вам нужно что-то более производительное , попробуйте это:
static inline char itoh(int i) {
if (i > 9) return 'A' + (i - 10);
return '0' + i;
}
NSString * NSDataToHex(NSData *data) {
NSUInteger i, len;
unsigned char *buf, *bytes;
len = data.length;
bytes = (unsigned char*)data.bytes;
buf = malloc(len*2);
for (i=0; i<len; i++) {
buf[i*2] = itoh((bytes[i] >> 4) & 0xF);
buf[i*2+1] = itoh(bytes[i] & 0xF);
}
return [[NSString alloc] initWithBytesNoCopy:buf
length:len*2
encoding:NSASCIIStringEncoding
freeWhenDone:YES];
}
Версия Swift 4.2
extension Data {
var hexString: String? {
return withUnsafeBytes { (bytes: UnsafePointer<UInt8>) in
let charA = UInt8(UnicodeScalar("a").value)
let char0 = UInt8(UnicodeScalar("0").value)
func itoh(_ value: UInt8) -> UInt8 {
return (value > 9) ? (charA + value - 10) : (char0 + value)
}
let hexLen = count * 2
let ptr = UnsafeMutablePointer<UInt8>.allocate(capacity: hexLen)
for i in 0 ..< count {
ptr[i*2] = itoh((bytes[i] >> 4) & 0xF)
ptr[i*2+1] = itoh(bytes[i] & 0xF)
}
return String(bytesNoCopy: ptr,
length: hexLen,
encoding: .utf8,
freeWhenDone: true)
}
}
}