| occur(x, u) | = | True | (xがuの真部分項) |
| False | (xがuの真部分項でない) |
UNIFY(s, t) =
begin
θ := {}
if s∈V ∨ t∈V then
begin [変数をx, 他の項をuとする]
if x≡u then unifiable := True
else if occur(x, u) then unifiable := False
else <unifiable, θ> := <True, {u/x}>
end
else if s∈K ∨ t∈K then
begin
if s≡t then unifiable := True
else unifiable := False
end
else
begin [t≡f(t1, ..., tnn), s≡g(s11,...,sm)とする]
if ¬f≡g ∨ m≠n then unifiable := False
else
begin
unifiable := True
for k = 1,...,n while unifiable
begin
<unifiable, σ> := UNIFY(tkθ, skθ)
if unifiable then θ := θσ
end
end
end
return <unifiable, θ>
end
アルゴリズム UNIFY について以下のことが成り立ちます。
| subterm(x, y, s, t) | ⇔ | x=s ∧ y=t |
| ∨ | x∈I(f) ∧ y∈I(f) ∧ n=a(f) ∧ x≡f(x1, …, xn) ∧ y≡f(y1, …, yn) ∧ ∃i∈Nnsubterm(xi, yi, s, t) |
| s_equal(x, y) | ⇔ | x∈V ∧ y∈V ∧ x=y |
| ∨ | x∈I(f) ∧ y∈I(f) |
| s_unify(x, y, θ) | ⇔ | x∈V ∧ y∈V ∧ (θ={y/x} ∨ θ={x/y}) |
| ∨ | x∈V ∧ y∈I ∧ ¬(x∈V(y)) ∧ θ={y/x} | |
| ∨ | x∈I ∧ y∈V ∧ ¬(y∈V(x)) ∧ θ={x/y} |
| unify(x, y, μ, θ) | ⇔ | (subterm(xμ, yμ, s, t) ⇒ s_equal(s, t)) ∧ θ=μ |
| ∨ | subterm(xμ, yμ, s, t) ∧ ¬s_equal(s, t) ∧ s_unify(s, t, λ) ∧ unify(x, y, μλ, θ) |
| unify(x, y, μ, θ) | ⇔ | (subterm(xμ, yμ, s, t) ⇒ s_equal(s, t)) ∧ θ=μ |
| ∨ | xμ=s ∧ yμ=t ∧ ¬s_equal(s, t) ∧ s_unify(s, t, λ) ∧ unify(x, y, μλ, θ) | |
| ∨ | xμ∈I(f) ∧ yμ∈I(f) ∧ n=a(f) ∧ xμ≡f(x1, …, xn) ∧ yμ≡f(y1, …, yn)
∧ ∃i∈Nnsubterm(xi, yi, s, t) ∧ ¬s_equal(s, t) ∧ s_unify(s, t, λ) ∧ unify(x, y, μλ, θ) | |
| ⇔ | (subterm(xμ, yμ, s, t) ⇒ s_equal(s, t)) ∧ θ=μ | |
| ∨ | xμ=s ∧ yμ=t ∧ ¬s_equal(s, t) ∧ s_unify(s, t, λ) ∧ unify(x, y, μλ, θ) | |
| ∨ | xμ∈I(f) ∧ yμ∈I(f) ∧ n=a(f) ∧ xμ≡f(x1, …, xn) ∧ yμ≡f(y1, …, yn)
∧ subterm(x1, y1, s, t) ∧ ¬s_equal(s, t) ∧ s_unify(s, t, λ) ∧ unify(x, y, μλ, θ) | |
| … | ||
| ∨ | xμ∈I(f) ∧ yμ∈I(f) ∧ n=a(f) ∧ xμ≡f(x1, …, xn) ∧ yμ≡f(y1, …, yn)
∧ subterm(xn, yn, s, t) ∧ ¬s_equal(s, t) ∧ s_unify(s, t, λ) ∧ unify(x, y, μλ, θ) | |
|
一度実行した条件は、次の呼び出しでは s_equal(s, t) が成立します。
unify(xi, yi, …) を実行した後の unify(x, y, …) は、 unify(xj, yj, …) (j > i) だけを実行したものと同じになります。 | ||
| ⇔ | (subterm(xμ, yμ, s, t) ⇒ s_equal(s, t)) ∧ θ=μ | |
| ∨ | xμ=s ∧ yμ=t ∧ ¬s_equal(s, t) ∧ s_unify(s, t, λ) ∧ unify(x, y, μλ, θ) | |
| ∨ | xμ∈I(f) ∧ yμ∈I(f) ∧ n=a(f) ∧ xμ≡f(x1, …, xn) ∧ yμ≡f(y1, …, yn)
∧ unify(x1, y1, μ, λ) ∧ unify(x, y, μλ, θ) | |
| … | ||
| ∨ | xμ∈I(f) ∧ yμ∈I(f) ∧ n=a(f) ∧ xμ≡f(x1, …, xn) ∧ yμ≡f(y1, …, yn)
∧ unify(xn, yn, μ, λ) ∧ unify(x, y, μλ, θ) | |
| ⇔ | xμ∈V ∧ yμ∈V ∧ xμ=yμ ∧ θ=μ | |
| ∨ | xμ∈I ∧ yμ∈I ∧ (subterm(xμ, yμ, s, t) ⇒ s_equal(s, t)) ∧ θ=μ | |
| ∨ | xμ=s ∧ yμ=t ∧ ¬s_equal(s, t) ∧ s_unify(s, t, λ) ∧ unify(x, y, μλ, θ) | |
| ∨ | xμ∈I(f) ∧ yμ∈I(f) ∧ n=a(f) ∧ xμ≡f(x1, …, xn) ∧ yμ≡f(y1, …, yn)
∧ unify(x1, y1, μ, σ2) ∧ … ∧ unify(xn, yn, σn, σn+1) ∧ unify(x, y, σn+1, θ) | |
| … | ||
| ∨ | xμ∈I(f) ∧ yμ∈I(f) ∧ n=a(f) ∧ xμ≡f(x1, …, xn) ∧ yμ≡f(y1, …, yn)
∧ unify(xn, yn, μ, σ2) ∧ … ∧ unify(xn, yn, σn, σn+1) ∧ unify(x, y, σn+1, θ) | |
| 最後の unify(x, y, σn+1, θ) は2番めの条件から θ=σn+1 となります。 | ||
| ⇔ | xμ∈V ∧ yμ∈V ∧ xμ=yμ ∧ θ=μ | |
| ∨ | xμ=s ∧ yμ=t ∧ ¬s_equal(s, t) ∧ s_unify(s, t, λ) ∧ unify(x, y, μλ, θ) | |
| ∨ | xμ∈I(f) ∧ yμ∈I(f) ∧ n=a(f) ∧
xμ≡f(x1, …, xn) ∧ yμ≡f(y1, …, yn)
∧ ∀i∈Nn∃σi ∧ σ1=1 ∀i∈Nnunify(xi, yi, σi, σi+1) ∧ θ=σn+1 | |
|
2番めの条件は、3番めの条件から呼び出されたもの以外は3番めの条件に含まれるので、
最後の unify(x, y, μλ, θ) は1番めの条件だけでよいので θ=μλ となります。 | ||
| ⇔ | xμ∈V ∧ yμ∈V ∧ xμ=yμ ∧ θ=μ | |
| ∨ | s_unify(xμ, yμ, λ) ∧ θ=μλ | |
| ∨ | xμ∈I(f) ∧ yμ∈I(f) ∧ n=a(f) ∧
xμ≡f(x1, …, xn) ∧ yμ≡f(y1, …, yn)
∧ ∀i∈Nn∃σi ∧ σ1=1 ∀i∈Nnunify(xi, yi, σi, σi+1) ∧ θ=σn+1 |
| equal([], []). |
| equal([Z|X], [Z|Y]) :- equal(X, Y). |
| equal(x, y) | ⇔ | x=nil ∧ y=nil |
| ∨ | x=cons(x1, x2) ∧ y=cons(y1, y2) ∧ x1=y1 ∧ equal(x2, y2) |
これと同じように、単一化アルゴリズムを記述してみます。 S は記号の集合、 T は項の集合、 L は項のリストの集合、 Σ は代入の集合という意味です。 各集合を構成する写像と、集合 S の中の関係 = を以下のように定義します。
| subst(v, θ, y) | ⇔ | θ=map(v, y) |
| ∨ | θ=comp(λ, μ) ∧ subst(v, λ, x) ∧ op(x, μ, y) |
| op(x, θ, y) | ⇔ | x=var(u) ∧ subst(u, θ, y) |
| ∨ | x=func(u, xl) ∧ y=func(v, yl) ∧ op(xl, θ, yl) |
| op(x, θ, y) | ⇔ | x=nil ∧ y=nil |
| ∨ | x=cons(x1, x2) ∧ y=cons(y1, y2) ∧ op(x1, θ, y1) ∧ op(x2, θ, y2) |
| notoccur(v, x) | ⇔ | x=var(u) ∧ u≠v |
| ∨ | x=func(u, xl) ∧ notoccur(v, xl) |
| notoccur(v, x) | ⇔ | x=nil |
| ∨ | x=cons(x1, x2) ∧ notoccur(v, x1) ∧ notoccur(v, x2) |
| s_unify(x, y, θ) | ⇔ | x=var(u) ∧ y=var(v) ∧ (θ=map(u, y) ∨ θ=map(v, x)) |
| ∨ | x=var(u) ∧ y=func(v, yl) ∧ notoccur(u, y) ∧ θ=map(u, y) | |
| ∨ | x=func(u, xl) ∧ y=var(v) ∧ notoccur(v, x) ∧ θ=map(v, x) |
| unify3(x, y, θ) | ⇔ | x=var(s) ∧ y=var(s) ∧ θ=id |
| ∨ | s_unify(x, y, θ) | |
| ∨ | x=func(s, xlist) ∧ y=func(s, ylist) ∧ unify3(xlist, ylist, θ) |
| unify3(x, y, θ) | ⇔ | x=nil ∧ y=nil ∧ θ=id |
| ∨ |
x=cons(x1, x2) ∧ y=cons(y1, y2) ∧ unify3(x1, y1, λ) ∧
op(x2, λ, xs) ∧ op(y2, λ, ys) ∧ unify3(xs, ys, μ) ∧ θ=comp(λ, μ) |