2015-01-19 7 views
0

Учитывая дерево разбора строки, моя цель - обновить мою базу знаний.сделать несколько утверждений на основе соответствия шаблону

Из предложения с переменной длиной, как следующее:

"node 1 is near node 2 that is near node 3 that is near node 4 that..." 

в моем представлении становится дерево разбора представление предложения, например:

s(desc(np(noun(node),id(1)),vp(verb(is),prep(near),np(noun(node),id(2),rel_clause(rel(that)... 

, из которого я хотел бы выведите и утвердите следующую информацию:

edge(1,2),edge(2,3),edge(3,4). 

Как достичь этого Цель?

Я пытался управлять каким-то дело с чем-то вроде

:- dynamic edge/2. 

    extract(T):- T= s(desc(np(noun(node),id(A)),vp(verb(is),prep(near),np(noun(node),id(B)))), 
    assert(edge(A,B)). 

    extract(T):- T= s(desc(np(noun(node),id(A)),vp(verb(is),prep(near),np(noun(node),id(B),rel_clause(rel(that)... 

и т.д. , но я хотел бы, чтобы управлять потенциально бесконечные предложения.

Я использую SWI-пролог.

EDIT: полный пример дерева разбора я получаю на входе:

desc(np(noun(node), id(1)), vp(verb(is), prep(near), np(noun(node), id(2), 
    rel_clause(rel(that), vp(verb(is), prep(near), np(noun(node), id(3), 
    rel_clause(rel(that), vp(verb(is), prep(near), np(noun(node), id(4))))))))) 
+0

Не могли бы вы изложить полный пример, в котором есть 'rel_clause', так что ясно, какова ваша структура? – lurker

+0

добавил возможный ввод – newbie

ответ

1

Первое, что нужно сделать, это придумать более полезной описания данных. Один из способов разбить его так:

description = desc(subject, verb_part) 
subject = np(noun(node), id(A)) 
verb_part = vp(verb(is), prep(near), object_part) 
object_part = np(noun(node), id(B)) 
object_part = np(noun(node), id(B), rel_part) 
rel_part = relcl(rel(that), verb_part) 

Здесь вы можете увидеть, где происходит рекурсия и писать предикаты, которые выравнивают с приведенными выше определениями:

% description = desc(subject, verb_part) 
% subject = np(noun(node), id(A)) 
% 
extract(desc(np(noun(node), id(A)), VerbPart)) :- 
    select_edge(A, VerbPart). 

% verb_part = vp(verb(is), prep(near), object_part) 
% 
select_edge(A, vp(verb(is), prep(near), ObjectPart)) :- 
    connect_node(A, ObjectPart). 

% object_part = np(noun(node), id(B)) 
% 
connect_node(A, np(noun(node), id(B))) :- 
    assertz(edge(A, B)). 

% object_part = np(noun(node), id(B), rel_part) 
% rel_part = relcl(rel(that), verb_part) 
% 
connect_node(A, np(noun(node), id(B), relcl(rel(that), VerbPart))) :- 
    assertz(edge(A, B)), 
    select_edge(B, VerbPart). 

Для выполнения:

| ?- extract(desc(np(noun(node), id(1)), vp(verb(is), prep(near), np(noun(node), id(2), 
    relcl(rel(that), vp(verb(is), prep(near), np(noun(node), id(3), 
    relcl(rel(that), vp(verb(is), prep(near), np(noun(node), id(4))))))))))). 

true ? ; 

no 

результаты отстаиваются, как можно видеть, если мы перечислим edge/2 факты:

| ?- listing(edge). 

% file: user_input 

edge(1, 2). 
edge(2, 3). 
edge(3, 4). 

yes 

Вы можете также собрать края в списке вместо утверждения их, и есть результат запроса будет, [edge(1,2), edge(2,3), edge(3,4)]:

extract(desc(np(noun(node), id(A)), VerbPart), Edges) :- 
    select_edge(A, VerbPart, Edges). 

select_edge(A, vp(verb(is), prep(near), ObjectPart), Edges) :- 
    connect_node(A, ObjectPart, Edges). 

connect_node(A, np(noun(node), id(B)), [edge(A,B)]). 
connect_node(A, np(noun(node), id(B), relcl(rel(that), VerbPart)), [edge(A,B)|Edges]) :- 
    select_edge(B, VerbPart, Edges). 

А потом утверждать их все сразу из полученного списка с maplist:

extract(Description, Edges), maplist(assertz, Edges). 
Смежные вопросы