【问题标题】:Prolog search key/value list and output a list of valuesProlog搜索键/值列表并输出值列表
【发布时间】:2018-10-21 16:01:06
【问题描述】:

我再次陷入了一个非常简单的 Prolog 任务。我想定义一个谓词kv_search/3,它将一个键/值列表(例如[[a,1],[b,2],[c,3],[d,4],[e,8],[a,9],[b,10]])作为第一个参数,一个键作为第二个参数,并在第三个参数中输出一个包含该键的所有值的列表。

我目前的做法是这样的:

kv_find([[K,V|_]|Rest], K, Result) :- 
    kv_find(Rest, K, [V|Result]).

kv_find([[Ks,_|_]|Rest], K, Result) :-
    Ks \= K ,
    kv_find(Rest, K, Result).

kv_find([], _, _).

然而,这个解决方案的问题是它只输出真或假,而不是打印缺失的参数。

例如以下查询结果为true,而不是我预期的B=[1, 9]

kv_find([[a,1],[b,2],[c,3],[d,4],[e,8],[a,9],[b,10]], a, B).

如果列表中不存在该键,我想输出一个空列表。

【问题讨论】:

  • 您能解释一下您的基本案例背后的原因吗?例如,kv_find([],a,X) 应该与 X 绑定什么(如果有的话)?
  • 对于这个任务,我们可以假设第一个参数是我展示的表单中的有效键/值列表。但是您的示例可能会导致X=[]
  • “可以”吗?建议可能是别的东西?而且您的代码不会以这种方式运行。
  • 是的。但是直到现在我才想到这个案例,因为我的练习没有具体说明这个案例。
  • @JohnnyKonfetti "我的练习没有指定这种情况。" 当你有递归时,这不是真的,你需要始终认为正确的基本情况因为错误的基本情况可能会导致错误的整体谓词...

标签: prolog


【解决方案1】:

首先你的基本情况是错误的,你需要写:

kv_find([], _, []).

由于列表为空,因此只有一个空的输出列表应该成功。

那么您的解决方案中的另一个问题是您正在编写:

kv_find([[K,V|_]|Rest], K, Result) :- 
    kv_find(Rest, K, [V|Result]).

虽然你应该写这样的东西:

kv_find([[K,V|_]|Rest], K, [V | Result]) :- 
    kv_find(Rest, K, Result).

上面带有错误基本情况的规则使您的谓词对于任何第三个列表总是成功。

此外,我会进行一些更改,例如:

kv_find([[K,V]|Rest], K, [V|Result]) :- 
    kv_find(Rest, K, Result).

kv_find([[Ks,_]|Rest], K, Result) :-
    dif(Ks, K) ,
    kv_find(Rest, K, Result).

kv_find([], _, []).

【讨论】:

    猜你喜欢
    • 2013-10-13
    • 2012-05-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多