Algorithm Search⌘K

Proofs: Glushkov automaton

These are the human proofs of Glushkov automaton, at full length.

The Glushkov automaton accepts exactly the language of the expression full

This proof shows: correctness, termination.

Let rr be a regular expression with mm nodes and symbol leaves numbered 1,…,k1, \ldots, k from left to right, and let rˉ\bar r be the marked expression, in which leaf pp is the letter pp. For a node xx, xˉ\bar x is the marked subexpression, and pos(x)\mathrm{pos}(x) is the set of positions of the leaves below xx. Let hh be the homomorphism with h(p)=sym(p)h(p) = \mathrm{sym}(p).

Termination. The postorder walk visits each node of the finite tree once, and each visit does finitely many set operations on subsets of {1,…,k}\{1, \ldots, k\}. Lines L15 to L18 are finite. So the algorithm stops.

The computed sets. For a node xx, let N(x)N(x), First(x)\mathrm{First}(x) and Last(x)\mathrm{Last}(x) be the values set at lines L3 to L14, and let Fol(x)\mathrm{Fol}(x) be the set of pairs (p,q)(p, q) added at line L8 or line L13 while visiting xx or a node below xx. By the lines of the algorithm,

  • Fol(x)=∅\mathrm{Fol}(x) = \emptyset for a leaf xx;
  • Fol(s∣t)=Fol(s)∪Fol(t)\mathrm{Fol}(s \mid t) = \mathrm{Fol}(s) \cup \mathrm{Fol}(t);
  • Fol(st)=Fol(s)∪Fol(t)∪Last(s)×First(t)\mathrm{Fol}(st) = \mathrm{Fol}(s) \cup \mathrm{Fol}(t) \cup \mathrm{Last}(s) \times \mathrm{First}(t);
  • Fol(s∗)=Fol(s)∪Last(s)×First(s)\mathrm{Fol}(s^*) = \mathrm{Fol}(s) \cup \mathrm{Last}(s) \times \mathrm{First}(s).

Also First(x),Last(x)⊆pos(x)\mathrm{First}(x), \mathrm{Last}(x) \subseteq \mathrm{pos}(x) and Fol(x)⊆pos(x)×pos(x)\mathrm{Fol}(x) \subseteq \mathrm{pos}(x) \times \mathrm{pos}(x), by induction. At the end, Follow(p)={q:(p,q)∈Fol(r)}\mathrm{Follow}(p) = \{q : (p, q) \in \mathrm{Fol}(r)\} for p≥1p \ge 1.

Lemma 1. N(x)N(x) is true if and only if ε∈L(x)\varepsilon \in L(x).

Proof. By induction on xx. Leaves: L(∅)L(\emptyset) and L(a)L(a) do not contain ε\varepsilon, and L(ε)L(\varepsilon) does. Then ε∈L(s∣t)\varepsilon \in L(s \mid t) if and only if ε∈L(s)\varepsilon \in L(s) or ε∈L(t)\varepsilon \in L(t); ε∈L(st)\varepsilon \in L(st) if and only if ε∈L(s)\varepsilon \in L(s) and ε∈L(t)\varepsilon \in L(t); and ε∈L(s∗)\varepsilon \in L(s^*) always. These are lines L6, L9 and L14. □\square

Lemma 2 (locality). For every node xx and every nonempty word u=p1⋯pnu = p_1 \cdots p_n over the positions, u∈L(xˉ)u \in L(\bar x) if and only if (a) p1∈First(x)p_1 \in \mathrm{First}(x), (b) pn∈Last(x)p_n \in \mathrm{Last}(x) and (c) (pi,pi+1)∈Fol(x)(p_i, p_{i+1}) \in \mathrm{Fol}(x) for 1≤i<n1 \le i < n.

