Ошибка визуального пролога c502: выражение не дает значения

Я пытаюсь перевести простую проблему Turbo Prolog в Visual Prolog 7.1

Оригинальный код Turbo Prolog следующий.

    DOMAINS
            s=string   sl=s*  sll=sl*

    PREDICATES
            select(sl,s,sl)
            solve(sll)

    CLAUSES

            select([A|B],A,B).
            select([A|B],C,[A|D]):- select(B,C,D).

            solve([["Anna",A,A],["Kate",Vp,Vt],                ["Natasha",Np,"green"]]):-
                    select(["white","green","blue"],A,ColPl),
                    select(["white","blue"],A,[Vt]), Vt<>"white",
                    select(ColPl,Vp,[Np]), Vp<>"white", Np<>"green".

И его результирующий список выводится с solve(Out) с обеспечивает правильный результат для консоли Turbo Prolog.

При попытке перевести это в Visual Prolog, я получаю ошибку c502 в строке 33.

    implement main
        open core

    constants
        className = "main".
        classVersion = "".
    domains
    s=string.
    sl=s*.
    sll=sl*.
    %
    class predicates
    select:(sl,s,sl) nondeterm anyflow.
    solve:(sll) nondeterm anyflow.
    %
    clauses
    %
    select([A|B],A,B).
    select([A|B],C,[A|D]):- select(B,C,D).
    %
    solve([["Anna",A,A],["Kate",Vp,Vt],["Natasha",Np,"green"]]):-
    select(["white","green","blue"],A,ColPl),
    select(["white","blue"],A,[Vt]), Vt<>"white",
    select(ColPl,Vp,[Np]), Vp<>"white", Np<>"green".

    clauses
        classInfo(className, classVersion).

    clauses
        run():-
            console::init(),
            %ERROR AFTER THIS LINE
            stdIO::writef("%", solve(Out)),fail().

    end implement main

    goal
        mainExe::run(main::run).

Что я получаю от этой ошибки, так это то, что solve(Out) не дает ничего печатать. Чего я не знаю, так это как изменить код, чтобы создать что-то для печати.

Я новичок в Прологе, и я не могу понять, как решить эту проблему, и Google тоже не очень помогает, кажется, это очень непонятная проблема.

Спасибо!

1 ответ

Решение

Я не знаком с Visual Prolog, но не могли бы вы переписать оскорбительную строку следующим образом:

solve(Out), stdIO::writef("%", Out),fail().

и попробуй еще раз?

Помните, что предикаты не являются функциями, как в других языках программирования; они не имеют возвращаемого значения.

РЕДАКТИРОВАТЬ, чтобы ответить на комментарий: предикат процедуры должен завершиться ровно один раз. Вот, main зовет ваш solve функция, которая может быть неудачной или успешной несколько раз. Чтобы убедиться в этом, вы можете попытаться заключить вызов для решения в другой предикат:

wrap_solve(S) :- solve(S), !.
wrap_solve([]).

Разрез после звонка solve следует убедиться, что вы получите только одно решение, если это удастся. Если нет решения (например, вызов solve терпит неудачу), тогда второе предложение даст значение по умолчанию (пустой список в этом случае).

В mainпозвони wrap_solve вместо solve,

Другие вопросы по тегам