iOS的HTML到NSString的Unicode?

我正在将一个Android应用程序移植到iOS上,并遇到了一个小小的障碍。 我从网页中拉取HTML编码的数据,但是一些数据以Unicode显示,以显示外来字符…所以俄语(Летизамной)中的字符将被parsing为"Лет..."

在android中我可以通过调用HTML.fromHTML()来解决这个问题。 有什么类似的iOS?

编写自己的HTML实体解码器非常简单。 只要扫描string寻找&,阅读以下;然后解释结果。 如果是“amp”,“lt”,“gt”或“quot”,则将其replace为相关字符。 如果它以#开始,它是一个数字实体。 如果#后面跟着一个“x”,则将其余的为hex,否则为十进制。 读取数字,然后将字符插入到string中(如果要写入NSMutableString ,可以使用[str appendFormat:@"%C", thechar] NSScanner可以使string扫描非常容易,特别是因为它已经知道如何读取hex数字。

我只是掀起了一个function,应该为你做这个。 请注意,我没有真正testing过,所以你应该通过它的步伐来运行它:

 - (NSString *)stringByDecodingHTMLEntitiesInString:(NSString *)input { NSMutableString *results = [NSMutableString string]; NSScanner *scanner = [NSScanner scannerWithString:input]; [scanner setCharactersToBeSkipped:nil]; while (![scanner isAtEnd]) { NSString *temp; if ([scanner scanUpToString:@"&" intoString:&temp]) { [results appendString:temp]; } if ([scanner scanString:@"&" intoString:NULL]) { BOOL valid = YES; unsigned c = 0; NSUInteger savedLocation = [scanner scanLocation]; if ([scanner scanString:@"#" intoString:NULL]) { // it's a numeric entity if ([scanner scanString:@"x" intoString:NULL]) { // hexadecimal unsigned int value; if ([scanner scanHexInt:&value]) { c = value; } else { valid = NO; } } else { // decimal int value; if ([scanner scanInt:&value] && value >= 0) { c = value; } else { valid = NO; } } if (![scanner scanString:@";" intoString:NULL]) { // not ;-terminated, bail out and emit the whole entity valid = NO; } } else { if (![scanner scanUpToString:@";" intoString:&temp]) { // &; is not a valid entity valid = NO; } else if (![scanner scanString:@";" intoString:NULL]) { // there was no trailing ; valid = NO; } else if ([temp isEqualToString:@"amp"]) { c = '&'; } else if ([temp isEqualToString:@"quot"]) { c = '"'; } else if ([temp isEqualToString:@"lt"]) { c = '<'; } else if ([temp isEqualToString:@"gt"]) { c = '>'; } else { // unknown entity valid = NO; } } if (!valid) { // we errored, just emit the whole thing raw [results appendString:[input substringWithRange:NSMakeRange(savedLocation, [scanner scanLocation]-savedLocation)]]; } else { [results appendFormat:@"%C", c]; } } } return results; } 

&#(number); HTML(和XML)中的结构被称为字符引用。 这不是Unicode特定的,除了HTML中的所有字符都是用Unicode定义的,无论是逐字还是编码为字符或实体引用。 (实体引用是指名称类似于&eacute;或者&amp;并且如果您要抓取HTML页面,那么您肯定也必须处理这些。)

标准库中没有用于解码字符或实体引用的函数。 看到这个问题的方法来解码HTML文本内容。 如果你只有字符引用和标准的XML实体像&amp; 你可以利用NSXMLParser来parsing一个<element> + yourstring + </element> ,但是这不能处理HTML特定的实体,比如&eacute;

一般来说,最好使用合适的HTMLparsing器来完成屏幕抓取,而不是string破解。 这将把所有的文本内容转换成文本节点,并随时转换字符和实体引用。 但是,标准库中没有可用的HTMLparsing器。 如果目标页面是格式正确的独立XHTML,则可以再次使用NSXMLParser 。 否则,你可能会喜欢尝试libxml2,它提供了一个HTMLparsing器以及XML。 看到这个问题的一些背景。

如果您从网站获取数据,您将有一个NS(Mutable)Data对象作为您的接收缓冲区。 你只需要通过以下方式将该NSData转换为NSString
NSString *myString = [[NSString alloc] initWithData:myRecvData usingEncoding:NSUnicodeStringEncoding]
如果你的服务器是用Unicode发送的。 如果您的服务器正在发送utf-8或其他文件,那么您必须在接收代码中调整stringencoding。

这里是所有支持的string编码types的列表

编辑:看看这个如此线程 。