Студопедия
Новини освіти і науки:
МАРК РЕГНЕРУС ДОСЛІДЖЕННЯ: Наскільки відрізняються діти, які виросли в одностатевих союзах


РЕЗОЛЮЦІЯ: Громадського обговорення навчальної програми статевого виховання


ЧОМУ ФОНД ОЛЕНИ ПІНЧУК І МОЗ УКРАЇНИ ПРОПАГУЮТЬ "СЕКСУАЛЬНІ УРОКИ"


ЕКЗИСТЕНЦІЙНО-ПСИХОЛОГІЧНІ ОСНОВИ ПОРУШЕННЯ СТАТЕВОЇ ІДЕНТИЧНОСТІ ПІДЛІТКІВ


Батьківський, громадянський рух в Україні закликає МОН зупинити тотальну сексуалізацію дітей і підлітків


Відкрите звернення Міністру освіти й науки України - Гриневич Лілії Михайлівні


Представництво українського жіноцтва в ООН: низький рівень культури спілкування в соціальних мережах


Гендерна антидискримінаційна експертиза може зробити нас моральними рабами


ЛІВИЙ МАРКСИЗМ У НОВИХ ПІДРУЧНИКАХ ДЛЯ ШКОЛЯРІВ


ВІДКРИТА ЗАЯВА на підтримку позиції Ганни Турчинової та права кожної людини на свободу думки, світогляду та вираження поглядів



Заперечення як невдача. (not as failure)

Три предикати ARITY-prologa.

Get0(X)

Get(X)

Put(X)

Заперечення як невдача (not as failure)

Швидке сортування quick.

Метод вставки.

Декларативний опис:

Для того щоб упорядкувати не порожній список L=[X|T] необхідно:

Впорядкувати хвіст Т списку L

Вставити голову X списку L в впорядкований хвіст, помістивши її таким чином, щоб список, що вийшов,

залишився упорядкованим.

insort([], []).

insort([X|L], M) :- insort(L, N), insortx(X, N, M).

insortx(X, [A|L], [A|M]) :- order(A, X), !, insortx(X, L, M).

insortx(X, L, [X|L]).

order(X, Y) :- X =< Y.

Опис методу:

Забираємо перший елемент:

5 3 7 8 1 4 7 6

одержуємо: X =5.

і список, що залишився:

3 7 8 1 4 7 6

Розбиваємо новий список на два, поміщаючи в перший елементи менше X, а в другий - більше X:

( X: 3 1 4 ) X: 7 8 7 6

Сортуємо обидва списки:

1 3 4 6 7 7 8

З'єднаємо перший список, X, другий список.

1 3 4 5 6 7 7 8

Декларативний опис:

Видалити зі списку голову Х и розбити список, що залишився, на два списки Small і Big у такий спосіб: всі

елементи більші ніж Х містяться в Big і менші X - у Small.

Відсортувати список Small у Small1.

Відсортувати список Big у Big1.

З'єднати списки Small1 Х и Big1.

qsort([], []).

qsort([H|Tail], S) :- split(H, Tail, Small, Big), qsort(Small, Small1), qsort(Big, Big1), append(Small1, [H|Big1], S).

order(X, Y) :- X =< Y.

split(H, [A|Tail], [A|Small], Big) :- order(A, H), !, split(H, Tail, Small, Big).

split(H, [A|Tail], Small, [A|Big]) :- split(H, Tail, Small, Big).

split(_, [], [], []).


Лекція 6

Вбудовані предикати. Пошук на Пролозі.

Зміст

6.2. Алгоритм пошуку в пролозі

6.3. Читання і запис інформації з файлів

6.3.1. Обробка вхідних потоків

6.3.2. Обробка вихідних потоків

6.4. Обробка символів

 

Розглянемо спочатку приклад.

Нехай деяка Мери любить усіх тварин.

Це записується:

likes(mary,X):-annimal(X).

Мери не любить змій:

likes(mary,X):-snake(X),!,fail.

