63
1 Gabriel David FEUP - Rua dos Bragas, 4099 Porto Codex - PORTUGAL Tel. 351-2-2041842 - Fax: 351-2-2059280 Email: [email protected] URL: http://www.fe.up.pt Programação em Lógica Programação em Lógica • Programas em Lógica • Prolog • Técnicas de programação

Programação em Lógica

  • Upload
    ronnie

  • View
    81

  • Download
    5

Embed Size (px)

DESCRIPTION

Programação em Lógica. Programação em Lógica • Programas em Lógica • Prolog • Técnicas de programação. Gabriel David FEUP - Rua dos Bragas, 4099 Porto Codex - PORTUGAL Tel. 351-2-2041842 - Fax: 351-2-2059280. Email: [email protected] URL: http://www.fe.up.pt. Lógica e computadores. Lógica - PowerPoint PPT Presentation

Citation preview

Page 1: Programação em Lógica

1

Gabriel DavidFEUP - Rua dos Bragas, 4099 Porto Codex - PORTUGALTel. 351-2-2041842 - Fax: 351-2-2059280

Email: [email protected]: http://www.fe.up.pt

Programação em Lógica

Programação em Lógica

• Programas em Lógica• Prolog• Técnicas de programação

Page 2: Programação em Lógica

Prolog - 2

Lógica e computadores

Lógica linguagem precisa para a expressão dos objectivos, conhecimento e

assunções fundamento para a dedução de consequências a partir de premissas limitada apenas pela capacidade humana de raciocínio

Computadores também requerem uma formulação precisa de objectivos e

assunções dificuldades iniciais de construção desenho da linguagem de

instrução das máquinas dominada pelo hardware seguiram-se linguagens cada vez mais abstractas, mas

essencialmente baseadas na arquitectura de von Neumann

Page 3: Programação em Lógica

Prolog - 3

Paradigma

Programação em Lógica derivada de um modelo abstracto, natural para o raciocínio

humano, independente de máquinas concretas exprimir o conhecimento relevante e as assunções como axiomas

lógicos; formalizar o problema como uma expressão lógica a ser provada a partir dos axiomas

Exemplo - conhecimento (dois axiomas):1 humano(Sócrates)2 x humano(X) mortal(X)

problemamortal(Sócrates)?

Sim! É uma consequência lógica dos axiomas eliminação do universal e modus ponens

Page 4: Programação em Lógica

Prolog - 4

Fundamento

1965 Robinson: Princípio da Resolução base matemática das provas desenvolvida no contexto dos

sistemas de demonstração de teoremas Cláusula de Horn

A se B1, B2, ..., Bn

Leitura declarativa A é verdadeiro se todos os Bi's forem verdadeiros

Conhecimento: conjunto de cláusulas de Horn Sistema de inferência

prova construtiva de um golo a partir dos axiomas só baseada no algoritmo da unificação e no princípio da resolução

Page 5: Programação em Lógica

Prolog - 5

Origens

1970's Kowalski: leitura procedimental da cláusula de Horn: para resolver/executar A, resolver/executar B1 e B2 e ... Bn

A é visto como a cabeça de um procedimento e os Bi's o corpo 1970's Colmerauer (Marselha): implementação

sistema demonstrador de teoremas chamado Prolog (Programmation en Logique)

1978/79 Edinburgo primeiras implementações eficientes de Prolog; estabelecimento

de um estilo 1981 projecto japonês da Quinta Geração de

Computadores construir máquinas para executar directamente Prolog

Page 6: Programação em Lógica

Prolog - 6

Programa em Lógica

Programa em Lógica - conjunto de axiomas ou regras (cláusulas de Horn) que definem relações entre objectos

Computação - dedução de consequências do programa

Significado do programa - conjunto de consequências definido pelo programa

Arte da Programação em Lógica - construir programas concisos e elegantes, que tenham o significado pretendido

Page 7: Programação em Lógica

Prolog - 7

A interpretação é convencional, mas essencial para a compreensão da formulação do problema.

Factos

relação ou predicado gosta objectos ou indivíduos joao, maria facto gosta( joao, maria ). interpretação O João gosta da Maria.

Notas: nada se diz sobre o recíproco nomes de predicados e de objectos começam com minúscula

(átomos) predicados primeiro, objectos em lista ordenada ponto final

Page 8: Programação em Lógica

Prolog - 8

soma( 0, 0, 0 ).soma( 0, 1, 1 ).soma( 0, 2, 2 );soma( 1, 0 ,1 ).soma( 1, 1, 2 ).

Família

Soma

Um conjunto de factos é um programa descreve uma situação.

Programas simples

pai( terach, abraao ). macho( terach ).pai( terach, nachor ). macho( abraao ).pai( terach, haran ). macho( nachor ).pai( abraao, isaac ). macho( haran ).pai( haran, lot ). macho( isaac ).pai( haran, milcah ). macho( lot ).pai( isaac, jacob ). macho( jacob ).pai( haran, yiscah ). femea( sara ).

femea( milcah ).mae( sara, isaac ). femea( yiscah ).

Page 9: Programação em Lógica

Prolog - 9

Um facto G. afirma que o golo G é verdadeiro.

Uma pergunta G? interroga se o golo é verdadeiro.

Perguntas

pergunta ou golo (goal) sintacticamente semelhante a um facto

gosta( joao, maria )? ou?- gosta( joao, maria )

sistema responde 'yes' se existir no programa o facto gosta( joao, maria ).

Page 10: Programação em Lógica

Prolog - 10

Um golo é verdadeiro relativamente a um programa, se for uma sua consequência lógica.

Uma pergunta é uma consequência lógica de um facto idêntico.

Operacionalmente: procurar um facto no programa que seja idêntico à pergunta.

Regra da identidade: de G deduzir G

Regra de dedução 1: identidade

pai( abraao, isaac )pai( abraao, isaac ).pai( haran, lot ).…femea( sara ).femea( milcah ).femea( yiscah ).

femea(abraao)

americano( clinton )

programa conclusão

Page 11: Programação em Lógica

Prolog - 11

Respostas negativas

Resposta 'no' - significa que o golo não é consequência lógica do programa, mas nada diz sobre a sua veracidade.

possível interpretação de 'no': • tanto quanto sei, não, i.e, • não consegui provar o golo com os factos de que disponho.

Ex: (programa da Família)pai( abraao, isaac )?

yesfemea(abraao )?

noamericano( clinton )?

no

Page 12: Programação em Lógica

Prolog - 12

Realidade Programa

A se B.C se A.B.

computação

ConclusõesA, B, C

Programas para quê?

Page 13: Programação em Lógica

Prolog - 13

Interpretação

indivíduos — constantes e termos afirmações — factos e golos

relacionam indivíduos; são verdadeiras ou falsas Objectivo: se a interpretação I dos factos

representados no programa for correcta, então todas as conclusões computadas a partir do programa correspondem, nessa interpretação, a afirmações também verdadeiras mesmo que não directamente observáveis - daí o carácter

inteligente destas

Page 14: Programação em Lógica

Prolog - 14

Ex: de quem é que Abraão é pai? fazer perguntas com os vários indivíduos até obter uma

resposta 'yes'• pai( abraao, lot )? no• pai( abraao, milcah )? no• pai( abraao, isaac )? yes

ou perguntar• pai( abraao, X )?

significando:• existe algum indivíduo X que faça com que o golo seja uma

consequência lógica do programa? resultado:

• X = isaac

Variável - representa um indivíduo não especificado [não uma posição de memória].

Uma variável resume muitas perguntas.

pergunta existencialvariáveis nas perguntas são implicitamente existenciais

Nota: começa com maiúscula.

Variável lógica

Page 15: Programação em Lógica

Prolog - 15

1) Constantes e variáveis são termos2) Termos compostos são termos:

functor + lista de argumentos

nome/aridade termos

nome( joao, costa )nome/2

lista( a, lista( b, nil ) ) lista/2s(0) s/1

arv( arv(nil,3,nil), 5, R) arv/3

• termos base (ground)- sem variáveis

• termos não base (nonground)- com variáveis- estruturas incompletas

arv/3

arv/3 5 R

nil 3 nil

Termos• são a única estrutura de dados• interpretação de um termo é um indivíduo• um predicado é V ou F (não confundir com termo)

Termos

Page 16: Programação em Lógica

Prolog - 16

Substituição - conjunto finito de pares Xi=ti

Xi variável, ti termo,

Xi Xj para todo o i j e

Xi não ocorre em tj para todo i, j

Substituição

Ex: = { X = isaac } e G= pai( abraao, X ) aplicação da substituição aos argumentos de G G = pai( abraao, X ) = pai( abraao, isaac ).

instância de A, a variável X está instanciada não existe a noção de atribuição

Page 17: Programação em Lógica

Prolog - 17

Exemplos de substituição

Ex: possui( joao, livro( lusiadas, autor( luis, camoes) ) ). livro( lusiadas, autor( luis, camoes) ) é um termo cuja

interpretação dá um indivíduo, um exemplar dos Lusíadas possui( joao, X )?

X= livro( lusiadas, autor( luis, camoes ) ) possui( Nome, livro( Obra, autor( _, camoes ) ) )?

Quem possui alguma obra do Camões ? Nome= joao, Obra= lusiadas

o símbolo _ é uma variável anónima e portanto não aparece na resposta.

as respostas dadas pelo Prolog são substituições.

Page 18: Programação em Lógica

Prolog - 18

Generalização - uma pergunta existencial P é uma consequência lógica de uma sua instância, P, para qualquer substituição .

Regra de dedução 2: generalização

de pai( abraao, isaac ) concluir pai( abraao, X ), pois existe um X (X= isaac) que torna este verdadeiro

operacionalmente, para responder a uma pergunta existencial com variáveis, procurar um facto que seja uma instância dessa pergunta; a resposta é essa instância, representada pela substituição respectiva

pai( abraao, X )

pai( abraao, isaac ).programa

conclusão

X= isaac

Page 19: Programação em Lógica

Prolog - 19

Soluções múltiplas

Podem existir soluções múltiplas: quais as soluções de soma( A, B, 4 )? {A=0, B=4}, {A=1, B=3}, {A=2, B=2}, {A=3, B=1}, {A=4, B=0}

Quais as soluções de soma( A, A, 4 )? a substituição de A na pergunta é feita só de uma vez,

pelo que o significado é qual o número que somado consigo próprio dá 4?,

{A=2}

Page 20: Programação em Lógica

Prolog - 20

Instanciação - de um facto universalmente quantificado P, deduzir uma sua instância P, para qualquer substituição .

Regra de dedução 3: instanciação

Suponha-se que todos os elementos da Família gostam de maná. gosta( abraao, mana ). gosta( terach, mana ). •••

Em vez disto, pode-se usar um facto universal. gosta( X, mana ).

A variável resume muitos factos. As variáveis nos factos estão universalmente

quantificadas.

Page 21: Programação em Lógica

Prolog - 21

Exemplos de instanciação

Operacionalmente: pergunta sem variáveis — encontrar um facto de que a

pergunta seja instância Ex: incluir o facto soma( 0, X, X ) no programa significa que o

0 é o elemento neutro da adição.

gosta( abraao, mana )

gosta( X, mana).programa

conclusão

Page 22: Programação em Lógica

Prolog - 22

Combinação de regras

Operacionalmente: pergunta com variáveis — procurar uma instância comum à

pergunta e ao facto, o que envolve dois passos: instanciação (do facto para a instância) e generalização (da instância para a pergunta)

Ex: soma( 0, 3, Y ), a partir do facto soma( 0, X, X ) e da instância comum soma( 0, 3, 3), responde {Y=3} (substituições sem variáveis da pergunta, não aparecem na resposta)

soma( 0, 3, 3 )

soma( 0, 3, Y ).programa

instância comum

soma( 0, 3, Y )conclusão

Y= 3

Page 23: Programação em Lógica

Prolog - 23

Perguntas conjuntivas

pergunta conjuntiva é aquela que possui mais do que um golo

• pai( abraao, isaac ), mae( sara, isaac )? vírgula = conjunção resposta a perguntas sem variáveis é a conjunção das respostas

a cada golo perguntas com variáveis partilhadas por vários

golos• pai( haran, X ), macho (X )?• Haran tem algum filho homem?

o alcance da variável é a pergunta conjuntiva também estas variáveis são existenciais

Page 24: Programação em Lógica

Prolog - 24

Variáveis partilhadas

operacionalmente, para resolver A1, A2, ..., An? encontrar uma substituição tal que A1 , A2 , ... An sejam instâncias sem variáveis de factos no programa. solução: {X=lot}

Uso: restrição — dentre os filhos de Haran escolher só os machos

• Ex: pai( terach, X), pai( X, Y )? - escolhe os filhos de Terach que por sua vez têm filhos, i.e.,

netos

Page 25: Programação em Lógica

Prolog - 25

Regra - define uma nova relação em termos das relações existentes.

Regras

dá um nome a uma pergunta conjuntiva; transforma-a numa pergunta simples

• avo( X, Y ) pai( X, Z ), pai( Z, Y ), forma geral das cláusulas de Horn

• (cabeça) (corpo)– facto A – regra A B1, B2, ... Bn– pergunta B

leitura procedimental a pergunta avo( terach, Y ) é traduzida por pai( terach, Z ), pai( Z, Y ) e reduzida a pai( haran, Y )

{Z=haran} para concluir { Z=haran, Y=lot}

Page 26: Programação em Lógica

Prolog - 26

Leitura declarativa

• avo( X, Y ) pai( X, Z ), pai( Z, Y ), regra vista como um axioma lógico

denota implicação lógica lê-se: para todo o X, Y e Z, X é avô de Y se X for o pai de Z e

Z o pai de Y as variáveis nas regras (caso particular: factos) são

quantificadas universalmente leitura alternativa: para todo o X e Y, X é avô de Y se existir

um Z tal que X seja o pai de Z e Z o pai de Y

Page 27: Programação em Lógica

Prolog - 27

Equivalências• avo( X, Y ) pai( X, Z ), pai( Z, Y ),

justificação da segunda leitura equivalências: a b a ~b; X, p(X) ~x: ~p(X)

X Y Z avo( X, Y) pai( X, Z ), pai( Z, Y ) X Y Z avo( X, Y) ~[ pai( X, Z ), pai( Z, Y )] X Y avo( X, Y) Z ~[ pai( X, Z ), pai( Z, Y )] X Y avo( X, Y) ~Z: [ pai( X, Z ), pai( Z, Y )] X Y avo( X, Y) Z: [ pai( X, Z ), pai( Z, Y )] só as variáveis dos golos da pergunta interessam para a expressão

da substituição variáveis nas perguntas (cláusulas só com corpo) são

portanto existenciais

Page 28: Programação em Lógica

Prolog - 28

Regra de dedução 4: modus ponens

Lei do modus ponens universal trata das deduções via regras diz que da regra

• R= (A B1, B2, ..., Bn) e dos factos

• B'1. B'2. .... B'n.

se pode deduzir A' se A' B'1, B'2, ..., B'n for uma instância de R.

[identidade e instanciação são casos particulares] Um programa em lógica é um conjunto finito de

regras.

Page 29: Programação em Lógica

Prolog - 29

Consequência lógica

Um golo quantificado existencialmente G é uma consequência lógica de um programa P, se existir uma cláusula em P com uma instância sem variáveisA B1, B2, ..., Bn, n0,

tal que B1, B2, ..., Bn sejam consequências lógicas de P e A uma instância de G. responder a perguntas é aplicar (redução) o modus ponens da

frente para trás o número de vezes necessário para ir do golo até aos factos

a) escolhendo uma instância do golo eb) uma regra para aplicar, recursivamente.

Page 30: Programação em Lógica

Prolog - 30

Procedimento - colecção de regras com o mesmo predicado na cabeça.

Procedimentos

para obter todos os netos — acrescentar definições em falta ao procedimento do predicado avo/2.

• avo( X, Y ) pai( X, Z ), pai( Z, Y ),• avo( X, Y ) pai( X, Z ), mae( Z, Y ),• avo( X, Y ) mae( X, Z ), pai( Z, Y ),• avo( X, Y ) mae( X, Z ), mae( Z, Y ),

outra representação, mais compacta progenitor( X, Y ) pai( X, Y ), progenitor( X, Y ) mae( X, Y ), avo( X, Y ) progenitor( X, Z ), progenitor( Z, Y ),

progenitor/2 tem duas alternativas — é uma forma de representar disjunção

Page 31: Programação em Lógica

Prolog - 31

resolvente - pergunta conjuntiva com os golos ainda a processartraço - evolução da computação, com a indicação de

a) golo seleccionadob) regra escolhida para a reduçãoc) substituição associada

- resolvente vazia (= true)

Traço de uma execução

avo( X, jacob ) progenitor( X, Z ), progenitor( Z, jacob ) progenitor( X, Z ), pai( Z, jacob)

progenitor( X, isaac ) {Z= isaac }

mae( X, isaac ) {Z= isaac } {Z= isaac, X= sara}

Page 32: Programação em Lógica

Prolog - 32

Outro traço de execução

avo( X, jacob ) progenitor( X, Z ), progenitor( Z, jacob ) pai( X, Z ), progenitor( Z, jacob )

progenitor( isaac, jacob ) { X=abraao, Z= isaac }pai( isaac, jacob ) { X=abraao, Z= isaac }

{ X=abraao, Z= isaac}

Page 33: Programação em Lógica

Prolog - 33

livro( Titulo, autor( Proprio, camoes), data(1585, Mes, Dia)) )

livro( lusiadas, autor( luis, Apelido), Ano )

= {Titulo=lusiadas, Proprio=luis, Apelido=camoes,

Ano= data(1585, Mes, Dia)}

Unificação

um termo T é uma instância comum de T1 e T2 se existirem substituições 1 e 2 tais que T=T11 e T=T22

um termo S é mais geral do que um termo T, se T for uma instância de S e S não for uma instância de T

um termo S é uma variante de um termo T se se puderem converter um no outro por simples renomeação de variáveis

um unificador de dois termos é uma substituição que torna os dois termos iguais

Page 34: Programação em Lógica

Prolog - 34

Algoritmo de unificação

o algoritmo de unificação produz o unificador ou reporta falha baseia-se na comparação de functores e na tentativa de unificar

os respectivos argumentos, propagando cada substituição a todas as ocorrências de variáveis

o resultado é o unificador mais geral possível (a respectiva instância é a mais geral de todas as instâncias)

verificação de ocorrência - para unificar uma variável S com um termo T, T não pode conter S [não há unificador mais geral para X e s(X)]

Page 35: Programação em Lógica

Prolog - 35

Interpretador abstracto

Entrada programa P golo GSaída G, se existir, ou falhaAlgoritmo

inicializar a resolvente para ser o golo G enquanto a resolvente não estiver vazia fazer

• escolher um golo A da resolvente e uma cláusula (renomeada)A' B1, B2, ..., Bn n0

em P tal que A e A' unifiquem com unificador (sair do ciclo se não existirem tais golo e cláusula)

• remover A da resolvente e adicionar-lhe B1, B2, ..., Bn

• aplicar à resolvente e a G se a resolvente estiver vazia devolver G, se não reportar falha

Page 36: Programação em Lógica

Prolog - 36

Bases de dados

conjunto de factos = base de dados (BD extensional)regras = vistas (BD intencional)

predicado só com factos = relaçãopai( Pai, Filho ), mae( Mae, Filho ), macho( Pessoa ),femea( Pessoa ) [esquemas]

definição de vistasprogenitor( P, Filho ) pai (P, Filho ).progenitor( P, Filho ) mae( P, Filho ).irmao( X, Y ) progenitor( P, X ), progenitor( P, Y ), macho( X ), X \= Y.tio( Tio, Sob ) irmao( Tio, P ), progenitor( P, Sob ).antepassado( A, X ) progenitor( A, X ).antepassado( A, X ) progenitor( A, Y ), antepassado( Y, X ).

Page 37: Programação em Lógica

Prolog - 37

not G é verdadeiro relativamente a um programa P se G não for uma consequência lógica de P

PL vs BD relacionais

programação em lógica — extensão ao modelo relacional, fornece uma linguagem integrada de acesso aos dados, e de programação de aplicações

operações básicas reunião

r_uniao_s( X1, ..., Xn ) r( X1, ..., Xn )r_uniao_s( X1, ..., Xn ) s( X1, ..., Xn )

diferença• requer um predicado de negaçãor_menos_s( X1, ..., Xn ) r( X1, ..., Xn ), not s( X1, ..., Xn )

Page 38: Programação em Lógica

Prolog - 38

Operações da álgebra relacional

produto cartesianor_vezes_s( X1, ..., Xm, Xm+1, ..., Xm+n )

r( X1, ..., Xm ), s( Xm+1, ..., Xm+n ) projecção

r13( X1, X3 ) r( X1, X2, X3 ) selecção

r1( X1, X2, X3 ) r( X1, X2, X3 ), X2 > X3

operações derivadas intersecção

r_inter_s( X1, ..., Xn ) r( X1, ..., Xn ), s( X1, ..., Xn ) junção natural

r_join_y( X1, X2, X3 ) r( X1, X2 ), s( X2, X3 )

Page 39: Programação em Lógica

Prolog - 39

Estilo de programação

dois estilos1) exprimir a informação à custa de relações entre indivíduos

atómicos2) codificar informação em termos, indivíduos complexos e

manipular estruturas arte: encontrar o adequado nível de abstracção

esconder os detalhes da representação — independência dos dados

evidenciar associações entre indivíduos, evitando redundâncias — normalização

Page 40: Programação em Lógica

Prolog - 40

Representação de informação

Representar o facto de o João possuir um exemplar dos Lusíadas de Luís de Camões, editado em 1940.

Codificação em termos complexos, com poucos predicados possui( joao, livro( lusiadas, autor( luis, camoes), 1940 ) ).

Quem possui livros editados em 1940??- possui( X, livro( _, _, 1940 ) ).

Codificação baseada em predicados, com termos simplesescritor( 1, luis, camoes). livro( 427, lusiadas, 1940 ).autor( 1, 427). pessoa(1002, joao ). possui( 1002, 427 ).

?- possui( CodP, CodL), pessoa( CodP, X ), livro(CodL, _, 1940).

Page 41: Programação em Lógica

Prolog - 41

Tipos

não existe noção independente de tipo; existem predicados que definem implicitamente tipos

tipo — conjunto de termos definição de tipo — (muitas vezes) predicado unário tipo macho definido como o conjunto dos termos X tais que

macho(X) é verdade tipos recursivos simples — definidos por programas em lógica

unários recursivos• inteiros, listas, árvores binárias

inteiros: predicado de tipo% natural( X ) X é um número natural% sn(0) denota nnatural( 0 ).natural( s(X) ) natural( X ).

s(X) representa o sucessor de X

Page 42: Programação em Lógica

Prolog - 42

relação de ordem% X Y se X e Y são números naturais e X Y (notação infixa de ''( X, Y ) )

0 X natural( X ).s(X) s(Y) X Y

traço de um golo:s(s(0)) s(0)s(0) 0 • este golo não tem redução porque não unifica com nenhuma

cabeça de cláusula — o traço falha ( para suceder teria que terminar em )

Aritmética

Page 43: Programação em Lógica

Prolog - 43

Adição

operação de adição como relação ternária

% soma( X, Y, Z ) se X, Y e Z são números naturais e Z é a soma de X e Y

