2010-11-05 56 views
2

好吧,所以我使用序言來構建一個簡單的XML解析器。我有下面的XML文件: 應該添加什麼DCG規則?

<ip> <line> 7 </line> <envt> p1:1 in main:1 </envt> </ip> 

<contour> 
    <name> main:1 </name> 
    <items> 
    <item> <var> x:int </var> <val> 2 </val> </item> 
    <item> <var> y:int </var> <val> 2 </val> </item> 
    </items> 
    <rpdl> system </rpdl> 
    <nested> 
    <contour> 
     <name> p1:1 </name> 
     <items> 
     <item> <var> y:int </var> <val> 0 </val> </item> 
    <item> <var> q:proc </var> <val> p2 in main:1 </val> </item> 
     </items> 
     <rpdl> <line> 21 </line> <envt> main:1 in root:1 </envt> </rpdl> 
    </contour> 
    </nested> 
</contour> 

</program_state> 

在序言我用下面的DCG規則:在主1:

xml([E]) --> element(E). 
xml([E|L]) --> element(E), xml(L). 

element(E) --> begintag(N), elements(L), endtag(N), {E =.. [N|L]}. 

elements(L) --> xml(L). 
elements([E]) --> [E]. 

begintag(N) --> ['<', N, '>']. 
endtag(N) --> ['<', '/', N, '>']. 

這樣的規則無法處理的東西,如「P1 1 「,」x:int「,」main:1「。我實際上試圖將這些東西改爲「p1」,「x」,「main」,並且解析器完美地工作。現在我應該添加哪些規則以便解析器可以處理不規則的令牌?

的解析樹會是這樣的:

program_state(
    ip(line(7), envt(p1:1 in main:1)), 
    contour(name(main:1), 
     items(item(var(x:int),val(2)), 
       item(var(y:int),val(2))), 
     rpdl(system), 
     nested(contour(name(p1:1), 
       items(item(var(y:int),val(0)), 
         item(var(q:proc),val(p2 in main:1))), 
       rpdl(line(21),envt(main:1 in root:1)), 
       )))) 

和下面的是我得到:

program_state(
    ip(line(7), envt(p1)), 
    contour(name(main), 
     items(item(var(x), val(2)), 
       item(var(y), val(2))), 
    rpdl(system), 
    nested(contour(name(p1), 
      items(item(var(y), val(0)), 
        item(var(q), val(p2))), 
      rpdl(line(21), envt(main)) 
       )))). 
+0

什麼想法?我試圖添加「元素(E) - > [E]」,但它會拋出異常.... – pippoflow 2010-11-05 20:11:07

回答

1

我記號化的XML,它送進分析器,它工作得很好。驗證輸入:需要引用冒號(:)的符號;否則它們代表module_name:module_specific_symbol。這裏的輸入:

?- listing(input). 
input([<, program_state, >, <, ip, >, <, line, >, '7', <, /, line, >, <, envt, >, ['p1:1', in, 'main:1'], <, /, envt, >, <, /, ip, >, <, contour, >, <, name, >, 'main:1', <, /, name, >, <, items, >, <, item, >, <, var, >, 'x:int', <, /, var, >, <, val, >, '2', <, /, val, >, <, /, item, >, <, item, >, <, var, >, 'y:int', <, /, var, >, <, val, >, '2', <, /, val, >, <, /, item, >, <, /, items, >, <, rpdl, >, system, <, /, rpdl, >, <, nested, >, <, contour, >, <, name, >, 'p1:1', <, /, name, >, <, items, >, <, item, >, <, var, >, 'y:int', <, /, var, >, <, val, >, '0', <, /, val, >, <, /, item, >, <, item, >, <, var, >, 'q:proc', <, /, var, >, <, val, >, [p2, in, 'main:1'], <, /, val, >, <, /, item, >, <, /, items, >, <, rpdl, >, <, line, >, '21', <, /, line, >, <, envt, >, ['main:1', in, 'root:1'], <, /, envt, >, <, /, rpdl, >, <, /, contour, >, <, /, nested, >, <, /, contour, >, <, /, program_state, >]). 

true. 

的A上市分析器是如何調用:

?- listing(run). 
run :- 
    consult('input.db'), 
    input(A), 
    phrase(xml(B), A), 
    write(B), 
    nl. 

true. 

解析器運行的清單:

?- run. 
% input.db compiled 0.00 sec, 2,768 bytes 
[program_state(ip(line(7),envt([p1:1,in,main:1])),contour(name(main:1),items(item(var(x:int),val(2)),item(var(y:int),val(2))),rpdl(system),nested(contour(name(p1:1),items(item(var(y:int),val(0)),item(var(q:proc),val([p2,in,main:1]))),rpdl(line(21),envt([main:1,in,root:1]))))))] 
true 
+0

感謝您的回答!我實際上添加了以下規則:元素([X:N]) - > [X,':',N]。 ([''中的X':N])→[X''in',Y'':',N]。 ('Y:M'中的[X:N'))→[X'':',N''in',Y'':',M]。 – pippoflow 2010-11-21 12:21:20

+0

這會工作。看起來像是IDE或其他一些代碼工具的一部分。 – frayser 2010-11-22 21:49:34