fail - спеціальна мета, вбудований предикат,

що завжди зазнає невдачі.

Графічно предикат зображується:

Можна записати у вигляді одного правила, використовуючи

диз’юнкцію цілей.

likes(mary,X):-snake(X),!,fail; annimal(X).

Подивимося інший приклад.

Відношення different(X,Y) буде істина, якщо X і Y різні. (не порівнянні).

different(X,X):-!,fail.

Або

different(X,Y):-X=Y,!,fail.

different(X,Y).

Якщо X і Y порівнянні, то ціль different зазнає невдачі.

Інакше X і Y різні, і ціль different успішна.

Або в одній пропозиції

different(X,Y):-X=Y,!,fail;true.

Тут true - убудований предикат, що завжди істина.

І в тому і в іншому випадку більш зручно вказувати, що відношення істинне, якщо ціль помилкова.

Для цієї мети використовується предикат not.

not(Goal). -істина, якщо Goal -неправда, і навпаки not(Goal) помилкове, якщо Goal успішна.

Це можна записати:

not(Goal):-Goal,!,fail;true.

Запис аналогічний зробленим, тому наші приклади можна переписати:

likes(mary,X):-annimal(X),not(snake(X)).

Або

different(X,Y):-not(X=Y).

Використання not вимагає обережності, тому що визначається через січення.

Розглянемо приклад:

r(a).

g(b).

p(X):-not(r(X)).

?-g(X),p(X).

yes

?-p(X),g(X).

no.

6.2 Алгоритм пошуку на Пролозі.

(Логічний підхід до задачі про фермера, вовка, козу і капусті.)

Задача полягає в наступному:

Фермер ( Farmer ), вовк ( Wolf ), коза ( Goat ) і капуста ( Cabbidge ) знаходяться на одному березі. Треба

перебратися на інший берег на човні. Човен перевозить тільки двох. Не можна залишати на одному березі

козу і капусту, козу і вовка.

Головна проблема у формуванні алгоритму - знайти ефективне представлення структурою даних Ліспа

інформації про задачу.

Процес перевезення може бути представлений послідовністю станів. Стан представляється відношенням

state c 4 аргументами, кожний з яких відбиває розміщення об’єктів F,W,G,S:

Farmer

Wolf

Goat

Cabbidge

state(e, w, e, w) - F,G in east side (e - east);

F W G C W,C in west side (w - west).

Програма, що залишилася, ґрунтується на цих предикатах. Зокрема, вони використовуються для реалізації

чотирьох можливих дій фермера, виражених у перевозі фермера через ріку:

самого себе

W

G

C

Предикат opposite (визначений пізніше) визначає нове розміщення об'єктів, що перетнули річку.

move(state(X,X,G,C),state(Y,Y,G,C)):-opposite(X,Y). /* FARMER + WOLF */

move(state(X,W,X,C),state(Y,W,Y,C)):-opposite(X,Y). /* FARMER + GOAT */

move(state(X,W,G,X),state(Y,W,G,Y)):-opposite(X,Y). /*FARMER + CABBIDGE*/

move(state(X,W,G,C),state(Y,W,G,C)):-opposite(X,Y). /* ONLY FARMER */

Тепер можна визначити предикат opposite, що визначає іншу сторону.

opposite(east,west).

opposite(west,east).

Предикат unsafe визначений для перевірки двох небезпечних станів:

F знаходиться на протилежному березі від W,G

F знаходиться на протилежному березі від G ,C.

unsafe( state(F,X,X,_) ):- opposite(F,X).

/* The wolf eats the goat */

unsafe( state(F,_,X,X) ):- opposite(F,X).

/* The goat eats the cabbage */

path тепер визначається:

path(S,G,L,L1):-

move(S,S1),

not( unsafe(S1) ),

not( member(S1,L) ),

path( S1,G,[S1|L],L1),!.

path(G,G,T,T):-!. /* The final state is reached */

Для рішення можна використовувати:

