XML adatkezelés 11. témakör Az nyelv alapjai ME GEIAL dr Kovács Lászl szló célja egy imperatív lekérdező nyelv biztosítása SQL XPath XSLT (nem XML) XDM Forrás XML processzor Eredmény XML 1
jellemzői -- W3C szabvány 2007 óta -- halmazorientált -- gazdag kifejezőerő -- XML bemeneti adat és XML kimeneti adat -- a parancsok nem XML formátumban adottak -- XPath alapú -- SQL-hez hasonló (de laza a kapcsolat) -- XSLT vetélytársa -- procedurális elemeket is tartalmaz minta for $x in doc('xx9.xml')/adatbazis/autok/auto where $x/ar < 222 order by $x/tipus descending <car> $x/@rsz $x/tipus/text() $x/ar ll:felez($x/ar)</car> <adatbazis> <autok> <auto rsz= > <tipus> opel</tipus> <ar>214 </ar> </auto> </autok> <emberek> </emberek> </adatbazis> <car rsz=> opel 214 107 </car> 2
feldolgozás váza XML alapadat parsing előfeldolgozás infoset validation XMLSchema post-schema validation infoset tree generation XDM lekérdezés végrehajtás feldolgozás váza XML alapadat előfeldolgozás parsing műveleti gráf statikus elemzés OS kontexus meghatározás kontexus leíró külső dinamikus elemzés modulok betöltése névfeloldás, normalizálás normalizált műveleti gráf 3
feldolgozás váza előfeldolgozás statikus elemzés műveleti lépések meghatározás kifejezések kiértékelés kimenti atomok eredmény előállítás dinamikus elemzés XML sorosítás XDM lekérdezés struktúrája (FLOWER) FOR elem LET elem ORDER BY elem WHERE elem RETURN elem : ciklus : értékadás : rendezés : szelekció : projekció for $x in doc('xx9.xml')/adatbazis/autok/auto where $x/ar < 222 order by $x/tipus descending GEIAL <car> Kovács László $x/@rsz $x/tipus/text() $x/ar ll:felez($x/ar)</car> 4
XPath-ra épülő kifejezések: nyelvi alapok - element() : bármely csomópont - element(a,b) : A nevű, B típusú csomópont - attribute(a,b) : A nevű, B típusú elemjellemző - text() : szövegcsomópont - node() : bármely csomópont - node() * : bármely csomópont akárhányszor - attribute() + : egy vagy több elemjellemző - element(*,b)? : opcionális B típusú elem - derives-from(a,b) : A típus a B-ből származik-e - item() : csomópont vagy érték - comment() : megjegyzés XPath-ra épülő kifejezések: nyelvi alapok szekvencia : (1,2,5,,8) tartomány : 1 to 6 érték összehasonlítás : eq ne lt le gt ge szekvencia, tartomány összehasonlítás: =,<, >,!= csomópont összehasonlítás : is << >> kifejezés megadása kiértékelésre: kif statikus eredmény XML struktúra felépítése: <nev> <auto> Fiat, melynek ara 2+4 </auto> 5
Egyértékű változó LET $v := ertek RETURN kifejezes let $x := ( a, b, s ) <a> $x </a> let $x := ( a, b, s ) <a> $x </a> Többértékű változó FOR $v IN lista RETURN kifejezes A változó végigfut a megadott halmaz elemein Implicit ciklus for $x in ( a, b, s ) <a> $x </a> 6
XML dokumentum kijelölés fn:doc(file-specifikáció) Részfa kijelölés (XPath) fn:doc(file-specifikáció)/p1/p2/ for $x in fn:doc("xx9.xml")/adatbazis/autok/auto <a> $x </a> Descartes-szorzat képzése for $x in ('a','b') for $y in ('c','d') let $z := 'e' <a> $x $y $z </a> FOR $v1 IN lista1 FOR $v2 IN lista2 LET $w1 := kifejezes1 LET $w2 := kifejezes1.. RETURN kifejezes 7
Descartes-szorzat képzése for $x in doc('xx9.xml')/adatbazis/autok/auto for $y in doc('xx9.xml')/adatbazis/emberek/ember <a> $x $y </a> let $b := doc('xx9.xml')/adatbazis for $x in $b/autok/auto for $y in $b/emberek/ember <a> $x $y </a> Descartes-szorzat képzése let $b := doc('xx9.xml')/adatbazis for $x in $b/autok/auto for $y in $b/emberek/ember <a> <car>$x/tipus/text()</car> <owner>$y/nev/text()</owner> </a> <a> <car>$x/@rsz$x/tipus/text()</car> <owner>$y/nev/text()</owner> </a> 8
Szelekcio FOR $v IN lista LET $w := kifejezes WHERE feltetel RETURN kifejezes for $x in doc('xx9.xml')/adatbazis/autok/auto where $x/ar > 222 <a> <car>$x/@rsz$x/tipus/text()</car> </a> Csomópontok létrehozása* FOR $v IN lista RETURN ELEMENT nev ertek ATTRIBUTE nevertek TEXTertek for $x in doc('xx9.xml')/adatbazis/autok/auto where $x/ar > 222 <a> element car text$x/@rsz </a> 9
Elemek rendezese FOR $v IN lista LET $w := kifejezes WHERE feltetel ORDER BY kifejezes mod RETURN kifejezes or $x in doc('xx9.xml')/adatbazis/autok/auto where $x/ar < 222 order by $x/tipus descending <a> <car> $x/@rsz $x/tipus/text() </car> </a> Minta a 200-nál drágább autok rendszáma for $v in fn:doc('xx9.xml')//auto where $v/ar>200 element eredmeny $v/@rsz Auto rendszama es a tulaj neve for $a in fn:doc('xx9.xml')//auto for $e in fn:doc('xx9.xml')//ember where $a/@tulaj eq $e/@kod element eredmeny element auto $a, element tulaj $e 10
Minta Autok rendszam es ar, ar szerint rendezve for $a in fn:doc('xx9.xml')//auto order by $a/ar element auto $a/tipus, $a/ar A 200-nal dragabb autok rendszamai rsz sorrendben for $a in fn:doc('xx9.xml')//auto where $a/ar > 200 order by $a/@rsz <aa> $a/@rsz </aa> Minta Auto elemek rendszam tartalommal for $a in fn:doc('xx9.xml')//auto element auto text$a/@rsz Autokhoz olyan elemek, melynek neve a rendszam erteke, tartalma: tipus, jellemzoje: ar for $a in fn:doc('xx9.xml')//auto element $a/@rsz attribute a $a/ar, text$a/tipus 11
Gyökérelem létrehozása a ciklus köré <elem> FOR $v IN lista RETURN kifejezes </elem> <adatok> for $a in fn:doc('xx9.xml')//auto element car $a/tipus </adatok> Feltételes végrehajtás FOR $v IN lista RETURN IF (kifejezes) THEN kifejezes ELSE kifejezes for $x in doc('xx9.xml')/adatbazis/autok/auto <a> <car> $x/@rsz $x/tipus/text() $x/ar if ($x/ar>151) then 'sok' else 'keves' </car> </a> 12
<a> for $x in doc('xx9.xml')/adatbazis/autok/auto <car> $x/@rsz if ($x/ar>151) then 'sok' else 'keves'</car> </a> <adatok> for $a in fn:doc('xx9.xml')//auto element car text $a/tipus, element ar if ($a/ar/@valuta eq 'USD') then text 250*$a/ar else text $a/ar </adatok> Gyári függvények doc() uppercase() substring() max() min() avg() sum() count() distinct-values() every $x in kif1 satisfies kif2 some $x in kif1 satisfies kif2 13
Autotipusok es autoik <adatok> for $t in fn:distinct-values( fn:doc('xx9.xml')//auto/tipus ) element tipus attribute tip $t, element autok for $a in fn:doc('xx9.xml')//auto where $a/tipus eq $t element auto $a/@rsz </adatok> <adatok> for $t in fn:distinct-values( fn:doc('xx9.xml')//auto/tipus ) element tipus attribute tip $t, attribute db count( for $a in fn:doc('xx9.xml')//auto where $a/tipus eq $t element auto $a/@rsz ) </adatok> Tipusok es darabszamuk 14
Gyári függvények for $x in doc('xx9.xml')/adatbazis/autok <atlagar> fn:avg($x//ar) </atlagar> <db> fn:count( for $x in doc("xx9.xml")/adatbazis/autok/auto where $x/ar > 211 $x ) </db> Gyári függvények Akiknek nincs autoja for $e in fn:doc('xx9.xml')//ember let $a := fn:doc('xx9.xml')//auto[@tulaj = $e/@kod] where fn:count($a) eq 0 element ember $e/nev for $e in fn:doc('xx9.xml')//ember where not (some $x in fn:doc('xx9.xml')//auto satisfies $e/@kod eq $x/@tulaj) element ember text $e/nev 15
Saját függvények létrehozása DECLARE NAMESPACE prefix=kifejezes; DECLARE FUNCTION prefix:fnev ($p1 AS t1,..) AS rtip utasitasok RETURN kifejezes Saját függvény declare namespace ll="http:me.kl"; declare function ll:felez($x as xs:decimal) as xs:decimal let $c:=2 $x div $c ; for $x in doc('xx9.xml')/adatbazis/autok/auto where $x/ar < 222 order by $x/tipus descending <car> $x/@rsz $x/tipus/text() $x/ar ll:felez($x/ar)</car> 16
Elso n szam osszege declare namespace ll="http:me.kl"; declare function ll:ossz($r as xs:integer) as xs:integer let $x := 1 ( if ($r > 0) then $r + ll:ossz($r -1) else 0 ) ; let $x := 5 <ered> ll:ossz($x)</ered> A függvény argumentuma és visszatérési értéke lehet csomópont típusú is declare function local:order-value ($po as element(purchase-order)) as xs:double sum($po/order-item/(@price * @quantity)) ; node() element() element(nev) attribute() attribute(nev) Any node Any element node Any element with name nev 17
declare namespace ll="http:me.kl"; declare function ll:felez($x as element(auto)) as element(mind) let $c:=2 element mind $x/tipus ; for $x in doc('xx9.xml')/adatbazis/autok/auto where $x/ar < 222 order by $x/tipus descending <car> ll:felez($x)</car> Az exp(x) kiszamitasa Rekurziv algoritmus exp(x) = 1 + exp2(x, 1, s, n, m) exp2(x, i, s, n, m) = (s*x)/(n*i) + exp2(x,i+1,s*x, n*i, m), ha i<m 18
Az exp(x) kiszamitasa declare function ll:exp($x as xs:decimal) as xs:decimal let $s := 1 let $n := 1 let $m := 10 let $i:=1 1 + ll:exp2($x,$i,$s,$n,$m) ; let $x := 2 <ered> ll:exp($x)</ered> Az exp(x) kiszamitasa declare function ll:exp2($x as xs:decimal, $i as xs:integer, $s as xs:integer, $n as xs:integer, $m as xs:integer) as xs:decimal let $us := $s*$x let $un := $n*$i ( if ($i < $m) then $us div $un + ll:exp2($x,$i+1,$us,$un,$m) else $us div $un ) ; 19