Как мне преобразовать значение NSString в NSData?


Ответы:


1419
NSString* str = @"teststring";
NSData* data = [str dataUsingEncoding:NSUTF8StringEncoding];

Каковы плюсы и минусы использования UTF-8 в отличие от чего-то более высокого, такого как UTF-16 или UTF-32?
Альберт Реншоу

4
NSData не заботится о том, является ли это UTF-8 или UTF-16 или UTF-32. Есть две проблемы: одна, UTF-16 и UTF-32 должны иметь правильный порядок байтов. Во-вторых, тот, кто преобразует его обратно в NSString *, должен знать кодировку и часто будет использовать кодировку UTF-8. Как правило, UTF-8, скорее всего, будет обрабатываться правильно.
gnasher729

1
@bendytree на самом деле это не так, -dataUsingEncoding: вернет строку, не заканчивающуюся нулем, что и требуется для stringWithUTF8String: вы обязаны читать память, которая вам не нужна. Что преобразует его обратно: -initWithData: encoding :.
Психо

1
@ Альберт Реншоу в настоящее время (без гарантий того, что так и останется) NSStringиспользует UTF-16 для внутреннего использования, поэтому возможен небольшой выигрыш в производительности, поскольку ему не нужно выполнять преобразование UTF-16 <-> UTF-8. Лично мы предпочитаем (как подсказывает @ gnasher729) надежность над производительностью и везде используем UTF-8.
Какой-то разработчик

66
NSString *str = @"helowrld";
// This converts the string to an NSData object
NSData *data = [str dataUsingEncoding:NSUTF8StringEncoding];

Вы можете взять ссылку по этой ссылке


3
Одно линейное решение:NSData *data = [@"helowrld" dataUsingEncoding:NSUTF8StringEncoding];
Raptor

32

Делать:

NSData *data = [yourString dataUsingEncoding:NSUTF8StringEncoding];

тогда не стесняйтесь продолжать NSJSONSerialization:JSONObjectWithData.


Исправление к ответу относительно NULL-терминатора

После комментариев, официальной документации и проверок этот ответ был обновлен в отношении удаления предполагаемого терминатора NULL:

  1. Как задокументировано dataUsingEncoding :

    Возвращаемое значение

    Результат вызова dataUsingEncoding:allowLossyConversion: с NO в качестве второго аргумента

  2. Как задокументировано getCString: maxLength: encoding: и cStringUsingEncoding ::

    обратите внимание, что возвращаемые данные dataUsingEncoding:allowLossyConversion:не являются строгой C-строкой, так как не имеют терминатора NULL


14
Это не верно! Пожалуйста, смотрите мой пост здесь: stackoverflow.com/q/14087094/192819
jpswain

4
Ага. dataUsingEncoding:не возвращает данные с нулевым символом в конце Только UTF8Stringи другие методы, которые возвращают строку C, возвращают строку с нулевым символом в конце.
Питер Хоси

@PeterHosey у тебя есть источник для этого? Мне трудно найти это в любых документах.
shortstuffsushi

1
Благодаря @PeterHosey, Документы вы связаны там же явно указать отсутствие прекращения NULL - (note that the data returned by dataUsingEncoding:allowLossyConversion: is not a strict C-string since it does not have a NULL terminator). Должно быть, я пропустил это раньше. Я обязательно напишу что-нибудь в будущем, хотя.
shortstuffsushi

1
(Для тех, кто интересуется: цитата shortstuffsushi под cStringUsingEncoding:. Я искал под dataUsingEncoding:.)
Питер Хоси

20

В случае появления Swift Developer,

конфертировать из NSString / String в NSData

var _nsdata = _nsstring.dataUsingEncoding(NSUTF8StringEncoding)

18

Objective-C:

NSString *str = @"test string";
NSData *data = [NSKeyedArchiver archivedDataWithRootObject:str];
NSString *thatStr = [NSKeyedUnarchiver unarchiveObjectWithData:data];

Swift:

let str = "test string"
let data = NSKeyedArchiver.archivedData(withRootObject: str)
let thatStr = NSKeyedUnarchiver.unarchiveObject(with: data) as! String

Вероятно, интенсивно использует процессор по сравнению с другими методами, но очень полезно, если вы постоянно обращаетесь к файловой системе
Стивен Дж

10

Прежде всего, вы должны использовать dataUsingEncoding:вместо прохождения UTF8String. Вы используете только UTF8Stringтогда, когда вам нужноC строка в этой кодировке.

Тогда UTF-16просто пройдите NSUnicodeStringEncodingвместо NSUTF8StringEncodingвашего dataUsingEncoding:сообщения.


7

Для Swift 3 вы будете в основном конвертировать из Stringв Data.

let myString = "test"
let myData = myString.data(using: .utf8)
print(myData) // Optional(Data)

6
NSString *str = @"hello";
NSData *data = [NSData dataWithBytes:str.UTF8String length:str.length];

5
Этот ответ неверен, если strсодержит кодовые точки больше 127. Это потому, что str.lengthдает количество символов Юникода, а не количество байтов. Например, если strесть @"にほんご", str.lengthдает 4, а на str.UTF8Stringсамом деле содержит 12 байтов. Даже если вы замените str.lengthна strlen(str.UTF8String), это все равно будет неправильно для случая, когда strсодержит символ NULL, например @"にほ\0んご".
Панг

Созданный таким образом объект NSData выбрасывает исключение при использовании с [NSJSONSerialization JSONObjectWithData: параметры данных: NSJSONReadingMutableLeaves error: & error];
Adobels,

2

Objective-C:

NSString to NSData:

NSString* str= @"string";
NSData* data=[str dataUsingEncoding:NSUTF8StringEncoding];

NSData to NSString:

NSString* newStr = [[NSString alloc] initWithData:theData encoding:NSUTF8StringEncoding];

Swift:

Строка для данных:

var testString = "string"
var somedata = testString.data(using: String.Encoding.utf8)

Данные в строку:

var backToString = String(data: somedata!, encoding: String.Encoding.utf8) as String!


0

Objective-C

NSString *str = @"Hello World";
NSData *data = [str dataUsingEncoding:NSUTF8StringEncoding allowLossyConversion:NO];

стриж

let str = "Hello World"
let data = string.data(using: String.Encoding.utf8, allowLossyConversion: false)
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.