Как получить имя и значение атрибутов из xml при использовании синтаксического анализатора libxml2?

Я застрял при попытке определить пару имени и значения атрибутов в некоторых общих xmls, используя libxml2 для анализа API в приложении iPhone. Для моего проекта скорость синтаксического анализа действительно важна, поэтому я решил использовать сам libxml2 вместо NSXMLParser.

Теперь, ссылаясь на XMLPerformance, который является примером iPhone SDK для эталонного анализа между NSXMLParser и libxml2, я попытался получить подробную информацию об атрибуте в одном из обработчиков синтаксического анализатора XML, как показано ниже, но я не знаю точно, как его обнаружить,

/* for example, <element key="value" /> */
static void startElementSAX(void *ctx, const xmlChar *localname, const xmlChar *prefix,
const xmlChar *URI, int nb_namespaces, const xmlChar **namespaces, int nb_attributes,
int nb_defaulted, const xmlChar **attributes)
{
    if (nb_attributes > 0)
    {
        NSMutableDictionary* attributeDict = [NSMutableDictionary dictionaryWithCapacity:(NSUInteger)[NSNumber numberWithInt:nb_attributes]];
        for (int i=0; i<nb_attributes; i++)
        {
            NSString* key = @""; /* expected: key */
            NSString* val = @""; /* expected: value */
            [attributeDict setValue:val forKey:key];
        }
     }
}

Я видел документ libxml2, но не могу. Пожалуйста, помогите мне, если вы отличный хакер:)

2 ответа

Решение

Глядя на связанную документацию, я думаю, что-то вроде этого может сработать:

    for (int i=0; i<nb_attributes; i++) 
    { 
        // if( *attributes[4] != '\0' ) // something needed here to null terminate the value
        NSString* key = [NSString stringWithCString: attributes[0] encoding: xmlencoding];
        NSString* val = [NSString stringWithCString: attributes[3] encoding: xmlencoding];
        [attributeDict setValue:val forKey:key];
        attributes += 5;
    } 

Это предполагает, что всегда есть 5 строковых указателей для каждого атрибута. Поскольку не указано иное, я думаю, что можно с уверенностью предположить, что строка значения заканчивается нулем, а указатель конца дается только для простого вычисления длины. Если указатель конца не указывает на нулевой символ, вам нужно будет интерпретировать только символы из атрибутов [3] до атрибутов [4] как строку значений (length = attribute [4]-attributes[3]).

Вероятно, xmlencoding должен быть кодировкой документа / сущности xml, за исключением того, что libxml2 уже выполняет какое-то преобразование, хотя это кажется маловероятным, поскольку оно определяет xmlChar для unsigned char.

Для других, на основе x4u ответа и комментария tksohishi:

 static void startElementSAX(void *ctx, const xmlChar *localname, const xmlChar *prefix, const xmlChar *URI,
                                         int nb_namespaces, const xmlChar **namespaces, int nb_attributes, int nb_defaulted, const xmlChar **attributes)
 {

        NSLog(@"localname = %s",localname);

        if(nb_attributes>0)
        {
            NSMutableDictionary * attributeDict =[[NSMutableDictionary alloc] initWithCapacity:nb_attributes];

            for (int i=0; i<nb_attributes; i++)
            {

                NSString* key = [NSString stringWithCString:(const char*)attributes[0] encoding:NSUTF8StringEncoding];
                NSString* val = [[NSString alloc] initWithBytes:(const void*)attributes[3] length:(attributes[4] - attributes[3]) encoding:NSUTF8StringEncoding]; // it'll be required // [val release];
                [attributeDict setValue:val forKey:key];
                attributes += 5;
            }
        }
 }
Другие вопросы по тегам