Kapitola 20: AI v praxi 2 – Zpracování přirozeného jazyka (NLP)

Jak naučit počítač rozumět lidské řeči? To je svatý grál umělé inteligence. Siri, Alexa nebo Google Translate musí umět rozložit větu na kousky, pochopit, co je podmět, co přísudek a jak to spolu souvisí. Prolog je pro tento úkol jako stvořený. Má v sobě zabudovaný nástroj pro definování gramatiky, který funguje jako pravidla pro skládání LEGO kostiček.

20.1 Gramatika DCG – Pravidla jazyka

Prolog používá speciální zápis zvaný DCG (Definite Clause Grammar). Místo :- používáme šipku -->. Ta říká: "Tohle se skládá z tamtoho."

DCG (DEFINITE CLAUSE GRAMMAR) Speciální syntaxe v Prologu pro psaní gramatických pravidel. Umožňuje snadno definovat strukturu jazyka (nebo jakýchkoli sekvencí dat).

Příklad věty: "Kočka loví myš."

Gramatický strom
Obrázek 20.1: Gramatický strom pro větu "Kočka loví myš". Ukazuje, jak se věta rozkládá na menší části.
% Gramatická pravidla
veta --> podmetna_cast, prisudkova_cast.
podmetna_cast --> clen, podstatne_jmeno.
prisudkova_cast --> sloveso, podmetna_cast.

% Slovník (Terminály)
clen --> [ta].
clen --> [tu].
podstatne_jmeno --> [kocka].
podstatne_jmeno --> [mys].
sloveso --> [lovi].

20.2 Použití: Čtení i psaní

K práci s gramatikou používáme vestavěný predikát phrase(Gramatika, Veta).

1. Analýza (Parsing): Je to správná věta?

?- phrase(veta, [ta, kocka, lovi, tu, mys]).
true.

?- phrase(veta, [kocka, ta, lovi]).
false.

2. Generování: Vymysli větu!

Tohle je ta největší magie. Můžeme nechat proměnnou prázdnou a Prolog vygeneruje všechny platné věty, které podle naší gramatiky existují.

?- phrase(veta, X).
X = [ta, kocka, lovi, ta, kocka] ;
X = [ta, kocka, lovi, ta, mys] ;
X = [ta, kocka, lovi, tu, kocka] ...

20.3 Pokročilá gramatika: Shoda podmětu s přísudkem

Čeština je složitá. Nemůžeme říct "Kočky loví" (množné číslo) a "Kočka loví" (jednotné číslo) se stejným slovesem, pokud se tvar liší. Prolog umí hlídat gramatickou shodu pomocí argumentů v gramatice.

% Přidáme argument 'Cislo' (jednotne/mnozne)
veta(Cislo) --> podmetna_cast(Cislo), prisudkova_cast(Cislo).

podmetna_cast(jednotne) --> [kocka].
podmetna_cast(mnozne)   --> [kocky].

prisudkova_cast(jednotne) --> [lovi]. % Kočka loví
prisudkova_cast(mnozne)   --> [lovi]. % Kočky loví (zde je to stejné, ale...)
prisudkova_cast(jednotne) --> [spi].  % Kočka spí
prisudkova_cast(mnozne)   --> [spi].  % Kočky spí (krátké i)

Díky unifikaci proměnné Cislo Prolog zajistí, že pokud vybereme podmět v jednotném čísle, musí být i přísudek v jednotném čísle.

Klíčový koncept: Obousměrnost

V Prologu gramatika neslouží jen k kontrole (rozumím tomu?), ale i k tvorbě (řekni něco!). Stejný kód funguje oběma směry. To je v jiných jazycích velmi obtížné naprogramovat.

Otázky k zamyšlení

  1. Proč píšeme slova do hranatých závorek (např. [kocka])? (Protože DCG pracuje se seznamy slov).
  2. Jak byste rozšířili gramatiku o přídavná jména (např. "ta černá kočka")? Kam byste vložili pravidlo pro přídavné jméno?
  3. Co by se stalo, kdybychom měli ve slovníku tisíc slov? Jak by to ovlivnilo generování vět?

🧪 Laboratoř: Básník Prolog