Специальные символы в NSString от HTML

Я выбираю данные из исходного кода XML и анализирую через них с tbxml. Все хорошо работает, пока я не добираюсь до латинской буквы как "é", который она отобразит как: Код:

é

Я не вижу правильного метода NSString сделать преобразование. Какие-либо идеи?

6
задан kennytm 12 February 2010 в 20:33
поделиться

2 ответа

Это довольно распространенная проблема. Ознакомьтесь с Декодирование символов HTML в Objective-C / Cocoa Touch

3
ответ дан 17 December 2019 в 00:08
поделиться

Вы можете использовать regex. Регекс - это решение и причина всех проблем! :)

В примере ниже используется, по крайней мере на момент написания этой статьи, еще не выпущенная версия RegexKitLite 4.0. Вы можете получить снимок разработки 4.0 через svn:

shell% svn co http://regexkit.svn.sourceforge.net/svnroot/regexkit regexkit

Примеры ниже используют преимущества новой функции блоков 4.0 для поиска и замены сущностей символов é.

Первый пример - более простой из двух. Он только обрабатывает десятичные символьные сущности, такие как é, а не шестнадцатеричные символьные сущности, такие как é. Если вы можете гарантировать, что у вас никогда не будет шестнадцатеричных символьных сущностей, это должно быть нормально:

#import <Foundation/Foundation.h>
#import "RegexKitLite.h"

int main(int argc, char *charv[]) {
  NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];

  NSString *string = @"A test: &#233; and &#xe9; ? YAY! Even >0xffff are handled: &#119808; or &#x1D400;, see? (0x1d400 == MATHEMATICAL BOLD CAPITAL A)";
  NSString *regex = @"&#([0-9]+);";

  NSString *replacedString = [string stringByReplacingOccurrencesOfRegex:regex usingBlock:^NSString *(NSInteger captureCount, NSString * const capturedStrings[captureCount], const NSRange capturedRanges[captureCount], volatile BOOL * const stop) {
      NSUInteger u16Length = 0UL, u32_ch = [capturedStrings[1] integerValue];
      UniChar u16Buffer[3];

      if (u32_ch <= 0xFFFFU)       { u16Buffer[u16Length++] = ((u32_ch >= 0xD800U) && (u32_ch <= 0xDFFFU)) ? 0xFFFDU : u32_ch; }
      else if (u32_ch > 0x10FFFFU) { u16Buffer[u16Length++] = 0xFFFDU; }
      else                         { u32_ch -= 0x0010000UL; u16Buffer[u16Length++] = ((u32_ch >> 10) + 0xD800U); u16Buffer[u16Length++] = ((u32_ch & 0x3FFUL) + 0xDC00U); }

      return([NSString stringWithCharacters:u16Buffer length:u16Length]);
    }];

  NSLog(@"replaced: '%@'", replacedString);

  return(0);
}

Скомпилируйте и запустите с:

shell% gcc -arch i386 -g -o charReplace charReplace.m RegexKitLite.m -framework Foundation -licucore
shell% ./charReplace
2010-02-13 22:51:48.909 charReplace[35527:903] replaced: 'A test: é and &#xe9; ? YAY! Even >0xffff are handled:                   
4
ответ дан 17 December 2019 в 00:08
поделиться
Другие вопросы по тегам:

Похожие вопросы: