Prolog if then else logi c (ошибка: приоритет оператора cla sh) - PullRequest
0 голосов
/ 09 мая 2020

Я новичок в прологе и практикуюсь, чтобы понять его. В данный момент меня смущает ошибка в строке 5, в которой говорится: Синтаксическая ошибка: приоритет оператора cla sh. Вероятно, это связано с вложением logi c, но мне было интересно, есть ли способ заставить это вложение работать.

loopOver3(elt1, elt3, [H|T], sum):-
    ( =(elt1, elt2) =:= true ->  
      sum is sum + (elt1 + elt2),
      ;   =(elt1, elt2) =\= false -> ( =(elt1, H) =:= true ->  
            sum is sum + (elt1 * H),
            ;  =(elt1, H) =\= false -> ( =(elt2, H) =:= true ->  
                    ( \=(H, 0) =:= true ->
                      sum is sum + (100 / H)
                    )
                )
          )
    )
    loopOver3(elt1, elt3, T, sum).

Код Sudo для того, что я пытаюсь сделать:

for elt3 in list3: 
    if elt1 == elt2: 
        sum = sum + (elt1 + elt2) 
    else: 
        if elt1 == elt3: 
            sum = sum + (elt1 * elt3) 
        else: 
            if (elt2 == elt3) and (elt3 != 0): 
                sum = sum + (100 / elt3)

1 Ответ

1 голос
/ 09 мая 2020

Вам нужно немного поработать до go, чтобы понять концепции Пролога. Ваша первоначальная попытка полна атомов (нижний регистр), а не переменных (верхний регистр). В нем есть изменчивость. Вы думаете, что у Пролога есть функции (у него есть предикаты), которые возвращают значения (их нет - они либо успешны, либо терпят неудачу).

Я сделал предположение, что вы очищаете первые три значения вне списка, а затем отбрасывая первый элемент и возвращаясь вниз.

Итак, если у меня есть этот список [1,2,1,2], я сначала посмотрю на [1,2,1], а затем на [2,1,2].

Или, в этом более длинном примере:

[1,2,1,2,2,1,1] => [1,2,1]
[2,1,2,2,1,1] => [2,1,2]
[1,2,2,1,1] => [1,2,2]
[2,2,1,1] => [2,2,1]
[2,1,1] => [2,1,1]

Как только в списке будет только 2 элемента, я могу остановиться.

Я предполагаю, что каждый из списка из трех значения - это ваши [Elt1, Elt2, Elt3].

Чтобы вычислить это, нам нужны входной список и выходная сумма, но для рекурсии вниз по списку нам нужен аккумулятор, чтобы отслеживать текущую сумму, поскольку мы go. Первый предикат прост:

compute(List,Sum) :- compute(List,0,Sum).

Теперь у вас есть 5 предикатов, которым мы должны сопоставить.

  1. список, содержащий 2 элемента - мы можем вернуть наш аккумулятор
  2. Elt1 = Elt2 затем sum = sum + (elt1 + elt2)
  3. Elt1 = Elt3 затем sum = sum + (elt1 * elt3)
  4. Elt2 = Elt3 и Elt3 \= 0 затем sum = sum + (100 / elt3)
  5. Ничего из вышеперечисленного поэтому мы просто передаем текущий аккумулятор, т.е. sum = sum
compute([_,_],Sum,Sum).

compute([Elt1,Elt2,Elt3|Tail],AccNow,Sum) :-
    Elt1 = Elt2,
    !,
    AccNext is AccNow + Elt1 + Elt2,
    compute([Elt2,Elt3|Tail],AccNext,Sum).

compute([Elt1,Elt2,Elt3|Tail],AccNow,Sum) :-
    Elt1 = Elt3,
    !,
    AccNext is AccNow + Elt1 * Elt3,
    compute([Elt2,Elt3|Tail],AccNext,Sum).

compute([_,Elt2,Elt3|Tail],AccNow,Sum) :-
    Elt3 \= 0,
    Elt2 = Elt3,
    !,
    AccNext is AccNow + 100 / Elt3,
    compute([Elt2,Elt3|Tail],AccNext,Sum).

compute([_,Elt2,Elt3|Tail],Acc,Sum) :-
    compute([Elt2,Elt3|Tail],Acc,Sum).  

Если я попробую это на ?- compute([1,2,1,2],X)., то получу X = 5. Это совпадает с предикатом Elt1 = Elt3 и дает мне 0 + 1 * 1, а затем снова по предикату Elt1 = Elt3 дает мне 1 + 2 * 2 или 5.

Если я попробую это на ?- compute([1,2,1,2,2,1,1],X)., я получу X = 159. Я оставлю это вам, чтобы убедиться, что это правильный результат.

Просто имейте в виду, что все, что пытается сделать Prolog, - это успех. Если его просят доказать цель (например, compute/3), он находит первый совпадающий предикат и пытается доказать это (путем доказательства любых подцелей), а когда он терпит неудачу, он просто возвращается к предыдущей точке выбора и пробует другой выбор и продолжает. Если это доказывает первоначальную цель, значит, она успешна. Если этого не произошло, то это не удалось. Нет возвращаемых значений - только связанные переменные.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...