使用 SWI-Prolog。
如何在不绑定变量的情况下复制带有变量的术语?
我试过的
我试过copy_term/2和duplicate_term/2
例如:
foo(c).
foo(E) :-
E = bar(a,b,X),
copy_term(E,Ec),
duplicate_term(E,Ed),
write("E: "),write(E),nl,
write("Ec: "),write(Ec),nl,
write("Ed: "),write(Ed),nl.
结果是
?- foo(bar(a,b,bar(a,b,bar(a,b,c)))).
E: bar(a,b,bar(a,b,bar(a,b,c)))
Ec: bar(a,b,bar(a,b,bar(a,b,c))) <-- Copy
Ed: bar(a,b,bar(a,b,bar(a,b,c))) <-- Duplicate
true.
?- foo(bar(a,b,bar(a,b,c))).
E: bar(a,b,bar(a,b,c))
Ec: bar(a,b,bar(a,b,c)) <-- Copy
Ed: bar(a,b,bar(a,b,c)) <-- Duplicate
true.
?- foo(bar(a,b,c)).
E: bar(a,b,c)
Ec: bar(a,b,c) <-- Copy
Ed: bar(a,b,c) <-- Duplicate
true.
并检查了分析和构建术语部分
我需要的
这En
是谓词返回我需要的结果
?- foo(bar(a,b,bar(a,b,bar(a,b,c)))).
E: bar(a,b,bar(a,b,bar(a,b,c)))
En: bar(a,b,X), <-- Need this
true.
?- foo(bar(a,b,bar(a,b,c))).
E: bar(a,b,bar(a,b,c))
En: bar(a,b,X), <-- Need this
true.
?- foo(bar(a,b,c)).
E: bar(a,b,c)
En: bar(a,b,X), <-- Need this
true.
我希望有一个内置的谓词。
TL;博士
这需要解决二进制表达式。原文用于选择谓词和求解表达式。我称为本地的副本用于显示子表达式的重写,而我称为全局的副本用于显示应用于整个表达式的重写。如果只有一个术语,例如没有副本,一旦变量被绑定为一种用途,它会导致其他用途失败。
当前的解决方案是在谓词中输入具有不同变量的多个术语以用于每次使用。将其乘以数百到可能数千个可能存在键入或复制/粘贴错误的谓词,您就会看到需要。
其他注意事项
我还考虑在谓词中拥有该术语的主副本,然后使用它来制作三个副本。问题是其中一个副本用于选择谓词,因此在选择谓词之前必须进行副本。因此,即使未选择谓词进行评估,也必须在谓词中发生副本。
foo(c).
foo(Ec) :-
M = bar(a,b,X),
copy_term(M,Ec),
duplicate_term(M,Ed),
write("M: "),write(M),nl,
write("Ec: "),write(Ec),nl,
write("Ed: "),write(Ed),nl.
?- foo(bar(a,b,bar(a,b,bar(a,b,c)))).
M: bar(a,b,_9364)
Ec: bar(a,b,bar(a,b,bar(a,b,c)))
Ed: bar(a,b,_9384)
true.
?- foo(bar(a,b,bar(a,b,c))).
M: bar(a,b,_9240)
Ec: bar(a,b,bar(a,b,c))
Ed: bar(a,b,_9260)
true.
?- foo(bar(a,b,c)).
M: bar(a,b,_9116)
Ec: bar(a,b,c)
Ed: bar(a,b,_9136)
true.
所以
copy_term/2
给了我一个带有谓词选择和评估部分所需的变量绑定的副本,
duplicate_term/2
给了我与其他谓词一起使用的自由变量的术语。
实际应用的示例输出
Global Local
------------------ -----------------------------
Input (1 + ((0 + 0) + 0))
0 + X -> X (0 + 0) -> 0
= (1 + (0 + 0))
X + 0 -> X (0 + 0) -> 0
= (1 + 0)
X + 0 -> X (1 + 0) -> 1
= 1