I.
Wprowadzenie do  języków zapytań (1)
II.
Wprowadzenie do  języków zapytań (2)
III.
Pojęcia obiektowości w bazach danych (1)
IV.
Pojęcia obiektowości w bazach danych (2)
V.
Podstawy semantyczne języków zapytań
VI.
Modele składu obiektów
VII.
Stos środowisk, rezultaty zapytań, funkcja nested
VIII.
Język SBQL (Stack-Based Query Language) (1)
IX.
X.
Dalsze własności SBQL
XI.
Operatory order by i group by
XII.
Przetwarzanie struktur nieregularnych
  Wstęp
  1. Metody przetwarzania nieregularności w danych
  2. Nieregularne dane w modelach składu
  3. Konstrukcje w języku zapytań obsługujące dane nieregularne
  4. Możliwości zewnętrznych złączeń
  5. Problem z fałszywym wiązaniem
  6. Wartości domyślne
  Podsumowanie
  Zadania
XIII.
Rozszerzenie języków zapytań o konstrukcje imperatywne
XIV.
Procedury, procedury funkcyjne, metody, reguły zakresu
XV.
Parametry procedur i metod, procedury rekurencyjne, optymalizacja poprzez modyfikację zapytań

 

1. Metody przetwarzania nieregularności w danych

To, co jest nieadekwatne i frustrujące w istniejących koncepcjach i teoriach dotyczących wartości zerowych i danych półstrukturalnych, można określić jako "niezgodność zakresu". Jest to niezgodność pomiędzy funkcjonalnością koncepcji, teorii, języka lub modelu dotyczącą tego problemu a funkcjonalnością programistyczną, która musi obowiązywać wartości zerowe lub dane półstrukturalne. W typowych przypadkach pierwszy zakres obejmuje pewną algebrę, struktury danych lub pewien uproszony język zapytań. Trudno jednak sobie wyobrazić, aby jakikolwiek system ograniczał swą funkcjonalność wyłącznie do przechowywania i prostego odpytywania danych. Prawdziwy zakres nieregularności w danych jest więc znacznie szerszy i obejmuje wszystkie cechy środowiska programistycznego, z którym będzie miał do czynienia programista aplikacyjny. Nieregularności w danych muszą być uwzględnione nie tylko przez język zapytań, lecz przez kompletne środowisko do programowania aplikacji, włączając operacje aktualizacyjne, zdania imperatywne, procedury, funkcje, klasy, typy, metody itd. Obowiązuje przy tym zasada korespondencji, która żąda spójności wprowadzanych opcji z dotychczas wprowadzonymi opcjami. Niestety, kolejni autorzy proponujący rozwiązania dla danych półstrukturalnych i dla XML orientują się wyłącznie na pierwszy z wymienionych zakresów, i wyraźnie nie znają lub nie doceniają zasady korespondencji. Ta właśnie sprzeczność pomiędzy zakresem danej teorii a zakresem wymaganym przez praktykę stała się przyczyną faktu, że praktycznie całość akademickiego nurtu poświęconego wartościom zerowym okazała się bezwartościowa dla zastosowań praktycznych i dla dalszych badań.

Klasycznym rozwiązaniem zastosowanym w zanurzonym SQL jest metoda "ukrytego bajtu" (hiddden byte). W tabelach relacyjnych oraz w SQL wartość zerowa jest widoczna explicite i obsługiwana przez odpowiednie konstrukcje SQL. Inaczej jest, gdy tabela zwrócona przez SQL jest przetwarzana przez język programowania, np. C. W tym przypadku każda kolumna tabeli, w której może pojawić się wartość zerowa, jest implementowana jako dwie kolumny. Pierwsza z nich przechowuje normalną wartość danego atrybutu lub wartość przypadkową (nieistotną), jeżeli w tym miejscu ma być NULL. Druga kolumna przechowuje flagę posiadającą dwa stany: "nie jestem NULL" lub "jestem NULL". Na podstawie tej flagi programista może zbadać, czy w pierwszej wymienionej kolumnie jest wartość mająca znaczenie, czy też jest to (w przypadku "jestem NULL") wartość przypadkowa, nie podlegająca przetwarzaniu. Ten sposób jest dalej rozszerzany na całe środowisko programistyczne: jeżeli wartość krotki może być NULL, to programista musi powołać w języku programowania dwie zmienne: jedną na wartość, drugą na wspomnianą flagę. Dzięki temu stało się możliwe przetwarzanie wartości zerowych w klasycznym języku programowania z mocną statyczną kontrolą typów.

Opisany wyżej sposób nie nadaje się bezpośrednio do zastosowania dla danych półstrukturalnych, gdyż wprowadzane tam nieregularności w danych są znacznie większe niż to miało miejsce w przypadku relacyjnych tabel z wartościami zerowymi. Zakładając, że zbudujemy język zapytań do wyszukiwania w danych półstrukturalnych, przetwarzanie wyników zapytań przez środowisko programistyczne może być zrealizowane na jeden z trzech sposobów:

  • System typów danego uniwersalnego języka programowania (np. Java) przystosujemy w taki sposób, aby każdy wynik zapytania można byłoby potraktować jako poprawną wartość pewnego znanego w danym momencie typu. Sposób ten jest mało realny ze względu na znaczne trudności koncepcyjne i implementacyjne dla programisty aplikacyjnego.

  • "Spłaszczenie" hierarchicznej struktury zwracanej przez zapytanie. Przykładem takiego spłaszczenia jest potraktowanie całości wyniku wyszukiwania (łącznie z nazwami danych) jako ciągu bajtów a la XML. Podobnym sposobem jest reprezentacja danych półstrukturalnych w dwóch lub więcej tabelach relacyjnych, gdzie wszystkie nazwy danych są trzymane jako stringi obok wartości oraz istnieje specjalna tabela reprezentująca hierarchię danych. Rys.66 ilustruje takie spłaszczenie dla przypadku, gdy wynikiem zapytania jest dokument XML.

  • Zbudowanie nowego kompletnego środowiska programistycznego przystosowanego do przetwarzania danych półstrukturalnych. Sposób ten oznacza konieczność opracowania własnego języka programowania, co jest raczej trudne w warunkach szerokiego środowiska komercyjnego, ale całkowicie możliwe w ramach prototypu lub własnego projektu.


W dalszych podrozdziałach przeprowadzimy dyskusję, jak taki język programowania mógłby wyglądać i co jest potrzebne, aby go zdefiniować. Material ten pochodzi z prac [Subi96a, Subi98b].

Copyrights © 2006 PJWSTK
Materiały zostały opracowane w PJWSTK w projekcie współfinansowanym ze środków EFS.