Proof. By induction on xx. Call uu good for xx if (a), (b) and (c) hold.

  • x=∅x = \emptyset or x=εx = \varepsilon: L(xˉ)L(\bar x) has no nonempty word, and First(x)=∅\mathrm{First}(x) = \emptyset, so no word is good.
  • xx is the position pp: L(xˉ)={p}L(\bar x) = \{p\}. A good word has p1=pn=pp_1 = p_n = p and, since Fol(x)=∅\mathrm{Fol}(x) = \emptyset, length 1; so it is pp.
  • x=s∣tx = s \mid t. If u∈L(sˉ)u \in L(\bar s), then uu is good for ss by induction, hence good for xx, since each set of xx contains that of ss; the same for tt. Conversely, let uu be good for xx. Every pair of Fol(x)\mathrm{Fol}(x) lies in pos(s)2\mathrm{pos}(s)^2 or in pos(t)2\mathrm{pos}(t)^2, and these sets are disjoint, so by (c) all letters of uu lie in pos(s)\mathrm{pos}(s), or all in pos(t)\mathrm{pos}(t). In the first case p1∈First(x)∩pos(s)=First(s)p_1 \in \mathrm{First}(x) \cap \mathrm{pos}(s) = \mathrm{First}(s), pn∈Last(s)p_n \in \mathrm{Last}(s), and the pairs lie in Fol(x)∩pos(s)2=Fol(s)\mathrm{Fol}(x) \cap \mathrm{pos}(s)^2 = \mathrm{Fol}(s); so uu is good for ss and u∈L(sˉ)⊆L(xˉ)u \in L(\bar s) \subseteq L(\bar x). The second case is the same.
  • x=stx = st. Let u∈L(xˉ)u \in L(\bar x), so u=vv′u = vv' with v∈L(sˉ)v \in L(\bar s) and v′∈L(tˉ)v' \in L(\bar t). If v=εv = \varepsilon, then ε∈L(s)\varepsilon \in L(s), so N(s)N(s) holds by Lemma 1 and First(t)⊆First(x)\mathrm{First}(t) \subseteq \mathrm{First}(x); u=v′u = v' is good for tt, and hence for xx. If v′=εv' = \varepsilon, the argument is symmetric with N(t)N(t) and Last(s)⊆Last(x)\mathrm{Last}(s) \subseteq \mathrm{Last}(x). If both are nonempty, vv is good for ss and v′v' for tt, so p1∈First(s)⊆First(x)p_1 \in \mathrm{First}(s) \subseteq \mathrm{First}(x), pn∈Last(t)⊆Last(x)p_n \in \mathrm{Last}(t) \subseteq \mathrm{Last}(x), the pairs inside vv and v′v' are in Fol(x)\mathrm{Fol}(x), and the pair at the junction is in Last(s)×First(t)⊆Fol(x)\mathrm{Last}(s) \times \mathrm{First}(t) \subseteq \mathrm{Fol}(x). Conversely, let uu be good for xx. No pair of Fol(x)\mathrm{Fol}(x) goes from pos(t)\mathrm{pos}(t) to pos(s)\mathrm{pos}(s), so u=vv′u = vv' where vv has its letters in pos(s)\mathrm{pos}(s) and v′v' in pos(t)\mathrm{pos}(t). If v=εv = \varepsilon: p1∈First(x)∩pos(t)p_1 \in \mathrm{First}(x) \cap \mathrm{pos}(t), which is not empty only if N(s)N(s) holds, and then it is a subset of First(t)\mathrm{First}(t); also pn∈Last(x)∩pos(t)=Last(t)p_n \in \mathrm{Last}(x) \cap \mathrm{pos}(t) = \mathrm{Last}(t) and the pairs are in Fol(t)\mathrm{Fol}(t). So uu is good for tt, u∈L(tˉ)u \in L(\bar t), and ε∈L(s)\varepsilon \in L(s) by Lemma 1, so u∈L(xˉ)u \in L(\bar x). If v′=εv' = \varepsilon, the argument is symmetric. If both are nonempty, vv starts in First(x)∩pos(s)=First(s)\mathrm{First}(x) \cap \mathrm{pos}(s) = \mathrm{First}(s), its pairs are in Fol(x)∩pos(s)2=Fol(s)\mathrm{Fol}(x) \cap \mathrm{pos}(s)^2 = \mathrm{Fol}(s), and its last letter is in Last(s)\mathrm{Last}(s) because the junction pair lies in Fol(x)\mathrm{Fol}(x) and goes from pos(s)\mathrm{pos}(s) to pos(t)\mathrm{pos}(t), so it is in Last(s)×First(t)\mathrm{Last}(s) \times \mathrm{First}(t). So vv is good for ss, and in the same way v′v' is good for tt. By induction, u=vv′∈L(sˉ)L(tˉ)=L(xˉ)u = vv' \in L(\bar s) L(\bar t) = L(\bar x).
  • x=s∗x = s^*. Let u∈L(xˉ)u \in L(\bar x), nonempty. Then u=v1⋯vju = v_1 \cdots v_j with j≥1j \ge 1 and each vlv_l a nonempty word of L(sˉ)L(\bar s) (drop the empty factors). Each vlv_l is good for ss; the pairs inside the factors are in Fol(s)\mathrm{Fol}(s), and each pair at a junction is in Last(s)×First(s)\mathrm{Last}(s) \times \mathrm{First}(s). So uu is good for xx, since First(x)=First(s)\mathrm{First}(x) = \mathrm{First}(s) and Last(x)=Last(s)\mathrm{Last}(x) = \mathrm{Last}(s). Conversely, let uu be good for xx; all its letters are in pos(s)\mathrm{pos}(s). Cut uu between pip_i and pi+1p_{i+1} whenever (pi,pi+1)∉Fol(s)(p_i, p_{i+1}) \notin \mathrm{Fol}(s). Such a pair is in Fol(x)∖Fol(s)⊆Last(s)×First(s)\mathrm{Fol}(x) \setminus \mathrm{Fol}(s) \subseteq \mathrm{Last}(s) \times \mathrm{First}(s), so each piece starts in First(s)\mathrm{First}(s) (the first piece by (a), the others by the cut), ends in Last(s)\mathrm{Last}(s) (the last piece by (b), the others by the cut), and has all its pairs in Fol(s)\mathrm{Fol}(s). So each piece is good for ss, is in L(sˉ)L(\bar s) by induction, and u∈L(sˉ)+⊆L(xˉ)u \in L(\bar s)^+ \subseteq L(\bar x). □\square

