2010-11-22 1 views
3

В процессе обучения Пролога, я пытаюсь решить следующую задачу, используя аккумуляторы:Проблемы с аккумуляторами в прологе

Написать предикат addone2 ​​/ чей первый аргумент списка целых чисел, а второй аргумент список целых чисел, полученных добавлением 1 к каждому целому числу в первом списке. Например, запрос

 addone([1,2,7,2],X). 

должен дать

 X = [2,3,8,3]. 

Я создал следующий код:

addone([], _). 
addone([E|Tail], [R|Rs]) :- 
    NewE is E+1, 
    append([R|Rs], [NewE], NewRs), 
    addone(Tail, NewRs). 

Но это не работает. Может кто-нибудь сказать мне, почему? Итак, как я могу использовать аккумуляторы в Prolog?

Спасибо!

ответ

4

anthares является правильным в том, что вы должны уточнить базовый случай. Тем не менее, вы также делаете вещи очень неэффективно с вашими звонками append. В Prolog требуется некоторое время, чтобы привыкнуть к силе унификации, но, к примеру, в этом случае это поможет вам сразу настроить список результатов. Попробуйте следующее:

addone([E|Tail], [E1|Rs]) :- 
    E1 is E+1, 
    addone(Tail, Rs). 

Это действительно все, что к чему. Немедленно разместив E1 в шаблоне второго аргумента, вы уже создали первый элемент списка результатов. Остальные элементы Rs будут созданы во время рекурсии. Очень типичный шаблон Пролога.

+0

Спасибо за помощь Фрэнк! Не сейчас об этом «трюке» без добавления списка. Также спасибо anthares за исправление моего базового футляра! –

+0

Спасибо, Фрэнк! Этот трюк не очевиден и очень удобен! – ProfVersaggi

1

В нижней части вашей рекурсии должен быть addone([],[]). в NewRs для того, чтобы быть связан с []