我正在使用SWI-Prolog编写软件,在该软件中,我必须查找谓词的所有基础。特别是假设我可以独立访问头部和身体,则所有将头部和相关身体固定的替换都可以。这是我要获取的行为的示例:
nsecureSkipVerify = true
defaultEntryPoints = ["https", "http"]
# WEB interface of Traefik - it will show web page with overview of frontend and backend configurations
[api]
entryPoint = "traefik"
dashboard = true
address = ":8080"
# Force HTTPS
[entryPoints]
[entryPoints.http]
address = ":80"
[entryPoints.http.redirect]
entryPoint = "https"
[entryPoints.https]
address = ":443"
[entryPoints.https.tls]
# Let's encrypt configuration
[acme]
email = "example@gmail.com" #any email id will work
storage="acme.json"
entryPoint = "https"
acmeLogging=true
onDemand = false #create certificate when container is created
[acme.dnsChallenge]
provider = "cloudflare"
delayBeforeCheck = 300
[[acme.domains]]
main = "example.com"
[[acme.domains]]
main = "*.example.com"
# Connection to docker host system (docker.sock)
[docker]
endpoint = "unix:///var/run/docker.sock"
domain = "example.com"
watch = true
# This will hide all docker containers that don't have explicitly
# set label to "enable"
exposedbydefault = false
也许可以概括为:
student(a).
student(b).
student(c).
play.
study(A):-
play,
student(A).
ground(Head,Body,Result):-
% some code
...
?- ground([study(A)],[play, student(A)],R).
R = [
[study(a):- play, student(a)],
[study(b):- play, student(b)],
[study(c):- play, student(c)]
]
因此,对于身体,找到所有非地面变量,将其接地,然后将头部变量接地。基本上找到所有组合。问题是要管理身体...
也许我可以使用例如dog(d).
dog(e).
study(A,B):-
play,
dog(B),
student(A).
?- ground([study(A,B)],[play, dog(B),student(A)],R).
R = [[study(a):- play, dog(d), student(a)] ... ]
,=../2
和functor/3
,但是我不知道如何对身体(see this question/answer)进行拍针。
谢谢!
答案 0 :(得分:2)
我不确定为什么在示例中您提供的目标位于列表内,而您也提供了正文。
此答案中的过程以目标为目标,获取匹配子句,然后获取所有解决方案(在途中绑定变量)。如果没有目标,则可能会使一些变量不受约束。回溯时,可能会使用其他与初始目标匹配的子句。
ground(Goal, Body, LGroundClauses):-
clause(Goal, Body),
findall((Goal:-Body), call(Body), LGroundClauses).
样品运行:
?- ground(study(A), Body, LClauses).
Body = (play, student(A)),
LClauses = [
(study(a):-play, student(a)),
(study(b):-play, student(b)),
(study(c):-play, student(c))
]
答案 1 :(得分:1)
请注意有关问题和已接受的解决方案的评论,此评论可能太长了。
@gusbro写道(重点是我的):“我不确定为什么在示例中您提供的目标位于列表内,同时还提供了正文。”我也希望在这一点上得到澄清。
ISO Prolog Core标准允许clause/2
谓词检索 public 谓词的子句。但是大多数Prolog系统(特别是SWI-Prolog除外)仅允许使用clause/2
访问动态谓词的子句。此外,可以将SWI-Prolog protect_static_code
标志设置为true
以在静态谓词上禁用clause/2
。除非谓词被声明为动态,否则这将使解决方案不可移植(在部署方案中可能是不可取的)。假设Body
参数确实绑定在ground(Head,Body,Result)
目标中,一个可能的选择是使用目标列表 construct 子句主体。像这样:
ground(Goal, BodyGoals, LGroundClauses):-
list_to_conjunction(BodyGoals, Body),
findall(Goal:-Body, call(Body), LGroundClauses).
这将消除调用clause/2
的要求,并可能使谓词具有动态性以实现可移植性。但这对您来说有意义吗?