soma( 0, X, X ) natural( X ).soma( s(X), Y, s(Z) ) soma( X, Y, Z ).

definição de tipo recursivo permite forma compacta para a adição, em vez da explícita

Page 44: Programação em Lógica

Prolog - 44

Múltiplos usos

uso funcionalsoma( s(s(0)), s(0), X )soma( s(0), s(0), Z1 ) { X = s( Z1) }soma( 0, s(0), Z2 ) { Z1 = s(Z2), X = s(s(Z2)) } { Z2 = s(0), Z1 = s(s(0)), X = s(s(s(0))) } note como se constrói um termo para devolver em X, à custa de o

manter aberto com uma variável e da unificação que causa instanciação parcial

uso invertidosoma( s(0), Y, s(s(s(0)))soma( 0, Y, s(s(0)) ) { Y= s(s(0)) } note como se define o resultado e se pergunta as parcelas

Page 45: Programação em Lógica

Prolog - 45

Várias soluções

Traço com soluções múltiplassoma( X, Y, s(s(s(0))) ) { X= 0, Y= s(s(s(0))) };soma( X, Y, s(s(s(0))) )soma( X1, Y, s(s(0)) ) { X= s(X1) } { X1= 0, Y= s(s(0)) }etc.; {no}

pede-se uma nova solução com um sinal “;”

Page 46: Programação em Lógica

Prolog - 46

Significado de um programa P, M(P), é o conjunto dos golos completamente instanciados dedutíveis de P.

Significado

esquema da relação/predicado descreve o significado pretendido M, também definido em termos de golos na relação relativamente ao significado pretendido

• programa correcto M(P) M• programa completo M M(P)

objectivo: programas correctos e completos ou, pelo menos, correctos

Page 47: Programação em Lógica

Prolog - 47

•(a, •(b, []) ) [a | [b | []] ] [a, b]

a

b []

••

cabeça cauda

formal par elementos

.(a,[]) [a|[]] [a]

.(a, .(b, .(c, []))) [a|[b|[c | []] [a, b, c]

.(a, X) [a|X] [a|X]

.(a, .(b, X)) [a | [b | X] ] [a,b| X]

Listas

Lista — estrutura de dados binária em que o 1º argumento é um elemento e o 2º recursivamente o resto da lista; a base da recursão é a lista vazia []

Representações

b []

Page 48: Programação em Lógica

Prolog - 48

% lista( Xs ) Xs é uma lista

lista( [] ).

lista([X | Xs] ) lista( Xs ).

definição de tipo

lista( [1,2,3] ) lista( [2,3] )

R: { X= 1, Xs=[2,3] }

membro de uma lista% member( X, Xs ) X é um elemento

da lista Xs

member( X, [X|Xs] ) lista( Xs ).

member(X, [Z| Xs] ) member( X, Xs ).

omite-se

• nomes das variáveis são arbitrários e locais às regras

• mas convém ter uma disciplina

Manipulação de listas

member(b, [a,b,c]). R: yesmember(X, [a,b,c] ) R: { X= a } ou {X=b} ou {X = c}member(b, Xs) R: { Xs= [b]} ou {Xs = [X, b|Z]}

Page 49: Programação em Lógica

Prolog - 49

Predicados sobre listas

Comprimento de uma lista% comp( Xs, N ) a lista Xs tem N elementoscomp( [], 0 ).comp( [X| Xs], s(N) ) comp(Xs, N ).

Prefixo e sufixo de uma lista% prefixo(Ps, Xs ) Ps é uma sublista

consecutiva no início da lista Xsprefixo( [], Xs ) .prefixo( [X|Xs], [X| Ys] ) prefixo( Xs, Ys ).sufixo( Xs, Xs ) .sufixo( Xs, [Y| Ys] ) sufixo( Xs, Ys ).

Page 50: Programação em Lógica

Prolog - 50

% append( Xs, Ys, Zs ) se Zs for o resultado da concatenacao de Xs e Ys

append( [], Ys, Ys ).append( [X|Xs], Ys, [X|Zs] ) append( Xs, Ys, Zs ).

append( [a,b], [c,d], Zs )

append( [b], [c,d], Zs1 ) { Zs= [a|Zs1] }

append( [], [c,d], Zs2 ) { Zs1= [b|Zs2] }

{ Zs2= [c,d] }

R: Zs = [a,b,c,d]

append( Xs, [c,d], [a,b,c,d] )

append( Xs1, [c,d], [b,c,d] ) { Xs= [a|Xs1] }

append( Xs2, [c,d], [c,d] ) { Xs1= [b|Xs2] }

{ Xs2= [ ] }

R: Xs = [a,b]

programa semelhante em estrutura ao da soma de inteiros, mas assimétrico no primeiro argumento:

Concatenação

partição de uma lista• append( Xs, Ys, [a,b,c,d] )

tem múltiplas soluções e aplicações variadas• member( X, Xs ) append( As, [X|Ys], Xs )

Page 51: Programação em Lógica

Prolog - 51

Aplicações da concatenação

Sublistas% sublista( Sub, Lista ) Sub é uma sublista de Lista% prefixo de sufixo sublista( Sub, Lista ) prefixo( Sub, Xs ), sufixo( Xs, Lista ).% ou sublista(Xs, AsXsBs )

append( As, XsBs, AsXsBs ), append( Xs, Bs, XsBs ).

Inverter uma lista% inverte( Lista, Inv ) Inv é o resultado de inverter Lista% algoritmo ingénuoinverte( [], [] ).inverte( [X| Xs], Zs ) inverte( Xs, Ys ), append( Ys, [X], Zs ).

Page 52: Programação em Lógica

Prolog - 52

inverte( [b,c,d], [d,c,b] )

inverte( [c,d], [d,c] )

inverte( [d], [d] )

inverte( [], [] )

append([d], [c], [d,c] ) append([c], [b], [c,b] )

append([], [d], [d] )

append([d,c], [b], [d,c,b] )

append([], [b], [b] )append([], [c], [c] )

Dimensão da árvore de prova quadrática no número de elementos da lista a inverter.

Árvore de prova

Árvore de prova — os nós são os golos reduzidos durante a computação; a raiz é o golo da pergunta; há arcos de cada nó para todos os nós obtidos daquele por um passo de redução.

Objectivo: mais declarativa do que o traço, mostrar as razões da dedução.

Page 53: Programação em Lógica

Prolog - 53

• traçoinverte( [b,c,d],[] )

inverte( [c,d], [b] )

inverte( [d], [c,b] )

inverte( [], [d,c,b] )

Evitar a concatenação

Inverter sem concatenação (tentativa)

% inverte( Lista, Inv ) Inv é o resultado de inverter Lista

% algoritmo sem append

inverte( [X| Xs], Acc ) inverte( Xs, [X|Acc] ).

inverte( [], Acc ).

inverteu, mas ... e o resultado?

Page 54: Programação em Lógica

Prolog - 54

• traçoinverte( [b,c,d],Ys ) inverte( [b,c,d],[], Ys ) inverte( [c,d], [b], Ys )inverte( [d], [c,b], Ys )inverte( [], [d,c,b], Ys )

{ Ys= [d,c,b] }

Acumuladores Inverter sem concatenação usando acumulador para extrair o resultado (por unificação no último passo)% inverte( Lista, Inv ) Inv é o resultado de inverter Lista% algoritmo com acumulador (argumento suplementar)inverte( Xs, Ys ) inverte( Xs, [], Ys ).inverte( [X| Xs], Acc, Ys ) inverte( Xs, [X|Acc], Ys ).inverte( [], Ys, Ys ).

este traço corresponde a uma árvore de tamanho linear no número de elementos da lista

Page 55: Programação em Lógica

Prolog - 55

Filtro

% apaga( Lista, X, SemXs ) a lista SemXs é Lista com todos os X removidos

apaga( [X| Xs], X, Ys ) apaga( Xs, X, Ys ).apaga( [X| Xs], Z, [X|Ys] ) XZ, apaga( Xs, Z, Ys ).apaga( [], X, [] ).

A condição XZ na segunda regra é essencial para obter resultados correctos

Page 56: Programação em Lógica

Prolog - 56

Ordenação

% quicksort( Xs, Ys ) a lista Ys é uma permutação ordenada de Xsquicksort( [X| Xs], Ys ) particao( Xs, X, Pequenos, Grandes ), quicksort( Pequenos, Ps), quicksort( Grandes, Gs ), append( Ps, [X| Gs], Ys ).quicksort( [], [] ). particao( [X| Xs ], Y, [X| Ls], Bs ) X Y, particao( Xs, Y, Ls,

Bs ).particao( [X| Xs ], Y, Ls, [X| Bs] ) X > Y, particao( Xs, Y, Ls, Bs ).particao( [], Y, [], [] ).

Page 57: Programação em Lógica

Prolog - 57

Árvores Árvore - estrutura duplamente recursiva% arvore(Arv ) Arv é uma árvorearvore( void).arvore( arv(Elem, Esq, Dir) ) arvore( Esq ), arvore( Dir ).% membro_arv( E, A ) E é um elemento da árvore binária Amembro_arv( X, arv(X,E,D) ).membro_arv( X, arv(Z,E,D) ) membro_arv(X, E ).membro_arv( X, arv(Z,E,D) ) membro_arv(X, D ).% isomorfa(Arv1, Arv2 ) Arv1 e Arv2 são isomorfasisomorfa( void, void ).isomorfa( arv(X,Esq1,Dir1), arv(X,Esq2,Dir2) ) isomorfa( Esq1, Esq2), isomorfa(Dir1,

Dir2 ).isomorfa( arv(X,Esq1,Dir1), arv(X,Esq2,Dir2) ) isomorfa( Esq1, Dir2), isomorfa(Dir1,

Esq2 ).% pre_ordem( Arv, Pre ) Pre é uma travessia em preordem da árvore Arvpre_ordem( arv(X,E,D), Pre ) pre_ordem( E, Es ), pre_ordem( D, Ds ), append( [X|

Es], Ds, Pre ).pre_ordem( void, [] ).

Page 58: Programação em Lógica

Prolog - 58

Árvore de pesquisa

Árvore de pesquisa de um golo G relativamente a um programa P raiz da árvore: G nós: resolventes, com um golo seleccionado arcos a sair de um nó: um por cada cláusula de P cuja cabeça

unifica com o golo seleccionado no nó cada caminho na árvore, desde a raiz: computação de G por P folhas: nós de sucesso, se corresponderem a resolventes vazias;

nós de falha se o golo selecionado não puder ser reduzido

Page 59: Programação em Lógica

Prolog - 59

avo( X, jacob )

progenitor( X, Z ), progenitor( Z, jacob )

progenitor( X, Z ), pai( Z, jacob) progenitor( X, Z ), mae( Z, jacob)

{X= abraao}

progenitor( X, isaac )

mae( X, isaac )pai( X, isaac )

{Z= isaac }

{X= sara}

sucessoX=abraao, Z=isaac

sucessoX=sara, Z=isaac

falha

Árvore de pesquisa do Jacob

Page 60: Programação em Lógica

Prolog - 60

avo( X, jacob )

progenitor( X, Z ), progenitor( Z, jacob )

pai( X, Z ), progenitor( Z, jacob) mae( X, Z ), progenitor( Z, jacob)

{X= abraao}

pai( X, Z ), mae( Z, jacob )

pai( X, Z ), pai( Z, jacob)

sucesso

X=abraao, Z=isaacsucesso

X=sara, Z=isaac

Outra árvore de pesquisa

pai( X, isaac )

{Z= isaac}

falha{X= sara}

pai( X, Z ), mae( Z, jacob )

mae( X, Z ), pai( Z, jacob)

mae( X, isaac )

{Z= isaac}

falha

Page 61: Programação em Lógica

Prolog - 61

Características destas árvores árvore de pesquisa: independente do critério de

selecção de cláusulas (tem todas as alternativas) podem existir várias árvores de pesquisa diferentes

para o mesmo golo e o mesmo programa, conforme o critério de selecção dos golos

conclusão principal: o número de nós de sucesso é o mesmo em todas elas

uma árvore de pesquisa resume todas as respostas; chama-se de pesquisa porque um interpretador concreto terá que ter uma estratégia para percorrer a árvore em busca de soluções (pesquisa em profundidade, em largura, em paralelo, ...)

Page 62: Programação em Lógica

Prolog - 62

append( Xs, [c,d], Ys)

append( Xs1, [c,d], Ys1)

{Xs= [], Ys= [c,d]}{Xs= [X|Xs1], Ys= [X|Ys1]}

append( Xs2, [c,d], Ys2)

{Xs1= [], Ys1= [c,d]}{Xs1= [X1|Xs2], Ys1= [X1|Ys2]}

append( Xs3, [c,d], Ys3)

{Xs2= [], Ys2= [c,d]}{Xs2= [X2|Xs3], Ys2= [X2|Ys3]}

°°°

°°°

Computações infinitas

ramos infinitos na árvore correspondem a computações sem fim uma pesquisa em profundidade pode perder-se num ramo infinito avaliar a complexidade de uma pergunta: (interpretadores que

pesquisem sequencialmente toda a árvore) melhor analisar o número de nós da árvore de pesquisa do que da árvore de prova (esta inclui não determinismo)

Page 63: Programação em Lógica

Prolog - 63

Dedução usando negação por falha: not G é uma consequência de P se G estiver no conjunto de falha finita de P

Negação por falha os programas em lógica descrevem o que é verdade; o falso é omitido certas relações são mais fáceis de especificar com a negação

disjunto( Xs, Ys ) not ( member( X, Xs ), member( X, Ys ) ) para obter conclusões negativas: assunção do mundo fechado

not G é uma consequência do programa P se G não for uma consequência de P (mesmo que G dê ramo infinito)

árvore de pesquisa finitamente falhada: não contém nós de sucesso nem ramos infinitos

conjunto de falha finita do programa P: conjunto dos golos que têm uma árvore finitamente falhada relativamente a P

árvore finitamente falhada: progenitor( isaac, X ) pai( isaac, X ) mae(isaac,

X) falha falha