LINUX.ORG.RU

Prolog


0

0

День добрый. Есть необходимость использования языка prolog (нет, зачетная сессия еще не началась :) ), сам язык потихоньку осваиваю по книге И.Братко «Программирование на языке ПРОЛОГ для исскуственного интеллекта», но разобраться в swi-prolog и gnu-prolog никак не могу. Подкиньте документацию к этим компиляторам пожалуйста, желательно на русском.И было бы неплохо узнать структуру программ на диалектах для этих компиляторов, может кто подскажет?

★★

Об Братко весь мозг сломаешь, для начала попроще бы что-нибудь нашёл. А с swi-prolog'ом раньше нормальная документация шла, на английском, правда. Но я не специалист, с универа пролог не видел. А в чём проявляется «необходимость» использовать именно пролог?

Gvidon ★★★★
()
Ответ на: комментарий от Dikar

>Необходимость обуславливается курсом логического программирования в институте:)
исчо раз всем рекомендую, если препод не заинтересован что-то интересное рассказать, то надо сдать как можно быстрее лабы и попробовать досрочно сдать экзамен, на оставшееся время можешь делать, что хочешь.

dimon555 ★★★★★
()

Дык к преподу подойди. Он только рад будет увидеть студента, который собирается делать лабы по прологу сам :) И должны же у вас семинары какие-нибудь быть, не на листочке же вы там проги пишете.

Gvidon ★★★★
()

Сюрприз! Документация идет в составе самих gprolog и swi-prolog. Так же как и исходники, которые есть лучшая документация. Русский язык не нужен, на нем все равно ничего никогда нет.

lisprocks
()

Кстати, лучший способ изучить Пролог - это написать интерпретатор Пролога. Хороший пример был в дистрибутиве Hugs, там сразу два разных коротеньких интерпретатора.

Для более глубокого понимания надо читать про WAM.

lisprocks
()
Ответ на: комментарий от Gvidon

Препод кроме C-Prolog, Turbo Prolog и VisualProlog ничего не использовал, сам попросил притащить SWI-Prolog или GProlog. Лабы мы пишем на Turbo-Prolog, структура программы которого отличается от SWI-Prolog довольно сильно.

Dikar ★★
() автор топика
Ответ на: комментарий от lisprocks

Полистал офф-мануал с сайта SWI-Prolog, полноценных примеров не нашел, только сама документация. Дайте пруф плиз.

Dikar ★★
() автор топика
Ответ на: комментарий от lisprocks

Насколько я знаю , книга Братко для пролога столь же монументальна как K&R для Си, вот дочитаю и посмотрим стоит ли дальше изучать этот язык.

Dikar ★★
() автор топика
Ответ на: комментарий от Dikar

Дожили. Мануалы народ уже на сайтах ищет.

apt-get install swi-prolog (или что там у тебя)

И смотри документацию в установленном. Она в составе дистрибутива идёт. Вместе с примерами. Кроме того, там же есть и исходники, которые лучше всякой документации и лучше синтетических примеров.

lisprocks
()
Ответ на: комментарий от Dikar

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

Пролог надо понимать на уровне, достаточном для полноценной реализации его интерпретатора или компилятора. И использовать эти знания при нормальном, кошерном программировании. Большинство систем принятия решений, rule-based systems и тому подобного, что пишется на Java и прочих C#, по сути, является реализациями подмножеств Пролога. И по этому его и необходимо понимать, и на фиг не надо писать на самом Прологе.

lisprocks
()
Ответ на: комментарий от lisprocks

А нафига пролог-то тогда? Ботаешь себе спокойненько матлогику, предикаты там всякие и живёшь счастливо.

Gvidon ★★★★
()
Ответ на: комментарий от Gvidon

> А нафига пролог-то тогда? Ботаешь себе спокойненько матлогику, предикаты там всякие и живёшь счастливо.

Пролог - это и есть логика предикатов первого порядка + алгоритм разрушительной унификации с cut-ом и бектрекингом.

Поймешь реализацию этого алгоритма - поймешь и пролог, и дейталог, и все производные системы. Ничего другого в нем просто нет.

lisprocks
()
Ответ на: комментарий от lisprocks

Как человек, судя по всему разбирающйся в теории, не могли бы вы на пальцах пояснить почему именно дизъюнкты Хорна легли в основу Пролога?

mclaudt
()
Ответ на: комментарий от Gvidon

>Об Братко весь мозг сломаешь, для начала попроще бы что-нибудь нашёл.
Братко как раз пишет на редкость доступно и просто. Очень советую.

