Objective-C: Parsing XML with gdata



我试图用gdataxmlnode objective-c库来解析巨大的XML文档(描述3D模型)。

这是阻止我的XML样本:

<library_effects>
    <effect name="Love_Love-fx" id="Love_Love-fx">
        <profile_COMMON>
            <newparam sid="sexy-surface">
                <surface type="2D">
                    <init_from>sexy</init_from>
                    <format>A8R8G8B8</format>
                </surface>
            </newparam>
            ....
        </profile_COMMON>
    </effect>
    ....
</library_effects>

我的目标

  1. 获取效果名称(*love_love-fx*):完美工作

  2. 获取init_from的内容( sexy ):根本不起作用

这是我解析的方式:

xmlGetData = [xmlDoc.rootElement elementsForName:@"library_effects"];   
//Effects infos
int eff_c;
NSMutableArray *eff_ids = [[NSMutableArray alloc] init];  //effect names
NSMutableArray *eff_src = [[NSMutableArray alloc] init];  //efects sources
for (GDataXMLElement *e in xmlGetData)
{
    eff_c = [[e elementsForName:@"effect"]count];        
    NSArray *eff_node  = [e elementsForName:@"effect"];
    for (int i = 0; i < eff_c; i++)
    {
        //get the effect name (id & name are the same)
        [eff_ids addObject:[[eff_node objectAtIndex:i]attributeForName:@"id"]];
        //get the content of init_from
        [eff_src addObject:[[eff_node objectAtIndex:i]elementForName:@"init_from"]];
    }
}

我的问题:我在最后一行([eff_src addObject.........)上有一个sigabrt,所以我没有设法获得" init_from"的内容

(因为 [[eff_node objectAtIndex:i]elementForName:@"init_from"]]返回零。?)

有人可以帮我吗?(是否有清晰的文档?我只看到博客文章解释了其中一部分)

令人恶心的解决方案:使用[[[[[[eff_node objectAtIndex:i]childAtIndex:0]childAtIndex:0]childAtIndex:0]childAtIndex:0]stri‌​ngValue];

eff_node是XML节点effect。我的猜测是elementForName:方法不递归起作用,并且由于init_from不是effect的直接孩子,因此返回了零。

您的XML中没有effect s,其中没有init_from节点。

基本上,您不能将零添加到NSMutableArray,因此您需要测试两个 addObject:参数nil,例如。

id idAttr = [[eff_node objectAtIndex:i]attributeForName:@"id"];
if (idAttr != nil)
{
    [eff_ids addObject:idAttr];
}
GDataXMLElement* initFrom = [[eff_node objectAtIndex:i]elementForName:@"init_from"];
if (initFrom != nil)
{
    [eff_src addObject: initFrom];
}

还请注意该行

NSArray *eff_node  = [[NSArray alloc] init];

不必要地实例化一个空数组,在手动参考计数中是记忆泄漏。


我刚刚看过gdataxml api,它是a)无证件(从某种意义上说,他们不能写文档,而不是私人API的感觉)和b)限制。

您使用的方法不会进行递归搜索,因此您有两个选项,要么实现自己的递归搜索,要么使用XPath API。填充应该得到您想要的节点:

 NSError* myError = nil;
 NSArray* initFromNodes = [[eff_node objectAtIndex: i] nodesForXPath: @"//init_from" error: &myError]; 

XPath的//部分表示"树下的任何数量的级别"

最新更新