5

iPhoneアプリケーションでAPIを解析するためにlibxml2を使用して、いくつかの一般的なxmlの属性の名前と値のペアを検出しようとして立ち往生しました。私のプロジェクトでは、解析速度が非常に重要であるため、NSXMLParserを使用する代わりにlibxml2自体を使用することにしました。

さて、NSXMLParserとlibxml2の間の解析ベンチマーク用のiPhone SDKのサンプルであるXMLPerformanceを参照して、以下のようにXMLパーサーハンドラーの1つで属性の詳細を取得しようとしましたが、正確に検出する方法がわかりません。

/* 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ドキュメントを見ましたが、できません。あなたが素晴らしいハッカーなら私を助けてください:)

4

2 に答える 2

6

リンクされたドキュメントを見ると、次のようなものがうまくいくと思います:

    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 つの文字列ポインターがあることを前提としています。特に明記されていないので、値の文字列は null で終了し、エンド ポインターは長さを簡単に計算できるようにするためだけに与えられていると想定しても安全だと思います。エンド ポインタがヌル文字を指していない場合は、属性 [3] から属性 [4] までの文字のみを値文字列 (長さ = 属性 [4]-属性 [3]) として解釈する必要があります。

xmlencoding はおそらく xml ドキュメント/エンティティのエンコーディングである必要がありますが、libxml2 はすでに何らかの変換を行っていますが、xmlChar を unsigned char に typedef するため、これはありそうにありません。

于 2010-01-16T04:44:22.360 に答える