2015-11-07 63 views
0

我有一個XML數據如下Perl的哈希使用的libxml

<type> 
    <data1>something1</data1> 
    <data2>something2</data2> 
</type> 
<type> 
    <data1>something1</data1> 
    <data2>something2</data2> 
</type> 
<type> 
    <data1>something1</data1> 
</type> 

如可以看到的,子節點DATA2有時不存在。

我已經使用this作爲指導來創建下面的代碼

my %hash; 
my $parser = XML::LibXML->new(); 
my $doc = $parser->parse_file($file_name); 
my @nodes = $doc->findnodes("/type"); 

foreach my $node(@nodes) 
{ 
    my $key = $node->getChildrenByTagName('data1'); 
    my $value = $node->getChildrenByTagName('data2'); 
    $hash{$key} = $value; 
} 

後來,我用這哈希生成基於一個事實,更多的數據,如果孩子節點DATA2存在或不存在。

我使用ne操作者假設在%hash該數據是字符串的鍵值對,並且當data2不存在時,Perl的插入空間中的散列值(I已打印該散列並發現,只有空間被打印爲一個值)

但是,我結束了以下編譯錯誤。

Operation "ne": no method found, 
     left argument in overloaded package XML::LibXML::NodeList, 
     right argument has no overloaded magic at filename.pl line 74. 

我該如何解決這個問題?當我們有時一個節點不會在那裏時,什麼是最好的數據結構來存儲這些數據?

回答

3

要實現的第一件事是$value是一個XML :: LibXML :: NodeList對象。它在打印時看起來只是一個字符串,因爲它的字符串化過載。你可以用ref $value進行檢查。

隨着my $value = $node->getChildrenByTagName('data2');$value總是是一個NodeList對象。它可能是一個空的NodeList,但你總是會得到一個NodeList對象。


您的XML :: LibXML版本已過時。您的XML :: LibXML :: NodeList版本沒有字符串比較重載,並且默認情況下,Perl不會「後備」爲其他字符串運算符(如ne)使用字符串化。 I reported this bug back in 2010,它是fixed in 2011 in version 1.77

升級XML :: LibXML,問題就會消失。

作爲解決方案,您可以通過引用NodeList對象來強制進行字符串化。

if("$nodelist" ne "foo") { ... } 

但確實,更新該模塊。在這方面做了很多工作。

的Perl中的散列

這是一個NodeList對象字符串化插入空間的值。我從空的NodeList中得到一個空字符串。你可能會得到一箇舊的bug。

您還可以檢查$value->size以查看NodeList是否爲空。

+0

這就解釋了它。我將不得不更新我的libXML第三方庫。 – Recker

+0

@Recker,它是需要更新的Perl模塊,而不是libxml庫 – ikegami