Jogo dos Animais

De Augusto Baffa Wiki
Revisão de 11h55min de 17 de dezembro de 2020 por Abaffa (discussão | contribs)
Ir para navegação Ir para pesquisar

Está é uma versão Prolog do jogo de identificação de animais (sistema especialista simples) apresentado em um programa 'Lisp' no Capítulo 6 de Winston e Horn (1985)[1]. Carregue o arquivo e faça a consulta ?- go. O programa usa suas regras de identificação para determinar o animal que você escolheu.

 
/* animal.pro
  animal identification game.  

    start with ?- go.     */

go :- hypothesize(Animal),
      write('I guess that the animal is: '),
      write(Animal),
      nl,
      undo.

/* hypotheses to be tested */
hypothesize(cheetah)   :- cheetah, !.
hypothesize(tiger)     :- tiger, !.
hypothesize(giraffe)   :- giraffe, !.
hypothesize(zebra)     :- zebra, !.
hypothesize(ostrich)   :- ostrich, !.
hypothesize(penguin)   :- penguin, !.
hypothesize(albatross) :- albatross, !.
hypothesize(unknown).             /* no diagnosis */

/* animal identification rules */
cheetah :- mammal, 
           carnivore, 
           verify(has_tawny_color),
           verify(has_dark_spots).
tiger :- mammal,  
         carnivore,
         verify(has_tawny_color), 
         verify(has_black_stripes).
giraffe :- ungulate, 
           verify(has_long_neck), 
           verify(has_long_legs).
zebra :- ungulate,  
         verify(has_black_stripes).

ostrich :- bird,  
           verify(does_not_fly), 
           verify(has_long_neck).
penguin :- bird, 
           verify(does_not_fly), 
           verify(swims),
           verify(is_black_and_white).
albatross :- bird,
             verify(appears_in_story_Ancient_Mariner),
             verify(flys_well).

/* classification rules */
mammal    :- verify(has_hair), !.
mammal    :- verify(gives_milk).
bird      :- verify(has_feathers), !.
bird      :- verify(flys), 
             verify(lays_eggs).
carnivore :- verify(eats_meat), !.
carnivore :- verify(has_pointed_teeth), 
             verify(has_claws),
             verify(has_forward_eyes).
ungulate :- mammal, 
            verify(has_hooves), !.
ungulate :- mammal, 
            verify(chews_cud).

/* how to ask questions */
ask(Question) :-
    write('Does the animal have the following attribute: '),
    write(Question),
    write('? '),
    read(Response),
    nl,
    ( (Response == yes ; Response == y)
      ->
       assert(yes(Question)) ;
       assert(no(Question)), fail).

:- dynamic yes/1,no/1.

/* How to verify something */
verify(S) :-
   (yes(S) 
    ->
    true ;
    (no(S)
     ->
     fail ;
     ask(S))).

/* undo all yes/no assertions */
undo :- retract(yes(_)),fail. 
undo :- retract(no(_)),fail.
undo.

O programa é interessante principalmente no que diz respeito a como tenta verificar certas propriedades que usa para tirar conclusões e como faz perguntas e registra as respostas para referência futura. Se uma pergunta 'q' for feita e a resposta for 'yes', essa resposta será registrada afirmando (com o comando assert) yes(q) e bem-sucedida; caso contrário, a resposta será registrada afirmando(com o comando assert) no(q) e falhando.

Mesmo as respostas "yes" precisam ser registradas, uma vez que uma resposta "no" subsequente a uma pergunta diferente ao tentar verificar a mesma hipótese pode fazer com que toda a hipótese falhe, mas a mesma resposta "yes" pode levar a uma verificação bem-sucedida de um hipótese diferente mais tarde. É assim que o programa evita fazer a mesma pergunta duas vezes. O método geral de verificação de uma condição 'q' é então verificar se yes(q) foi armazenado na memória e se foi bem-sucedido ou se no(q) foi armazenado e falhar, caso contrário, pergunte: ask(q).

O Capítulo 6 constrói uma estrutura geral para sistemas especialistas em Prolog.

Veja Também

Referências

  1. Winston, P.H., and Horn, P., Lisp, Addison-Wesley, 1985.