go:- go(state(east,east,east,east),state(west,west,west,west)).

go(S,G):-

path(S,G,[S],L),

nl,write('A solution is:'),nl,

write_path(L),

fail.

go(_,_).

Для організації зручної форми висновку використані наступні процедури:

member(X,[X|_]).

member(X,[_|L]):-member(X,L).

write_move( state(X,W,G,C), state(Y,W,G,C) ) :-!,

write('The farmer crosses the river from '),

write(X),

write(' to '),

write(Y),nl.

write_move( state(X,X,G,C), state(Y,Y,G,C) ) :-!,

write('The farmer takes the Wolf from '),

write(X),

write(' of the river to '),

write(Y),nl.

write_move( state(X,W,X,C), state(Y,W,Y,C) ) :-!,

write('The farmer takes the Goat from' ),

write(X),

write(' of the river to '),

write(Y),nl.

write_move( state(X,W,G,X), state(Y,W,G,Y) ) :-!,

write('The farmer takes the cabbage from '),

write(X),

write(' of the river to '),

write(Y),nl.

write_path( [H1,H2|T] ) :- !,

write_move(H1,H2),write_path([H2|T]).

write_path( _ ).

Сама програма набагато коротше програми на ліспі.

6.3 Читання і запис інформації з файлів.

При введенні і виведенні інформації в пролозі використовується поняття потоків.

Файли для читання - це вхідні потоки.

Файли для запису - це вихідні потоки.

Для користувача визначені два потоки:

інформація вводиться з клавіатури - вхідний потік.

інформація виведена на монітор - вихідний потік.

Ці потоки є псевдофайлами з ім'ям user.

У кожний момент часу для прологу активні два файли:

для введення - поточний вхідний потік.

для висновку - поточний вихідний потік.

За замовчуванням ці потоки - користувацький термінал user.

6.3.1 Обробка вхідних потоків.

Вхідні потоки пролог "бачить".

Тому визначені наступні предикати:

see(F) - відкриває файл F, наприклад 'a.dat' і він стає поточним вхідним потоком.

seeing(F) - зв'язує F з ім'ям файлу, що є поточним вхідним потоком.

seen - закриває поточний вхідний потік і зв'язує його з user.

Ілюстрація SEE

Ілюстрація SEEN

Приклади:

p1:-see('a.dat'),read(X),write(X),seen.

p2:-see('a.dat'),seeing(F),write(F),seen,

read(A),write(A).

6.3.2 Обробка вихідних потоків.

У вихідні потоки пролог "говорить".

tell(F) - відкриває файл F як поточний вихідний потік. Якщо файлу ні, то створює його.

telling(F)- зв'язує F з ім'ям файлу, що є поточним вихідним потоком.

told - закриває файл, що є поточним вихідним потоком. Поточним вихідним потоком стає user.

Приклад:

p3:- tell('a.dat'),write(a),told,write(a).

6.4 Обробка символів.

Пролог має кілька предикатів для обробки символів.


Читайте також:

  1. Закон заперечення заперечення.
  2. ЗАПЕРЕЧЕННЯ ДЕЯКОМУ НЕУКОВІ Б ОБЛАСТІ ДІАЛЕКТИКИ
  3. Зв'язок між запереченням і доповненням
  4. Моральне виховання, на думку Д.Локка, як і фізичне, є процес загартування, підпорядкування бажань контролю розуму, утворення звичок шляхом постійного заперечення природних бажань.
  5. На нашу думку, визнання кари сутністю покарання зовсім не означає заперечення виховних властивостей останнього але лише стосовно окремих особистостей.




Переглядів: 950

<== попередня сторінка | наступна сторінка ==>
Метод пухирця. | ТВЕРДА ГРУПА

Не знайшли потрібну інформацію? Скористайтесь пошуком google:

  

© studopedia.com.ua При використанні або копіюванні матеріалів пряме посилання на сайт обов'язкове.


Генерація сторінки за: 0.02 сек.