Проблема с getCharacters:range:
состоит в том, что он дает вам символы UTF-16 (unichar
s), тогда как вы хотите ASCII.
*(ResType*)[aString UTF8String]
преобразует строку в UTF-8 (что эквивалентно ASCII, если все символы в строке вписываются в диапазон ASCII), а затем выдаст первые четыре байта в качестве значения ResType
. Насколько это эффективно, зависит от того, как часто вы хотите выполнять эти преобразования.
Другой вариант - использовать getBytes:maxLength:usedLength:encoding:options:range:remainingRange:
с кодировкой, установленной на NSASCIIStringEncoding
или NSUTF8StringEncoding
, целевым буфером, установленным на указатель на существующую переменную ResType
, и максимальной длиной, установленной на 4
(или sizeof (ResType)
).
Обновление:
Я понял, почему вы не получаете правильный результат с моим предложением. Оказывается, что в четырехзначных целочисленных литералах байты хранятся в порядке, противоположном тому, как они записаны. Вот пример:
#include <Foundation/Foundation.h>
int main() {
int code = 'RTF ';
printf("'%c%c%c%c' = %d\n", ((char*)&code)[0], ((char*)&code)[1],
((char*)&code)[2], ((char*)&code)[3],
code);
}
Вывод ' FTR' = 1381254688
. Итак, если вы хотите преобразовать из NSString
s в эти значения, вот несколько вариантов:
- Скопируйте строку в четырехбайтовый буфер (используя один из предложенных мной методов), а затем измените ее, поменяв местами байт
0
с байтом 3
и байт 1
с байтом 2
.
- То же самое, но выполните реверсирование с помощью стандартного алгоритма «смены порядка байтов», подобного алгоритму на на этой странице .
- Переберите первые (и только) четыре символа, используя
characterAtIndex:
, и вставьте их в четырехбайтовый буфер в обратном порядке. Помните, что characterAtIndex:
возвращает символ UTF-16, но его можно легко преобразовать в символ ASCII, если он находится в диапазоне ASCII.