Datenbanken:Übung 8
Aus Tudwiki
Inhaltsverzeichnis
Aufgabe 2
Formulieren Sie eine XQuery-Anweisung, welche alle Bücher ermittelt, die (mindestens) einen Autor mit dem Nachname "Lehner" aufweisen.
<lehner-buecher> { for $buch in doc("bib.xml")//book where some $author in $buch/author satisfies ($author/lastname = "Lehner") return $buch/title } </lehner-buecher>
Aufgabe 3
Für eine Preisübersicht sollen die Bücher nach dem Preis sortiert dargestellt werden. Geben Sie einen XQuery-Ausdruck an, der den Titel und den Preis der Bücher aufsteigend nach dem Preis sortiert ausgibt.
<buecher> { for $buch in doc("bib.xml")//book order by xs:decimal($buch/price) return <buch> { $buch/title } { $buch/price } </buch> } </buecher>
- (a) Wie kann die Position von Bücher ohne Preis beeinflusst werden?
order by xs:decimal($buch/price) empty least
oder
order by xs:decimal($buch/price) empty greatest
- (b) Was bewirkt die Angabe von stable bei der Sortierung?
stable order by xs:decimal($buch/price)
Wenn es zwei Bücher gibt mit dem gleichen Preis, dann wird die Reihenfolge des Dokuments behalten.
Aufgabe 4
Zur Unterstützung der Kaufentscheidung sollen die Bücher in teuere und billige Bücher eingeteilt werden. Teuere Bücher sind solche, deren Preis über dem durchschnittlichen Preis aller Bücher liegt, alle anderen Bücher sind billige Bücher. Formulieren Sie eine XQuery-Anweisung, die den Titel und den Preis sowie die Information, ob es sich um ein teures oder billiges Buch handelt, ausgibt.
<buecherliste> { let $input := doc("bib.xml") let $schnitt := avg($input//book/price) for $buch in $input//book return if (xs:decimal($buch/price) > $schnitt) then <teuer titel="{$buch/title}" preis="{$buch/price}" /> else <billig titel="{$buch/title}" preis="{$buch/price}" /> } </buecherliste>
Alternative Lösung
<bib> { let $schnitt:=fn:avg(doc("bib.xml")//price) for $x in doc("bib.xml")//book return if (xs:decimal($x/price)>$schnitt) then ( <book typ="teuer"> {$x/title} {$x/price} </book> ) else ( <book typ="billig"> {$x/title} {$x/price} </book> ) } </bib>
Aufgabe 5
Um den Absatz zu steigern, sollen Bücherpakete aus Büchern mit gemeinsamen Autoren angeboten werden. Geben Sie einen XQuery-Ausdruck an, der Bücherpaare, also eine Liste mit jeweils zwei Buchtiteln, die einen gemeinsamen Autor aufweisen, ausgibt.
<buecherpaare> { let $books := doc("bib.xml")//book for $a in $books, $b in $books where $a/author = $b/author and $a/title < $b/title return <buchpaar> {$a/title} {$b/title} </buchpaar> } </buecherpaare>
Alternative Lösung
<buecherpaare> { for $b1 in doc("bib.xml")//book for $b2 in doc("bib.xml")//book for $author in $b1/author for $author2 in $b2/author return if(($author=$author2) and ($b1/title<$b2/title)) then ( <paar> {$b1/title} {$b2/title} {$author} </paar> ) else () } </buecherpaare>
Aufgabe 6
Formulieren Sie einen XQuery-Ausdruck, der alle Bücher ausgibt (Buchtitel und Anzahl Autoren), die von mehr als zwei Autoren geschrieben wurden.
<buecherliste> { for $buch in doc("bib.xml")//book let $autoren := count($buch/author) where $autoren > 2 return <buch> {$buch/title} <anzahl_autoren>{$autoren}</anzahl_autoren> </buch> } </buecherliste>
Aufgabe 7
Zu einigen in bib.xml genannten Autoren sind in address.xml Angaben zum Wohnort hinterlegt. Gesucht sind zu jedem Buch der Autor und dessen Wohnort.
- (a) Geben Sie eine entsprechende XQuery-Anweisung an, die auch Bücher ausgibt, für die es keine Adressinformationen über die Autoren gibt (Outer Join Semantik)
<buecherliste> { let $bucher := doc("bib.xml")//book let $adressen := doc("address.xml")//address for $buch in $bucher return <buch> {$buch/title} { for $adresse in $adressen where $buch/author/firstname = $adresse/firstname and $buch/author/lastname = $adresse/lastname return <author name="{$adresse/lastname}" city="{$adresse/city}" /> } </buch> } </buecherliste>
- (b) Passen Sie diesen XQuery-Ausdruck so an, dass nur die Bücher erscheinen, für die zumindest teilweise Adressinformationen über die Autoren bekannt sind (Inner Join Semantik)
<buecherliste> { let $bucher := doc("bib.xml")//book let $adressen := doc("address.xml")//address for $buch in $bucher for $adresse in $adressen where $buch/author/firstname = $adresse/firstname and $buch/author/lastname = $adresse/lastname return <buch> {$buch/title} <author name="{$adresse/lastname}" city="{$adresse/city}" /> </buch> } </buecherliste>
Aufgabe 8
Gegeben ist eine Übersicht aus Büchern und Zeitschriften (publications.xml).
- (a) Geben Sie einen XQuery-Ausdruck an, der den durchschnittlichen Preis für die beiden Kategorien books und magazins ausgibt.
<bib> { for $bib in doc("publications.xml")//bib/* let $preis := $bib/*/price return <preis kategorie="{fn:node-name($bib)}"> {avg($preis)} </preis> } </bib>
- (b) Formulieren Sie einen weiteren XQuery-Ausdruck, der die Autoren absteigend nach der Anzahl ihrer Bücher (nicht Zeitschriften) ausgibt.
<autorenliste> { for $autor in fn:distinct-values(doc("publications.xml")//author) let $anzahl := count(doc("publications.xml")//book[author = $autor]) order by $anzahl descending return <autor> <name>{$autor}</name> <anzahl_buecher>{$anzahl}</anzahl_buecher> </autor> } </autorenliste>