OttoQL

OttoQL

OttoQL ist eine universelle Abfragesprache für Tabellen und Dokumente, die zunächst für XML implementiert wurde. Sie zeichnet sich durch eine besonders einfache Syntax (Schreibweise) aus. Die Operationen werden in der Regel nacheinander auf alle entsprechenden Tupel bzw. Subtupel angewandt. Im folgenden Programm ist ein XML-Dokument durch eine Tabelle gegeben:

Inhaltsverzeichnis

BMI-Beispiel in OttoQL

<<L(NAME,      GROESSE,L(ALTER, GEWICHT))::
    Klaus      1.68      18     61
                         30     65  
                         56     80
    Rolf       1.78      40     72
    Kathi      1.70      18     55 
                         40     70
    Valerie    1.00       3     16
    Viktoria   1.61      13     51
    Bert       1.72      18     66
                         30     70 >>
mit NAME: ALTER>20
ext BMI:=(GEWICHT div GROESSE**2)
gib BMIDUR,M(ALTER,BMIDUR,B(BMI,NAME)) BMIDUR:=avg(BMI)
round 2

Es ist auch ohne entsprechende Tags ersichtlich, dass der Satz (das Tupel) für Klaus mit der 80 endet und dass Klaus 3 Subtupel besitzt. In dieser Struktur ist beispielsweise das ALTER dem NAMEn untergeordnet. Im gib-Teil wird diese Hierarchie einfach durch Angabe des gewünschten Schemas umgekehrt. Hierbei steht M für Menge, B für Multimenge und L für Liste. Als erstes wird jedoch eine Selektion (mit- oder ohne-Teil) auf die gegebene Tabelle angewandt. Hierbei werden alle Personen verworfen, die keinen ALTERs-Eintrag größer 20 besitzen. Das sind Valerie und Viktoria. Das erste Subtupel von Klaus verbleibt jedoch in der Tabelle, da durch "NAME:" ausgedrückt wird, dass nur vollständige Tupel und keine Subtupel gelöscht werden sollen. Will man nur Subtupel streichen, so ist NAME durch ALTER oder GEWICHT zu ersetzen. Folgende beiden Bedingungen selektieren in beiden Listen: mit NAME,ALTER: ALTER>20 bzw. mit ALTER>20. Durch einen ext-Teil wird eine Tabelle um eine neue Spalte erweitert (Extension). Ohne Einführung von Variablen können hierbei Spaltennamen verschiedener zueinander gehöriger Ebenen benutzt werden. Hinter dem GEWICHT wird der Body-Mass-Index eingefügt. Neben Umstrukturierungen in eine nichtrekursive DTD kann man mit dem gib-Teil auch folgende Aufgaben realisieren:

  • Sortieren (M,B) (stets nach den ersten Feldern einer Kollektion)(M-,B-: abwärts)
  • Aggregieren (simultan horizontal und vertikal) (sum, count, max, min, avg, prod, ex, all)
  • Duplikate eliminieren (M)
  • bestimmte Joins und Unions (Vereinigungen)
  • Projektionen
  • Group by und Nest
  • Unnest
  • Taggen

Die letzte Operation (round) rundet alle Zahlen, die im Ergebnis des gib-Teils stehen, auf zwei Stellen nach dem Komma. Binäre Operationen werden in OttoQL stets infix geschrieben. Damit realisiert obiges Programm folgende Anfrage: Gesucht ist der durchschnittliche BMI und der Durchschnitt pro Altersstufe aller Personen über 20. Es soll nach Alter und innerhalb einer Altersgruppe nach BMI sortiert werden. Das Ergebnis hat als Tabelle folgende Gestalt:

<<BMIDUR,M(ALTER, BMIDUR, B(BMI,  NAME))::
  23.12    18     20.98     19.03 Kathi
                            21.61 Klaus
                            22.31 Bert
           30     23.34     23.03 Klaus
                            23.66 Bert
           40     23.47     22.72 Rolf
                            24.22 Kathi
           56     28.34     28.34 Klaus>>


Ein äquivalentes Programm in XQuery hat die folgende Gestalt:

BMI-Beispiel in XQuery

