Perl XML:: LibXML: findnode vs. findvalue vs. find - Quelle est la différence?
j'utilise XML::LibXML
, et j'ai simplement besoin de compter les noeuds spécifiés par une expression XPath.
L'utilisation de l'une ou l'autre des deux premières lignes de code ci-dessous donne ce que je cherche. Je peux utiliser le count
fonction XPath avec l'une ou l'autre findvalue
ou find
mais pas findnodes
(oui, je sais, parce qu'elle renvoie une liste).
my $node_cnt = $dom->findvalue("count($xpath_str)"); # WORKS!
my $node_cnt = $dom->find("count($xpath_str)"); # WORKS!
my @node_cnt = $dom->findnodes("count($xpath_str)"); # count doesn't work!
ce qui m'amène à une question générale lancinante: Quelle est la différence entre les trois types? Dans le de la documentation, il dit:
$string = $node->findvalue($xpath)
$result = $node->find($xpath)
@nodes = $node->findnodes($xpath_expression)
Est-il vraiment une différence entre l'argument
$xpath_expression
vs$xpath
dans la documentation?pour les deux retournant un scalaire, Quelle est la différence?
j'essaie de comprendre la signification de l'utilisation d'un type de find par rapport à l'autre - merci!
1 réponses
la différence est le type de valeur que les méthodes renvoient.
findnodes
est utilisée pour retourner une liste de nœuds. Si la méthode est appelée dans le contexte list, alors elle renvoie une liste d'objets du type approprié, tels queXML::LibXML::Element
,XML::LibXML::Text
etc. Si elle est appelée dans le contexte scalaire, elle renvoie unXML::LibXML::NodeList
objet qui contient les mêmes informations.ne peut pas être utilisé pour renvoyer une expression arbitraire, par exemple
$dom->findnodes('42')
retournera rien. Vous ne pouvez obtenir qu'une liste des noeuds de documents à partir de cette méthode.findvalue
est utilisé pour retourner un texte simple ou numérique valeur, c'est-à-dire pas un noeud XML. Si vous passez une expression XPath qui évalue à une liste de noeuds, alors elle convertit cette liste en texte en concaténant tous les noeuds de texte dans n'importe lequel des noeuds de la liste.find
peut rapporter n'importe quoi. Il retournera une liste de noeuds comme unXML::LibXML::NodeList
objet, une valeur numérique comme unXML::LibXML::Number
objet, une chaîne littérale comme unXML::LibXML::Literal
objet etc. Contrairement àfindnodes
,toujours renvoie une seule valeur scalaire, même si elle est appelée dans le contexte list.je n'ai jamais choisi d'utiliser
find
. Il semble qu'il est prévu comme un piège tous quand vous ne savez pas quel genre de résultat à attendre.
Par exemple, vous auriez probablement eu envie d'écrire my $nrecs = $dom->findvalue('count(/root/record)')
pour obtenir le nombre d'enregistrements dans la racine élément. $nrecs
serait une valeur numérique perl simple.
d'autre part, pour obtenir un liste de ces enregistrements, vous utiliseriez my @records = $dom->findnodes('/root/record')
. Maintenant @records
contient un nombre de XML::LibXML::Element
objets.
dans vos exemples,
my $node_cnt = $dom->findvalue("count($xpath_str)"); # WORKS!
jeux $node_cnt
à un nombre Perl simple, alors que celui-ci
my $node_cnt = $dom->find("count($xpath_str)"); # WORKS!
configure $node_cnt
XML::LibXML::Number
de l'objet, ce qui arrive à stringify (lors de l'impression) de la même manière que la précédente déclaration. Prouver vous-même en impression print ref $node_cnt
dans les deux cas.
my @node_cnt = $dom->findnodes("count($xpath_str)"); # count doesn't work!
échoue parce que le XPath count
évalue à un nombre, pas à un noeud XML (il ne fait pas partie de L'arborescence XML). Il n'y a aucun moyen de convertir des nombres en noeuds, donc le résultat est une liste vide. Si c'était l'inverse, et nous avions appelé findvalue
sur une expression évaluée à une liste de noeuds, alors il y a une façon vaguement sensible de convertir en valeur texte et findvalue
fait de son meilleur et renvoie la concaténation de tous les nœuds de texte contenue par les noeuds de la liste.