NSJSONSerialization 不工作,NSUTF8StringEncoding 工作
Posted
技术标签:
【中文标题】NSJSONSerialization 不工作,NSUTF8StringEncoding 工作【英文标题】:NSJSONSerialization Not Working, NSUTF8StringEncoding Is Working 【发布时间】:2014-03-11 12:50:23 【问题描述】:我已经阅读了文档、教程和其他 Stack Q&A,我很想知道如何使用 NSUTF8StringEncoding
让我的 JSON
出现,但不使用 NSJSONSerialization
- 这就是我需要将数据提取到NSDictionary
或NSArray
。我认为这是从我的 URL 返回的 NSData
格式的问题?
编辑这里是错误:Error Domain=NSCocoaErrorDomain Code=3840“无法完成操作。(Cocoa 错误 3840。)”(垃圾结束。) UserInfo=0x8aabc30
NSURLRequest *theRequest=[NSURLRequest requestWithURL:[NSURL URLWithString:@"http://www.sampleURL.com"]
cachePolicy:NSURLRequestUseProtocolCachePolicy
timeoutInterval:15.0];
NSMutableData* responseData = [NSMutableData dataWithCapacity: 0];
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data
//this works, and have NSLog below
responseString = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
NSLog(@"string %@", responseString);
[responseData appendData:data];
responseData = [[NSMutableData alloc] initWithData:data];
//this is null in NSLog
NSError * error;
NSDictionary *jsonDict = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers|NSJSONReadingAllowFragments error:&error];
NSLog(@"jsonDict dict %@",jsonDict);
调试控制台:
2014-03-11 07:41:58.233 WBPC[7845:a0b] string "id":"a1","session":"General","name":"Exhibitor Setup Begins","startTime":"0900","details":"9am Exhibitor Hall","png":"image","speaker1":"Johnson","speaker2":"Nelson","speaker3":"""id":"b1","session":"General","name":"Conference Registration","startTime":"1000","details":"10am Noon Upper Level Lobby","png":"image","speaker1":"Jackson","speaker2":"","speaker3":""
2014-03-11 07:41:58.236 WBPC[7845:a0b] jsonDict (null)
【问题讨论】:
NSMutableDictionary * json = [NSJSONSerialization JSONObjectWithData:data options: NSJSONReadingMutableContainers error: &error];试试这个 我实际上尝试过那个(来自你们中的其他 Stack 帖子),但没有运气。我确信这是从 URL 返回的 JSON 的格式问题... @NamoNamo - 这是我从 NSJSONSerialization 收到的错误:错误域 = NSCocoaErrorDomain 代码 = 3840“操作无法完成。(可可错误 3840。)”(垃圾结束。)用户信息=0x8aabc30。谢谢。 【参考方案1】:您在 'didReceiveData' 委托函数中完成这一切,这不是正确的位置。唯一应该存在的是:
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data
[self.responseData appendData:data];
但在此之前,您应该在连接收到响应时初始化“self.responseData”:
-(void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response
if(self.responseData != nil) self.responseData = nil;
self.responseData = [[NSMutableData alloc] init];
然后,您需要实现另一个名为“connectionDidFinishLoading”的委托函数,当调用此方法时,您的“responseData”将包含来自 JSON 的所有数据并准备好解析:
-(void)connectionDidFinishLoading:(NSURLConnection *)connection
responseString = [[NSString alloc] initWithData:self.responseData encoding:NSUTF8StringEncoding];
NSLog(@"string %@", responseString);
NSError * error;
NSDictionary *jsonDict = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers|NSJSONReadingAllowFragments error:&error];
NSLog(@"jsonDict dict %@",jsonDict);
我希望这在某种程度上有所帮助。
【讨论】:
感谢分享。实际上,我确实使用了这些委托方法,我只是出于说明目的简化了我的示例。 除了上面已经显示的之外,在委托方法connection: didReceiveResponse:
中应该检查HTTP 状态代码和响应数据的类型(MIME 类型)。如果状态码指示错误,我们无论如何都应该读取响应,以便从服务器获取可能的“错误消息”。在connectionDidFinishLoading:
中,我们再次使用 HTTP 状态码来决定是否应该记录错误消息或根据 MIME 类型处理预期的响应数据。【参考方案2】:
您的 JSON 格式不正确。您告诉我们它是(为便于阅读而添加了空格和换行符):
"id": "a1",
"session": "General",
"name": "Exhibitor Setup Begins",
"startTime": "0900",
"details": "9am Exhibitor Hall",
"png": "image",
"speaker1": "Johnson",
"speaker2": "Nelson",
"speaker3": ""
"id": "b1",
"session": "General",
"name": "Conference Registration",
"startTime": "1000",
"details": "10am Noon Upper Level Lobby",
"png": "image",
"speaker1": "Jackson",
"speaker2": "",
"speaker3": ""
这在两个字典条目之间缺少逗号,并且您缺少应该包装 JSON 的 [
和 ]
。如果它真的是一个字典条目数组,它应该是:
[
"id": "a1",
"session": "General",
"name": "Exhibitor Setup Begins",
"startTime": "0900",
"details": "9am Exhibitor Hall",
"png": "image",
"speaker1": "Johnson",
"speaker2": "Nelson",
"speaker3": ""
,
"id": "b1",
"session": "General",
"name": "Conference Registration",
"startTime": "1000",
"details": "10am Noon Upper Level Lobby",
"png": "image",
"speaker1": "Jackson",
"speaker2": "",
"speaker3": ""
]
如果你想检查你的 JSON,你可以访问http://jsonlint.com。此外,如果您检查了 JSONObjectWithData
返回的 error
对象,它会为您指明正确的方向。
您应该看看这个 JSON 是如何生成的。看起来它必须是手动生成的。例如,如果您从 php 页面生成此文件,则应使用 json_encode
,而不是手动生成 JSON。
顺便说一句,您正在尝试解析didReceiveData
中的结果。在connectionDidFinishLoading
之前,您不应该尝试解析。您的 didReceiveData
应该仅将 data
附加到您的 NSMutableData
对象。解析应该推迟到connectionDidFinishLoading
。
【讨论】:
问题在于我的 PHP 是如何输出 JSON 的,我需要将它包装在这样的数组中: $output = array();而 ($list = mysql_fetch_assoc($query)) $output[] = $list; echo json_encode($output);【参考方案3】:你好,你可以试试这个。
NSError *error = nil;
NSArray *jsonResponseArray = [NSJSONSerialization JSONObjectWithData: YOURDATA options: NSJSONReadingMutableContainers error: &error];
if (!jsonResponseArray)
NSLog(@"Error: %@", error);
else
for(NSDictionary *dic in jsonResponseArray)
NSLog(@"dic values are : %@", item);
谢谢
【讨论】:
不幸的是我也试过这个,但没有运气。【参考方案4】:您发布的 JSON 字符串不是有效的 JSON。仅仅因为数据是有效的 UTF8 字符串并不意味着它一定是 JSON。尝试将调试后的字符串粘贴到 JSONLint 中,它会显示您的 JSON 对象之间缺少逗号。
【讨论】:
当然 JSON 可以是 UTF-16 或 UTF-32,所以有效的 JSON 不需要是有效的 UTF8 字符串。以上是关于NSJSONSerialization 不工作,NSUTF8StringEncoding 工作的主要内容,如果未能解决你的问题,请参考以下文章
NSJSONSerialization 将 \n 添加到 JSON 字符串的开头和结尾
使用 NSJSONSerialization 解析 JSON - 抛出 NSException