UFSM > Informática > ELC117 - Paradigmas de Programação

Preparação

Para estes exercícios você vai precisar do ambiente SWI-Prolog. Ele está disponível em: http://www.swi-prolog.org/download/stable

Controlando a execução

Cut

Em Prolog, o operador ! (leia-se: cut) é usado para impedir o retrocesso (backtracking) na avaliação de um predicado. Por exemplo, na avaliação de uma regra, se uma variável X recebe um valor 1 e depois é feito um cut, o processo de inferência Prolog vai considerar que o valor 1 é a única instância possível para X, mesmo que existam outras possibilidades na base de dados.

Exercícios:

  1. Copie o seguinte código Prolog para um arquivo:
    b(2).
    b(3).
    c(4).
    c(5).
    regra1(X, Y) :- b(X), c(Y).
    regra2(X, Y) :- b(X), !, c(Y).
    

  2. Considerando o programa acima, qual será o resultado da seguinte consulta?
    ?- regra1(X,Y).
    
    Execute a consulta e verifique se sua resposta está correta. Obs: use ; para buscar todas as respostas possíveis.

  3. Ainda considerando o mesmo programa, qual será o resultado da seguinte consulta?
    ?- regra2(X,Y).
    
    Execute a consulta para verificar se sua resposta está correta, lembrando de usar ; para buscar todas as respostas possíveis.

  4. Ative o modo de rastreamento (trace) e re-execute as consultas acima. Observe a ocorrência de backtracking (Redo) nos 2 casos.

  5. Baixe o programa fatoriais.pl e carregue-o no SWI-Prolog.

  6. Execute a consulta abaixo e use ; para verificar se há outras respostas possíveis.
    ?- fatv1(3,N).
    

  7. A consulta acima deve ter gerado um erro depois que for digitado ;. Você consegue identificar o motivo deste erro?

  8. Para melhor entender o erro acima, ative o modo trace e re-execute a consulta:
    ?- trace.
    true.
    [trace]  ?- fatv1(3,N).
    
    Dica: quando você cansar de rastrear a execução passo-a-passo, digite a (abort) no lugar de Enter.

  9. Analise o código em fatoriais.pl, comparando os predicados fatv2 e fatv3 com o predicado fatv1.

  10. Execute as consultas abaixo, digitando ; após cada resposta. Compare os resultados com os da consulta anterior (fatv1).
    ?- fatv2(3,N).
    ?- fatv3(3,N).
    

  11. Ative o modo trace e re-execute as consultas acima, acompanhando suas execuções.

  12. Você consegue identificar alguma vantagem de fatv2 sobre fatv3?

Repeat

Em Prolog, uma forma de implementar laços é usando repeat. Na avaliação de um predicado, as proposições a partir de um repeat são repetidos até que cada uma de suas condições seja verdadeira. Se uma ou mais condições forem falsas, o laço se repete.

Exercícios:

  1. Copie o seguinte código Prolog para um arquivo:
    main :- repeat, 
    	write('Digite um numero: '), 
            read(X), 
            (X=:=42).
    
    O programa acima pede repetidamente que o usuário digite um número, até que o número digitado seja igual a 42.

  2. Carregue e execute este programa. Obs: você deve digitar um ponto (.) após cada número digitado.

  3. Ao executar o programa acima, experimente digitar 42. e depois digitar ;. O que acontece? Por que isso acontece?

  4. Modifique o programa de modo a impedir o retrocesso depois que o número digitado estiver correto.

Chatbot

  1. Baixe o programa mychatbot1.pl. Carregue-o e execute-o no SWI-Prolog:
    ?- [mychatbot1].
    % mychatbot1 compiled 0.00 sec, 3,976 bytes
    true.
    ?- main.
    Ola! Sou um chatbot e estou a sua escuta!
    > 'Bom dia'.
    Que conversa interessante.
    > 'Tambem acho'.
    Concordo com voce.
    > tchau.
    Que conversa interessante.
    > bye.
    Que conversa interessante.
    Foi otimo conversar com voce. Ate mais!
    true 
    
    Atenção: as frases digitadas pelo usuário devem ser strings (entre apóstrofes), terminadas por ponto, ou então uma única palavra, também terminada por ponto.

  2. Analise o código em mychatbot1.pl. Para que serve o predicado nth0? Quais são as limitações do algoritmo utilizado?

  3. Baixe o programa mychatbot2.pl. Carregue-o e execute-o no SWI-Prolog:
    ?- [mychatbot2].
    % mychatbot2 compiled 0.00 sec, 6,808 bytes
    true.
    ?- main.
    > 'Oi'.
    Ola!
    > 'Tudo bem?'.
    Tudo otimo!
    > 'O ceu eh azul?'.
    Nao entendo o que vc quer dizer.
    Por favor, escreva uma pergunta e me ensine a resposta.
    Pergunta: 'O ceu eh azul?'.
    Resposta: 'Sim, o ceu eh azul.'.
    Ok, continue falando comigo.
    > 'Quem eh vc?'.
    Sou um robo.
    > 'O ceu eh azul?'.
    Sim, o ceu eh azul.
    > bye.
    Ate mais! Foi otimo conversar com voce
    true
    

  4. Analise o código em mychatbot2.pl. Quais as diferenças em relação a mychatbot1.pl?

  5. O que acontece se removermos o ! (cut) das regras get_response?

  6. Em SWI-Prolog, existem os predicados assert, asserta e assertz. Quais as diferenças e semelhanças entre eles?

Material de apoio

Página criada em: Mon May 23 21:15:14 BRT 2011. Última atualização em: Tue May 24 10:14:07 2011. Autoria: Andrea Schwertner Charão.