Prolog - 打印EVEN编号的总和,从1到10

时间:2018-04-04 06:55:31

标签: prolog

我正在尝试使用Prolog从1到10打印所有偶数,这是我尝试过的:

printn(10,0):- write(10),!.
printn(X,Sum):- 
    ( X mod 2 =:= 0 -> Sum is X+Sum, Next is X+1, nl, printn(Next);
      Next is X+1, printn(Next) ).

但它返回false。

5 个答案:

答案 0 :(得分:2)

您不需要从头开始创建包含数字的列表,最好一次检查数字:

print(X,Y):-print_even(X,Y,0).

print_even(X, X, Sum):- 
    (   X mod 2 =:= 0 -> Sum1 is X+Sum; 
        Sum1 = Sum
    ), print(Sum1).
print_even(X, Y, Sum):- 
    X<Y, Next is X+1,
    (   X mod 2 =:= 0 -> Sum1 is X+Sum, print_even(Next, Y, Sum1); 
        print_even(Next, Y, Sum)
    ).

请注意,在Prolog中Sum is Sum+1总是失败,您需要使用新变量,例如Sum1

示例:

?- print(1,10).
30
true ;
false.

答案 1 :(得分:2)

获取Prolog输出的最有用方法是通过回溯单独或在列表中捕获变量中的解决方案。 “打印”的概念(使用其他语言而来)允许格式化等,但不被认为是表达解决方案的最佳方式。

在Prolog中,您希望将问题表达为关系。例如,如果even_with_max(X, Max)是小于或等于X的偶数,我们可能会说Max为真(或成功)。在Prolog中,当使用整数推理时,CLP(FD)库就是您想要使用的。

:- use_module(library(clpfd)).

even_up_to(X, Max) :-
    X in 1..Max,
    X mod 2 #= 0,   % EDIT: as suggested by Taku
    label([X]).

这将产生:

3 ?- even_up_to(X, 10).
X = 2 ;
X = 4 ;
X = 6 ;
X = 8 ;
X = 10.

如果您想收集到列表中,可以使用:findall(X, even_up_to(X), Evens).

答案 2 :(得分:1)

你有什么错误?这是我的解决方案:

  1. 创建列表[1 ... 10]
  2. 过滤它,不包括奇数
  3. 列表中的元素
  4. 代码:

    sumList([], 0).
    sumList([Head|Tail], Sum) :-
       sumList(Tail, Rest),
       Sum is Head + Rest.
    
    isOdd(X) :-
        not((X mod 2) =:= 0).
    
    sumOfEvenNums(A, B, Out) :- 
        numlist(A, B, Numbers),
        exclude(isOdd, Numbers, Even_numbers),
        sumList(Even_numbers, Out).
    

    现在您可以致电sumOfEvenNums(1, 10, N)

答案 3 :(得分:1)

在ECLiPSe中,您可以使用迭代器编写:

sum_even(Sum):-
( for(I,1,10),fromto(0,In,Out,Sum)
    do
  (I mod 2 =:= 0 -> Out is In + I;Out is In)
)

答案 4 :(得分:1)

使用library(aggregate)

evens_upto(Sum) :-
  aggregate(sum(E), (between(1, 10, E), E mod 2 =:= 0), Sum).

感谢@CapelliC的灵感。