我想出来的行使下列事实在抽象谓词
byCar(auckland,hamilton).
byCar(hamilton,raglan).
byCar(valmont,saarbruecken).
byCar(valmont,metz).
byTrain(metz,frankfurt).
byTrain(saarbruecken,frankfurt).
byTrain(metz,paris).
byTrain(saarbruecken,paris).
byPlane(frankfurt,bangkok).
byPlane(frankfurt,singapore).
byPlane(paris,losAngeles).
byPlane(bangkok,auckland).
byPlane(singapore,auckland).
byPlane(losAngeles,auckland).
开始...并要求读者定义谓词travel/3
这样,例如,
travel(valmont, losAngeles, T)
...会找到像这样的解决方案
T = go(byCar(valmont, metz),
go(byTrain(metz, paris),
go(byPlane(paris, losAngeles)))).
这是我想到的:
travel(X,Y,go(byCar(X,Y))):-byCar(X,Y).
travel(X,Y,go(byTrain(X,Y))):-byTrain(X,Y).
travel(X,Y,go(byPlane(X,Y))):-byPlane(X,Y).
travel(X,Z,go(byCar(X,Y),T)):-byCar(X,Y),travel(Y,Z,T).
travel(X,Z,go(byTrain(X,Y),T)):-byTrain(X,Y),travel(Y,Z,T).
travel(X,Z,go(byPlane(X,Y),T)):-byPlane(X,Y),travel(Y,Z,T).
看来工作...
?- travel(valmont, losAngeles, X).
X = go(byCar(valmont, saarbruecken), go(byTrain(saarbruecken, paris), go(byPlane(paris, losAngeles)))) ;
X = go(byCar(valmont, metz), go(byTrain(metz, paris), go(byPlane(paris, losAngeles)))) ;
false.
...但它伤害了我的眼睛;所有这些重复都是抽象的呼喊。
我试图通过定义
oneLeg(X,Y):-byCar(X,Y);byTrain(X,Y);byPlane(X,Y).
...并重新定义,以消除重复travel/3
为
travel(X,Y,go(oneLeg(X,Y))):-oneLeg(X,Y).
travel(X,Z,go(oneLeg(X,Y),T)):-oneLeg(X,Y),travel(Y,Z,T).
...但结果还没有应用:
?- travel(valmont, losAngeles, X).
X = go(oneLeg(valmont, saarbruecken), go(oneLeg(saarbruecken, paris), go(oneLeg(paris, losAngeles)))) ;
X = go(oneLeg(valmont, metz), go(oneLeg(metz, paris), go(oneLeg(paris, losAngeles)))) ;
false.
我该如何强制更换结果中第oneLeg
个实例e具体的byCar
,byTrain
或byPlane
那“证明”oneLeg
实例?
查看高级谓词的'call/N'系列。在你的情况下,'call/3'将特别有用。另外,'(= ..)/ 2'也值得一看。 – mat
@mat:谢谢,但是我无法弄清楚你的建议...... – kjo
如果你没有分成三个不同的表格,但有一个表格有三个参数:从,到,意味着一切都会更容易。然后,如果突然你还需要乘船出海或类似的东西,你不必改变你的计划。 – 2017-03-03 12:40:14