Expressions XPath

Expressions XPath

Nous allons à nouveau utiliser xmllint. Utilisez l'option --shell (et le manuel d'aide man xmllint). Vous entrez dans un interprète Xpath qui vous permettra de vous déplacer dans votre document. La commande xpath exprXpath vous permet d'évaluer une expression XPath, et cd exprXPath de vous déplacer dans le document XML. Utilisez la commande help pour connaître toutes les commandes disponibles.

On se sert maintenant du document Grand Prix.

Ecrire les expressions XPath qui retournent (le noeud contextuel est la racine) :

  1. tous les noeuds éléments de nom attr
    descendant::attr
    ou
    //attr
  2. tous les noeuds éléments qui ont un attribut order
    descendant::*[@order]
  3. le fils de nom attr de cast
    descendant::cast/attr
  4. le premier fils de nom name d'un Composer
    descendant::Composer/name[position()=1]
    ou
    descendant::Composer/name[1]
  5. le noeud attribut de nom Crew (attribut de filmography)
    descendant::filmography/@Crew
  6. le quatrième fils de filmography
    descendant::filmography/*[4]
  7. les quatre premiers fils de filmography
    descendant::filmography/*[position()<=4]
  8. les noeuds attributs de nom order
    descendant::*/@order
  9. le noeud contextuel étant maintenant remainder, retournez le sous-arbre de racine Editor
    parent::node()/Editors
  10. le nombre d'acteurs de premier plan (cité dans cast)
    count(//cast/name)
  11. le nombre total de comédiens (cast, remainder, miscellaneous)
    count(//cast/name)+count(//remainder/name)+count(//Miscellaneous/name)
    ou
    count(//Editors/following::name)
  12. une chaîne de caractères présentant le film : titre (année) - réalisateur
    concat(//title," (",//year,") - ",//Director/name)
  13. l'ensemble des intervenants dont le prénom est Bob
    //name[starts-with(.,"Bob ")]

Sur le document Spaghetti à la Bolognaise, utilisez l'interprète XPath de xmllint pour obtenir les éléments suivants :

  1. ensemble des éléments ingredient
    //ingredient
  2. les commentaires de la partie preparation
    //preparation//comment()
  3. les deux derniers commentaires du document
    //comment()[position()>= last()-1]
  4. quel est le nombre de noeuds suivant la première phase de préparation ?
    count(//phase[1]/following::node())
  5. quels sont les noeuds suivants la fiche technique ? les noeuds précédents ?
    //fiche-technique/following::node()
    //fiche-technique/preceding::node()
  6. combien y-a-t-il de phases de préparation dont le texte contient moins de 180 caractères ?
    count(//phase[string-length(.) >= 180])

Vous trouverez en annexe un document de recettes de cuisine danoise.

Donnez les expressions XPath qui retournent (à partir du noeud racine, sauf indication contraire) :

  1. les noeuds éléments dont le nom est preparation;
    //preparation
  2. les ingrédients de la tarte à la ricotta (ricotta pie) dont l'unité de mesure est la petite cuiller (teaspoon);
    /descendant::recipe[title="Ricotta Pie"]/descendant::ingredient[@unit="teaspoon"]
  3. le nombre d'étapes de préparation de la recette de la tarte à la ricotta ;
    count(/descendant::recipe[title="Ricotta Pie"]/descendant::step)
  4. le nom du quatrième ingrédient de la garniture (filling) de la tarte à la ricotta.
    /descendant::recipe[title="Ricotta Pie"]/ingredient[@name="filling"]/ingredient[4]
  5. à partir du noeud ingredient de la ricotta (name="ricotta cheese"), les autres ingrédients de le recette de la tarte à la ricotta dont la quantité est supérieure ou égale à 2;
    ancestor::recipe/descendant::ingredient[@amount >= 2]
  6. tous les titres des recettes dont le nombre de calories est inférieure à 1200;
    /descendant::recipe[nutrition/@calories < 1200]/title
  7. le nom du quatrième ingrédient de la pâte (dough) de la tarte à la ricotta;
    /descendant::ingredient[@name="dough"]/ingredient[4]
  8. toutes les étapes (step) qui contiennent le mot bake.
    /descendant::step[contains(text(),"bake")]
  9. le nombre de calories moyen d'une recette.
    sum(//@calories) div count(//recipe)
  10. le nombre moyen d'oeufs par recette (attention, il s'agit de retrouver les ingrédients qui contiennent le mot eggs).
    sum(//ingredient[contains(@name,"egg")]/@amount) div count(//recipe)

Vous trouverez en annexe un document listant des titres de bandes dessinées.

Donnez les expressions XPath qui retournent (à partir de la racine /) :

  1. le troisième commentaire
    //comment()[3]
  2. les titres des bandes dessinnées dont le résumé contient le mot village (on veut le texte du titre)
    //bd/titre[contains(../resume,"village")]/text()
  3. les titres des albums de la série Le retour à la terre
    //bd[../titreserie="Le retour à la terre"]/titre
  4. les titres des albums qui ne font pas partie d'une série
    //*[name(.)!="serie"]/bd/titre/text()
  5. les noms des différents illustrateurs (on ne veut pas de répétition)
    //personne[@id = //illustrateur/@ref]/nom/text()
  6. le nombre moyen d'albums publiés par auteur
    count(//bd) div count(//personne[@id=//auteur/@ref])
  7. toutes les zones de texte, commentaires ou attributs qui contiennent le nom Sattouf
    //text()[contains(.,"Sattouf")] | //comment()[contains(.,"Sattouf")] | //attribute::*[contains(.,"Sattouf")]
    

Reprenez le document oiseaux.xml.

Donnez les expressions XPath qui retournent (à partir de la racine /) les informations suivantes. Attention! Il y en a deux qui ne peuvent pas être retournées par une expression XPath. Lesquelles ?

  1. toutes les zones de texte qui contiennent le mot terril
    //text()[contains(.,"terril")]
  2. tous les noeuds éléments de nom espece qui contiennent une photo d'au moins 90 pixels de large et 70 pixels de haut;
    //espece[number(photo/@width)>=90 and number(photo/@height)>=70]
  3. toutes les fiches d'observation qui contiennent une observation d'un Turdidé
    //fiche-observations[espece/famille="Turdidés"]
  4. les noms de tous les ornithologues
    //@auteur
  5. le nom de la deuxième espèce observée dans la troisième fiche
    //fiche-observations[3]/espece[2]/@nom
  6. la taille moyenne en pixels des images proposées (la taille d'une photo est donnée par sa largeur multipliée par sa hauteur)
    Erreur! ne peut pas être exprimé en XPath. Pour cela il faudrait une expression Xpath qui multiplie la hauteur d'une photo par sa largeur. 
    L'opération * devrait alors être à la racine de cette expression, mais on ne pourra pas avoir une expression à gauche et une expression à droite qui désignent la même image.
  7. le nombre moyen d'espèces observées pour une fiche
    (count(//espece)) div (count(//fiche-observations))
  8. les noms de lieux concernés par au moins deux fiches d'observation
    //lieu[following::lieu=.]/text()
  9. les noms de lieux concernés par au moins trois fiches d'observation
    //lieu[following::lieu=.][preceding::lieu=.]/text()
  10. les noms de lieux concernés par au moins quatre fiches d'observation
    Erreur! ne peut pas être exprimé en XPath.
  11. retournez le nombre d'espèces observées dans la troisième fiche après la deuxième espèce de cette fiche
    //fiche-observations[3]/espece[2]/following-sibling::espece/@nom
  12. retournez les noms des familles de toutes les fiches suivant l'observation des cinq loriots pour lesquelles on a vu plus de 10 individus dans une même observation.
    //fiche-observations/espece[@nom="loriot"]/following::famille[number(../@nbre)>10]/text()