Definition of a path/trail/walk

后端 未结 3 1249
你的背包
你的背包 2020-11-22 04:21

Many predicates define some kind of an acyclic path built from edges defined via a binary relation, quite similarly to defining transitive closure. A generic definition is t

3条回答
  •  孤城傲影
    2020-11-22 05:05

    I do not see the reason to define in path/4 the arguments "start node" and "end node". It seems that a simple path/2 with the rule and the list of nodes must be enough.

    If the user wants a list starting with some node (by example, 'a'), he can query the statement as: path( some_rule, ['a'|Q] ).

    A user could, by example, request for path that have length 10 in the way: length(P,10), path( some_rule, P).

    * Addendum 1 *

    Some utility goals can be easily added, but they are not the main subject. Example, path/3 with start node is:

    path( some_rule, [start|Q], start ) :- 
      path ( some_rule, [start|Q ] ).   
    

    * Addendum 2 *

    Addition of last node as argument could give the false idea that this argument drives the algorithm, but it doesn't. Assume by example:

    n(a, b).
    n(a, c).
    n(a, d).
    

    and trace algorithm execution for the query:

    [trace]  ?- path( n, P, X, d ).
       Call: (6) path(n, _G1025, _G1026, d) ? creep
       Call: (7) path(n, _G1107, _G1026, d, [_G1026]) ? creep
       Exit: (7) path(n, [], d, d, [d]) ? creep
       Exit: (6) path(n, [d], d, d) ? creep
    P = [d],
    X = d ;
       Redo: (7) path(n, _G1107, _G1026, d, [_G1026]) ? creep
       Call: (8) n(_G1026, _G1112) ? creep
    
       Exit: (8) n(a, b) ? creep
    
       Call: (8) non_member(b, [a]) ? creep
       Call: (9) dif:dif(b, a) ? creep
       Exit: (9) dif:dif(b, a) ? creep
       Call: (9) non_member(b, []) ? creep
       Exit: (9) non_member(b, []) ? creep
       Exit: (8) non_member(b, [a]) ? creep
       Call: (8) path(n, _G1113, b, d, [b, a]) ? creep
       Call: (9) n(b, _G1118) ? creep
       Fail: (9) n(b, _G1118) ? creep
       Fail: (8) path(n, _G1113, b, d, [b, a]) ? creep
       Redo: (9) non_member(b, []) ? creep
       Fail: (9) non_member(b, []) ? creep
       Fail: (8) non_member(b, [a]) ? creep
       Redo: (8) n(_G1026, _G1112) ? creep
    
       Exit: (8) n(a, c) ? creep
    
       Call: (8) non_member(c, [a]) ? creep
       Call: (9) dif:dif(c, a) ? creep
       Exit: (9) dif:dif(c, a) ? creep
       Call: (9) non_member(c, []) ? creep
       Exit: (9) non_member(c, []) ? creep
       Exit: (8) non_member(c, [a]) ? creep
       Call: (8) path(n, _G1113, c, d, [c, a]) ? creep
       Call: (9) n(c, _G1118) ? creep
       Fail: (9) n(c, _G1118) ? creep
       Fail: (8) path(n, _G1113, c, d, [c, a]) ? creep
       Redo: (9) non_member(c, []) ? creep
       Fail: (9) non_member(c, []) ? creep
       Fail: (8) non_member(c, [a]) ? creep
       Redo: (8) n(_G1026, _G1112) ? creep
    
       Exit: (8) n(a, d) ? creep
    
       Call: (8) non_member(d, [a]) ? creep
       Call: (9) dif:dif(d, a) ? creep
       Exit: (9) dif:dif(d, a) ? creep
       Call: (9) non_member(d, []) ? creep
       Exit: (9) non_member(d, []) ? creep
       Exit: (8) non_member(d, [a]) ? creep
       Call: (8) path(n, _G1113, d, d, [d, a]) ? creep
       Exit: (8) path(n, [], d, d, [d, a]) ? creep
       Exit: (7) path(n, [d], a, d, [a]) ? creep
       Exit: (6) path(n, [a, d], a, d) ? creep
    P = [a, d],
    X = a .
    

    as you can see, in this case algorithm fails to brute force. For this reason, if algorithm is not improved, I suggest do not add "end node" as "path" argument.

提交回复
热议问题