Как разобрать XML с NSXMLParser - PullRequest
       32

Как разобрать XML с NSXMLParser

2 голосов
/ 07 апреля 2011

У меня есть следующий xml:

<?xml version="1.0" encoding="UTF-8"?>
<Message>
    <Text>Town park travel</Text>
    <Theme>Ready for racing?</Theme>
    <Activate_date>2011-03-08</Activate_date>
    <Login>Simon</Login>
    <Name>Simon </Name>
    <Longitude>46.00339</Longitude>
    <Latitude>51.515381</Latitude>
</Message>

Как я могу получить элементы в NSMutableDictionary?

Я пытался

- (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName attributes:(NSDictionary *)attributeDict{            
if ([elementName isEqualToString:@"Message"]){
    listOfFriends = [[NSMutableDictionary alloc] init];
    if ([elementName isEqualToString:@"text"]) {
        [listOfFriends setObject: elementName forKey @"text" ];
    }
    }

Но это неправильно

Теперь я использую тот же код:

- (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName attributes:(NSDictionary *)attributeDict{            
if ([elementName isEqualToString:@"Message"]){
    listOfFriends = [[NSMutableDictionary alloc] init];
} else if ([elementName isEqualToString:@"Text"] || [elementName isEqualToString:@"Theme"] || [elementName isEqualToString:@"Activate_date"] || [elementName isEqualToString:@"Login"] || [elementName isEqualToString:@"Longitude"] || [elementName isEqualToString:@"Latitude"]) {
    [currentElement setString:@""];
    storingCharacters = YES;
}
}   

- (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName {
if ([elementName isEqualToString:@"Message"]) {
    [listOfFriends release];
} else if ([elementName isEqualToString:@"Text"]) {
    txt.text = currentElement;
} else if ([elementName isEqualToString:@"Theme"]) {
    theme.text = currentElement;
} else if ([elementName isEqualToString:@"Activate_date"]) {
    aDate.text = currentElement;
} else if ([elementName isEqualToString:@"Login"]) {
    autor.text = currentElement;
} 
storingCharacters = NO;
}
- (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string {
if (storingCharacters) [currentElement appendString:string];
}

Но у меня на виду пустые этикетки ...

1 Ответ

5 голосов
/ 07 апреля 2011

NSXMLParser основан на потоке и отправляет различные сообщения своему делегату, когда он встречает определенные компоненты в потоке XML - открывающий тег, текст, конечный тег и так далее.Итак, создайте экземпляр NSXMLParser и назначьте ему записанный вами делегат, соответствующий протоколу NSXMLParserDelegate .( Edit: из кода, который вы добавили в свой вопрос, похоже, что вы, возможно, уже выполнили эту часть или, по крайней мере, хорошо ее начали. )

В классе вашего делегата'-parser:didStartElement:..., проверьте имя элемента.Если это «Сообщение», создайте новый NSMutableDictionary для хранения информации в его дочерних элементах и ​​сохраните ее в свойстве: ( Edit: в вашем коде выглядит так, как будто вы объявили переменную экземпляра, но вам следуетиспользуйте точечный синтаксис для доступа к нему как к свойству, чтобы убедиться, что происходит правильное управление памятью. )

self.listOfFriends = [NSMutableDictionary dictionary];

Для других имен элементов создайте пустую NSMutableString, которая будет использоваться для хранения текстаи сохраните его в свойстве:

self.thisString = [NSMutableString string];

В своем методе -parser:foundCharacters: добавьте строку в свойство изменяемой строки, созданное ранее.

[self.thisString appendString:string];

Наконец, в вашем методе -parser:didEndElement:... проверьте имя элемента.Если это «Сообщение», вы закончили с этим элементом сообщения.Если ваш XML-поток имеет только один элемент Message (как в примере), вы можете теперь напечатать созданный вами словарь или что-то еще, что вы хотели с ним сделать.Если может быть несколько элементов сообщения, вы можете добавить только что завершенный элемент в массив.

Если элемент только что закончен - это не сообщение, добавьте его в словарь с помощью -setValue:forKey: передача имени элемента в качестве ключа и созданной строки, полученной при получении более ранних -parser:foundCharacters: сообщений в качестве значения.

[self.listOfFriends setValue:self.thisString forKey:elementName];
...