let $personen:=(<PERSONEN>
 <PERSON>
   <NAME>Klaus</NAME>
   <GROESSE>1.68</GROESSE>
   <SUBTUP>
     <ALTER>18</ALTER>
     <GEWICHT>61</GEWICHT>
   </SUBTUP>
   <SUBTUP>
     <ALTER>30</ALTER>
     <GEWICHT>65</GEWICHT>
   </SUBTUP>
   <SUBTUP>
     <ALTER>56</ALTER>
     <GEWICHT>80</GEWICHT>
   </SUBTUP>
 </PERSON>
 <PERSON>
   <NAME>Rolf</NAME>
   <GROESSE>1.78</GROESSE>
   <SUBTUP>
     <ALTER>40</ALTER>
     <GEWICHT>72</GEWICHT>
   </SUBTUP>
 </PERSON>
 <PERSON>
   <NAME>Kathi</NAME>
   <GROESSE>1.7</GROESSE>
   <SUBTUP>
     <ALTER>18</ALTER>
     <GEWICHT>55</GEWICHT>
   </SUBTUP>
   <SUBTUP>
     <ALTER>40</ALTER>
     <GEWICHT>70</GEWICHT>
   </SUBTUP>
 </PERSON>
 <PERSON>
   <NAME>Walleri</NAME>
   <GROESSE>1.</GROESSE>
   <SUBTUP>
     <ALTER>3</ALTER>
     <GEWICHT>16</GEWICHT>
   </SUBTUP>
 </PERSON>
 <PERSON>
   <NAME>Viktoria</NAME>
   <GROESSE>1.61</GROESSE>
   <SUBTUP>
     <ALTER>13</ALTER>
     <GEWICHT>51</GEWICHT>
   </SUBTUP>
 </PERSON>
 <PERSON>
   <NAME>Bert</NAME>
   <GROESSE>1.72</GROESSE>
   <SUBTUP>
     <ALTER>18</ALTER>
     <GEWICHT>66</GEWICHT>
   </SUBTUP>
   <SUBTUP>
     <ALTER>30</ALTER>
     <GEWICHT>70</GEWICHT>
   </SUBTUP>
 </PERSON>
</PERSONEN>//PERSON[.//ALTER>=20])
let $bmis:=(for $p in $personen
           return <PER> {$p/NAME}
                        { for $t in $p/SUBTUP
                          return <TU> {$t/ALTER}
                                      <BMI>{$t/GEWICHT div($p/GROESSE * $p/GROESSE)}</BMI></TU>
                         }
                  </PER>)
return <results><BMIDUR>{round-half-to-even(avg($bmis//BMI),2)}</BMIDUR>
         { for $a in distinct-values($bmis//ALTER)
           order by $a
           return <AG>
                    <ALTER> {$a} </ALTER> 
                    <BMIDUR>{round-half-to-even(avg($bmis//TU
                                             [ALTER = $a]/BMI),2)}</BMIDUR>
                    { for $p2 in $bmis[.//ALTER=$a] for $b in $p2//TU[ALTER=$a]//BMI
                      order by $b,$p2/NAME
                      return<TU2><BMI>{round-half-to-even($b,2)}</BMI>{$p2/NAME}</TU2>
                    }
                 </AG>
}
</results>

Insbesondere verfügt OttoQL über Matrizenoperationen, Tupeloperationen, rekursive Erweiterungen, nutzerdefinierte Funktionen und geschachtelte Anfragen.

Datenstrukturunabhängigkeit

Die Operationen von OttoQL benötigen eine DTD (Dokumentypdefinition), da das System erkennen muss, was als Tupel und was als Kollektion aufzufassen ist. Trotzdem sind die wesentlichen Operationen von OttoQL weitestgehend unabhängig von der DTD. Obiges BMI-Programm funktioniert genauso, wenn die gegebene Tabelle flach (L(NAME,GROESSE,ALTER, GEWICHT)) oder auch anders strukturiert ist (M(GEWICHT,L(NAME,GROESSE,ALTER))). Diese Eigenschaft ist wichtig, wenn OttoQL für Suchmaschinen genutzt werden soll.

Entwicklung

Die Grundideen der wichtigsten Operationen von OttoQL finden sich bereits in der Dissertation B "Hierarchische Datenstrukturen" von Klaus Benecke. In "Strukturierte Tabellen - Ein neues Paradigma für Datenbank- und Programmiersprachen" wurden die Ideen erweitert. Allerdings findet sich in dieser Monographie noch keine Verallgemeinerung auf XML. Die vorliegende Implementation wurde zum großen Teil von Studenten der Universität Magdeburg realisiert, wobei die Studenten Andreas Hauptmann, Martin Schnabel und Dmitri Schamschurko einen besonderes großen Anteil daran hatten.

Literatur

  • Klaus Benecke, "Hierarchische Datenstrukturen", Dissertation B, Technische Universität "Otto von Guericke", Magdeburg, Mai 1987
  • Klaus Benecke, "A powerful Tool for Object Oriented Manipulation", in Object-Oriented Databases: Analysis, Design & Construction (DS-4), R.A.Meersman, W. Kent, S. Khosla (Editors), North -Holland 1991, S.95-122
  • Klaus Benecke, "Strukturierte Tabellen - Ein neues Paradigma für Datenbank- und Programmiersprachen", Deutscher Universitätsverlag, Wiesbaden 1998, ISBN 3-8244-2099-6
  • Wolfgang Lehner, Harald Schöning, "XQuery-Grundlagen und fortgeschrittene Methoden", dpunkt.verlag, Heidelberg 2004,ISBN 3-89864-266-6

Weblinks


Wikimedia Foundation.

Игры ⚽ Поможем написать реферат

Schlagen Sie auch in anderen Wörterbüchern nach:

  • OttoQL — is a universal QueryLanguage for tables and documents, which was implemented firstly for XML. It has a very simple syntax (kind of writing). The operations are applied generally sequentially on all corresponding tuples or subtuples. In the… …   Wikipedia

Share the article and excerpts

Direct link
Do a right-click on the link above
and select “Copy Link”