А структура программы в SWI Prolog такая же, как в примерах Братко. Без всех этих секций аля Паскаль.

Документация http://www.swi-prolog.org/pldoc/index.html , вверху - справочник на английском. Можешь еще в самом прологе набрать

?- help.

получив тот же справочник, только в окне справки. И, заодно,

?- emacs.

ipc
()

>но разобраться в swi-prolog и gnu-prolog никак не могу.
Что конкретно вызывает затруднения?

ipc
()
Ответ на: комментарий от ipc

конкретно после Turbo Prolog было непонятно хотябы-то как компилировать программу.Было неясно нужны ли пресловутые domainc, constants, goals и прочие секции в начале программы. И т.д.

Dikar ★★
() автор топика
Ответ на: комментарий от mclaudt

Спасибо, но книжка мне ближе, а лекции и так хорошие и понятные читают.)

Dikar ★★
() автор топика
Ответ на: комментарий от Gvidon

Пролог плюс к тому что нужен в универе, довольно интересен и очень локаничен. При этом на нем удобнее чем на большинстве других языков писать экспертные системы. Последнее я узнал от препода, но после 2 недель изучения языка в этом все больше уверяюсь.

Что за взгляды такие странные? Выучили 2-3 самых популярных языка (читай C,C++,Java) , на большее не хватило терпения, а везде твердят что декларативные языки не нужны...Странные люди...

Dikar ★★
() автор топика
Ответ на: комментарий от ipc

А как у вас происходило постижение сути Пролога?

Открылась ли структурная простота и обоснованность, или же просто свыклись, по принципу стерпится-слюбится?

Так почему же именно хорновские дизъюнкты-то?

mclaudt
()
Ответ на: комментарий от mclaudt

>А как у вас происходило постижение сути Пролога?
У меня было сугубо учебно-практическим по мере понимания, как всё работает.

ipc
()
Ответ на: комментарий от Dikar

> Что за взгляды такие странные? Выучили 2-3 самых популярных языка (читай C,C++,Java) , на большее не хватило терпения, а везде твердят что декларативные языки не нужны...Странные люди...
Я не говорил, что декларативные языки не нужны. Но сфера применения пролога довольно не велика, и прежде, чем на нём писать что-то кроме лаб по нему, неплохо бы подумать, а нужно ли оно тебе.

Gvidon ★★★★
()
Ответ на: комментарий от Gvidon

Изучить парадигму полезно вне зависимости от того будешь ли ты использовать именно её, возможность в будущем посмотреть на задачу с другой стороны возможно будет уже частью решения задачи.

Dikar ★★
() автор топика
Ответ на: комментарий от ipc

Есть 2 практически одинаковых предиката:

father(X,Y):-
	roditel(X,Y),
	man(X).

mother(X,Y):-
	roditel(X,Y),
	woman(X).

но их вывод разнится:

?- mother(X,k).
X = g ;
false.

?- father(X,k).
X = v.

Почему father пишет просто X=v, а mother еще и какой-то false?

И еще вопрос: как запускать пролог программы прямо из emacs? Нажимаю С-с С-b , от крывается окно с приветствием swi-prolog, но сделать ничего не получается:

For help, use ?- help(Topic). or ?- apropos(Word).

?- |: |: help(dif).
|: father(X,k).
Warning: user://1:12:
	Singleton variables: [X]
|: ?-father(X,k).
Warning: user://1:15:
	Singleton variables: [X]
|: 

Dikar ★★
() автор топика
Ответ на: комментарий от Dikar

>>Почему father пишет просто X=v, а mother еще и какой-то false?

Там если после первого вывода нажать ; то она продолжит искать и порой натыкается на false, а если Enter то остановится на достигнутом.

mclaudt
()
Ответ на: комментарий от Dikar

>Почему father пишет просто X=v, а mother еще и какой-то false?
На самом деле никакой разницы здесь нет.

Вначале ты вводишь

?- mother(X,k).

и получаешь

X = g <ожидание ввода>

Здесь тебе предлагается выбрать следующее действие. Можешь попробовать нажать h - получишь справку по тому, что можешь вводить.
Ввод "." - завершить поиск подходящих значений.
Ввод ";" - продолжить.
Поскольку другого значения нет, получаешь false.

И еще вопрос: как запускать пролог программы прямо из emacs?

C-c C-b и вводишь свои _запросы к Прологу_ в консоли. Объяви какой-нибудь «go», и вызывать его чтобы меньше писать. Может, есть какое-то предопределенное имя для цели по-умолчанию, не разбирался. В GNU Prolog кстати, есть, и бинарник можно даже получить.