Lemma 3. L(x)=h(L(xˉ))L(x) = h(L(\bar x)) for every node xx.

Proof. hh is a homomorphism, so it commutes with union, concatenation and star of languages, and h({p})={sym(p)}h(\{p\}) = \{\mathrm{sym}(p)\} for a leaf. Induction on xx. □\square

Theorem. The automaton GG returned at line L18 accepts exactly L(r)L(r).

Proof. The empty word is accepted if and only if 0∈F0 \in F, that is, if and only if N(r)N(r) holds, which by Lemma 1 means ε∈L(r)\varepsilon \in L(r).

Let w=a1⋯anw = a_1 \cdots a_n with n≥1n \ge 1. Every move into a state qq reads sym(q)\mathrm{sym}(q), and no move enters state 0. So an accepting run of GG on ww is a sequence of states 0,p1,…,pn0, p_1, \ldots, p_n with p1∈Follow(0)=First(r)p_1 \in \mathrm{Follow}(0) = \mathrm{First}(r), pi+1∈Follow(pi)p_{i+1} \in \mathrm{Follow}(p_i), that is (pi,pi+1)∈Fol(r)(p_i, p_{i+1}) \in \mathrm{Fol}(r), sym(pi)=ai\mathrm{sym}(p_i) = a_i for each ii, and pn∈Fp_n \in F; since pn≠0p_n \ne 0, this means pn∈Last(r)p_n \in \mathrm{Last}(r). By Lemma 2, such a sequence exists if and only if some word p1⋯pn∈L(rˉ)p_1 \cdots p_n \in L(\bar r) has h(p1⋯pn)=wh(p_1 \cdots p_n) = w. By Lemma 3, this holds if and only if w∈L(r)w \in L(r). ■\blacksquare

Back to Glushkov automaton