Singleton variable он пишет оттого, что переменная X в твоем коде больше не используется. Код и консоль Пролога - две разные вещи. Во втором случае оболочка сама выводит тебе значения и т. п.

ipc
()
Ответ на: комментарий от mclaudt

Но вот понять почему в одних случаях она выводит false а в других нет — это в доках пока не нашел.

Видать, как-то связано в ветвлением, если она после нажатия клавиши ; она не попробовала ни одной подстановки то ничего не выводится (как и в случае с Enter), а если попробовала, но неудачно, то fail.

(в swi это вроде называется fail а не false)

mclaudt
()
Ответ на: комментарий от ipc

У меня все то же только вместо false стоит fail.

Разработчики опять на ровном месте всех запутали, ни хрена не продкуоментировав эпохальные изменения...

mclaudt
()
Ответ на: комментарий от mclaudt

>Видать, как-то связано в ветвлением, если она после нажатия клавиши ; она не попробовала ни одной подстановки то ничего не выводится (как и в случае с Enter), а если попробовала, но неудачно, то fail.

Почти верно. Это связано с точками возврата: они или остаются после очередного успешного доказательства, или нет. При нажатии ";" происходит откат к последней такой точке (прямо как если бы в этом месте стоял false) и процесс доказательства начинается с того места по альтернативному пути. Это доказательство может обломаться и тогда получим 'false.' на экране. Ну а если точек не осталось, то и спрашивать как-бы не о чем - процесс доказательства окончен (иногда в конце пишется 'true.').

Чтобы понять, чем предикат false отличается от fail, надо попробовать выполнить listing(false).

anonymous
()
Ответ на: комментарий от mclaudt

Если тебя смущает напечатанный список символов вместо собственно текста, то дело не в false/fail, конечно же, а в кавычках. Одиночные кавычки - это атомы, двойные - строки (которые суть то же самое, что и списки символов).

anonymous
()
Ответ на: комментарий от anonymous

Спасибо, так и понимал.

Чтобы понять, чем предикат false отличается от fail, надо попробовать выполнить listing(false).

Нет такого. Вопреки всей логике, главную пару констант образуют не true и false, а true и fail. False даже нету в документации.

mclaudt
()
Ответ на: комментарий от anonymous

Ага,с кавычками-то ясно — это не вопрос.

Короче, при переходе от 5.6.54 к 5.6.64 они поменяли true/fail на true/false.

mclaudt
()
Ответ на: комментарий от mclaudt

>Вопреки всей логике, главную пару констант образуют не true и false, а true и fail. False даже нету в документации. Если речь о предикатах, то не «вопреки логике», а «согласно iso стандарту», там прописан именно fail. false определен в swi тривиальным образом как (false :- fail). Когда его туда ввели я не обратил внимания, у меня сейчас 5.8.0 стоит и он там есть. А если речь о том, что там печатается на экране, то это дело десятое. В YAP, например, вообще 'yes/no'.

anonymous
()
Ответ на: комментарий от anonymous

«согласно iso стандарту», там прописан именно fail. false определен в swi тривиальным образом как (false :- fail).

Ок, вопрос снят.

Тут вспомнил ещё одну «фичу»— обидно что не работает подборка списков некольких вложенностей.


?- flatten(X,[a,b,c]).
fail.

А так хочется чтоб она вернула все возможные [[a,b],c], [[[a]],,c] …

Понятно что комбинаторный взрыв но ведь можно установить предельную глубину.

mclaudt
()
Ответ на: комментарий от mclaudt

Так почему же именно хорновские дизъюнкты-то?

Потому что резолютивное опровержение на хорновских КНФ имеет гарантированно полиномиальную сложность. А чем тебя так беспокоит «хорновскость» пролога?

twosev ★★
()
Ответ на: комментарий от twosev

>>Потому что резолютивное опровержение на хорновских КНФ имеет гарантированно полиномиальную сложность.

А зачем ограничиваться резолютивным опровержением? Если все сводится к причесыванию НФ, так существует куча методов их упрощения, и если не ограничиваться одним методом то причесать можно оптимальнее? (Общая задача останется полиномиальной, не спорю)

А чем тебя так беспокоит «хорновскость» пролога?

Что-то мне подсказывает что благодаря двойственности конъюнкции и дизъюнкции должна существовать подобная система, основанная на другой операции.

Метод резолюций — это всего лишь вычёсывание катышков-«тавтологий» вида A⋁¬A из некой промежуточной дизъюнктивной формы.

Должен тогда существовать метод, основанный на вычёсывании катышков-«противоречий» вида A⋀¬A из некой промежуточной коньюнктивной формы.

mclaudt
()
Ответ на: комментарий от mclaudt

Хотя, наверное, с точностью до переобозначения true и false это будет один и тот же метод.

mclaudt
()
Ответ на: комментарий от mclaudt

> Если все сводится к причесыванию НФ...

Метод резолюций — это всего лишь вычёсывание катышков-«тавтологий»...

Метод резолюций - это метод логического вывода, использующий правило резолюций (и только). К причесыванию НФ здесь ничего не сводится. Каков вообще смысл резолютивного вывода и принцип работы пролога?

Ты ставишь перед прологом задачу проверки истинности определенного утверждения в некоторой системе аксиом. Он решает эту задачу при помощи метода резолюций (фактически, методом от противного).

Грубо говоря, происходит следующее. Предложениями вида «D :- A, B, C.» ты задаешь истинные утверждения «A & B & C -> D», что на нормальном языке можно записать как «¬A V ¬B V ¬C V D» (хорновский дизъюнкт). Определяя таким образом A, B и т. д., ты формируешь КНФ, составленную только из дизъюнктов указанного вида. Затем к КНФ приписываются все посылки и отрицание логического следствия (идеология метода доказательства от противного), которое необходимо проверить. Таким образом, получается КНФ, составленная только из хорновских дизъюнктов. Если пролог методом резолюций по данной КНФ далее выводит пустой список дизъюнктов, то этот факт означает false. В противном случае, имеем true. Вот и всё (пример, конечно, прост, и объяснения касаются пропозициональной логики - в первопорядковой логике всё сложнее, однако смысл вывода тот же).

При этом нетрудно показать, что на хорновских КНФ резолютивный вывод полиномиален от длины входных данных. Однако никаких полиномиальных оценок для метода резолюций на КНФ, заданных в общем виде, нет и не может быть в предположении, что P != NP (в первопорядковой логике вообще ничего нельзя сказать).

Изначальное ограничение «хорновости» пролога (я не знаю, как сейчас обстоят дела) состоит лишь в невозможности задать предложения вида «D, E, F :- A, B, C.» (то есть в одном предложении допустимо не более одного следствия). Ну, и как уже должно быть понятно из всего вышесказанного, данное ограничение обусловлено эффективностью метода резолюций на данном классе КНФ.

Как-то так.

twosev ★★
()
Ответ на: комментарий от ipc

>C-c C-b и вводишь свои _запросы к Прологу_ в консоли. Объяви какой-нибудь «go», и вызывать его чтобы меньше писать. Может, есть какое-то предопределенное имя для цели по-умолчанию, не разбирался.

Разве то что вводил - не запросы к Прологу?

можно хотя-бы пример подобного запроса?

А то везде как-то работает «roditel(X,k).» (В консоли после swipl /path/to/file работает, в Turbo-prolog - работает, в GNU Prolog - работает), а в emacs - нет.

Dikar ★★
() автор топика
Ответ на: комментарий от Dikar

>можно хотя-бы пример подобного запроса?
в emacs:

a(1).
a(2).
a(3).

test2 :- a(X), write(X), nl, fail.

Запрос в консоли:

?- a(X).
X = 1 ;
X = 2 ;
X = 3 ;
true.

А то везде как-то работает «roditel(X,k).» (В консоли после swipl /path/to/file работает, в Turbo-prolog - работает, в GNU Prolog - работает), а в emacs - нет.

Ну и я пишу, что в консоли это работает, а в файле(в том числе, редактируемом в emacs) нет... Или в чем вопрос?

localhost$ pl -f test.pl -g test2
% test.pl compiled 0.00 sec, 1,456 bytes
1
2
3
[49]
% halt

ipc
()
Ответ на: комментарий от ipc

Проблема с emacs решена, точнее она решилась сама собой: после приветствия появились обычные консольные запросы (?-) а не то что было (?- :| :| ).

Если не трудно разъясните смысл строки

test2 :- a(X), write(X), nl, fail.

a(X) и write(X) понятны, но зачем некий nl и fail ?

Dikar ★★
() автор топика
Ответ на: комментарий от Dikar

>>но зачем некий nl и fail ?

На такие вещи лучше учиться отвечать самому.

nl — new line, не имеющая отношения к работе пролога приблуда для выдачи новой строки.

fail объясняли выше.

mclaudt
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.