1. Este site usa cookies. Ao continuar a usar este site está a concordar com o nosso uso de cookies. Saber Mais.

Prolog

Discussão em 'Programação' iniciada por FASC, 14 de Maio de 2007. (Respostas: 26; Visualizações: 2226)

  1. FASC

    FASC Power Member

    Pessoal, estou aqui com um problema que não consigo resolver. A situação é esta: eu crio uma lista com o nome "Lista = []", que mais tarde é passada como argumento para dentro de uma função. O problema é que essa função TEM de alterar o conteúdo da lista (juntar uma lista a outra e guardar nessa variável "Lista"), só que o raio do Prolog não me está a deixar fazer isso! Simplesmente não executa o resto da função! Mesmo que seja outro tipo de variável, ele não deixa afectar os argumentos... Alguém me pode ajudar?


    Exemplo:

    Código:
    Fasc='fasc'.
    
    exemplo(Fasc) :-
            Fasc='bah',
            print(Fasc),nl.
    
    Ele nem chega ao "print"...

    Someone? :)


    EDIT: Outro exemplo:
    Código:
    Fasc1='fasc'.
    
    exemplo(Fasc2) :-
            Fasc2='bah',
            print(Fasc2),nl.
    
    E ainda o código que estou a trabalhar:

    Código:
    add_peca_list_fab(P, Lista) :-
    	findall((K,Z), (peca(K,Z), K=P), Result),
    	append(Lista, Result,Result), print(Result), nl,nl,
    	Lista = Result,
    	print(Lista).
    
    Pára na afectação da Lista. Já tentei de "n" maneiras diferentes e nunca consigo afectar os argumentos. Apenas consigo ler o seu conteúdo...
     
    Última edição: 14 de Maio de 2007
  2. legerdemain

    legerdemain Power Member

    hm.. recomendo-te a leres algumas coisas de prolog/lógica
    é que tu não podes fazer este tipo de coisas em prolog:
    append(Lista, Result,Result)

    o código correcto será
    Código:
    add_peca_list_fab(P, Lista,ListaResultante) :-
    	findall((K,Z), (peca(K,Z), K=P), Result),
    	append(Lista, Result,ResultResultante), print(ResultResultante), nl,nl,
    	ListaResultante = ResultResultante,
    	print(ListaResultante).
    edit: e tenho dúvidas quanto ao funcionamento do findall
     
    Última edição: 14 de Maio de 2007
  3. FASC

    FASC Power Member

    Posso posso. Isso funciona. Só não funciona a parte de afectar a variável... Se eu fizer um print do meu Result, ele tem lá o que quero.


    EDIT: Testei o código que me deste. Continuo sem conseguir afectar a varíavel "ListaResultante". Simplesmente fora da função a lista continua vazia, e dentro da função ele não corre a a partir da linha "ListaResultante = ResultResultante"...

    Está a acontecer o mesmo... O meu "print(Result)" escreve aquilo que eu quero que esteja dentro do Result, portanto a função está a funcionar. Simplesmente não afecta nenhuma varíavel que tenha vindo em argumento... Não percebo!
     
    Última edição: 14 de Maio de 2007
  4. legerdemain

    legerdemain Power Member

    não sei o que estás a fazer, mas palpita-me que andas praí a chamar isso à balda

    aqui fica o resultado de um pequeno teste que fiz:

    Código:
    | ?- add_peca_list_fab(a,[(f,g),(f,h)],L).    
    [(f,g),(f,h),(a,b),(a,c),(a,d)]
    
    [(f,g),(f,h),(a,b),(a,c),(a,d)]
    L = [(f,g),(f,h),(a,b),(a,c),(a,d)] ? n
    no
    
    código do teste:
    Código:
    :-use_module(library(lists)).
    
    peca(a,b).
    peca(a,c).
    peca(a,d).
    peca(b,c).
    peca(b,d).
    
    add_peca_list_fab(P, Lista,ListaResultante) :-
    	findall((K,Z), (peca(K,Z), K=P), Result),
    	append(Lista, Result,ResultResultante), print(ResultResultante), nl,nl,
    	ListaResultante = ResultResultante,
    	print(ListaResultante).
    
    e aquela última atribuição é redundante, podes meter tudo para a variável ListaResultante no append
     
  5. FASC

    FASC Power Member

    Código:
    :-abolish_files('pecas.pl').
    :-abolish_files('fabricas.pl').
    :-dynamic(peca/2).
    :-dynamic(fabrica/4).
    :-compile('pecas.pl').
    :-compile('fabricas.pl').
    
    
    
    get_def_fab_option(O) :-
    	print(' 1 - Se deseja listar novamente as peças'), nl,
    	print(' 2 - Se desejar ver as peças já adicionadas á fabrica'),nl,
    	print(' 3 - Se deseja terminar a insercção das peças'), nl,
    	read(O).
    
    check_val_fab(O):-
    	O>0,
    	O<4.
    
    
    add_peca_list_fab(P, Lista) :-
    	findall((K,Z), (peca(K,Z), K=P), Result),
    	append(Lista, Result,Result), print(Result), nl,nl,
    	Lista = Result,
    	print(Lista).
    	
    
    val_def_fab_option(O, Lista) :-
    	O = 1, !,
    		print('Peças disponiveis: '), nl,
    		findall(_,(peca(K,L), write(K), write(' - '), write(L),nl),_), 
    		nl,
    		read(P), add_peca_list_fab(P, Lista),nl;
    	O = 2, !, 
    		print(Lista),nl,nl;
    	O = 3.
    
    
    is_def_fab_quit_option(O) :-
    	O=3.
    		
    
    define_fabrica :-
    	Lista = [],
    	print('Introduza o nome da fabrica: '),
    	read(N), nl,
    	print('Introduza a coordenada X: '),
    	read(X), nl,
    	print('Introduza a coordenada Y: '),
    	read(Y), nl, nl,
    	repeat,
    		get_def_fab_option(O),
    		check_val_fab(O),
    		val_def_fab_option(O, Lista),
    		is_def_fab_quit_option(O),
    	!.
    
    Já tentei e não funciona no meu código... Isto é muito estranho... Começa por chamar o "define_fabrica"... Ele simplesmente não mexe no "Lista"...
     
  6. legerdemain

    legerdemain Power Member

    não sei se reparaste mas a assinatura do predicado add_peca_list_fab que eu pus é diferente

    add_peca_list_fab(P, Lista, ListaResultante) :-

    a variável ListaResultante é passada como argumento, para ser inicializado dentro do predicado e é a variável onde vai estar resultado da concatenação das listas Lista e Resultado

    em prolog puro tu não tens atribuição - a atribuição que existe é um artifício dos sistemas prolog
    o que tu tens é a unificação, e quando tentas unificar 2 variáveis que já estão instanciadas, aquilo falha (obviamente)
    é por isso que passas uma variável não instanciada - para que seja unificada dentro do predicado (e será o teu valor de retorno)
     
  7. FASC

    FASC Power Member

    E como é que eu aproveito essa variável FORA da função?
     
  8. Reptil

    Reptil Power Member

    Tenho aqui outro problema em prolog:
    por exemplo um predicado altura(+Arv,?N). que devolve emN a altura da arvore.Pensei em algo mas nao sei se so isso chega,pois nao tou a ver como aranjo maneira de diminuir o "N"
     
  9. legerdemain

    legerdemain Power Member

    essa descrição é um bocado vaga..
     
  10. Reptil

    Reptil Power Member

    Bem,tenho que admitir que tou a tentar resolver uma pergunta de um exame,para praticar.E a pergunta +e tal e qual como esta ai descrita.Um predicado que calcule a altura de uma arvore binaria.
    Sendo que geralmente as declarado assim:
    arvbin(vazia).
    arvbin(nodo(x,e,d)):-arvbin(e),arvbin(d).
     
  11. rjtd

    rjtd Power Member

    Hey man, prolog. Que degredo.
    Tens que ir fazendo isso tudo recursivo, até a lista estar vazia.
    Quanto ao resto, n me lembro. Detestei prolog na altura, e quem me deu isso ainda percebia menos que eu.
     
  12. Reptil

    Reptil Power Member

    Deixa me adevinhar tiraste na Uminho...os profs que dao prolog sao mt bons mesmos:P
    Pois mas nao tenho lista,e mesmo que tirando da arvore,o problema que coloco aqui é como tirar do N.
     
  13. legerdemain

    legerdemain Power Member

    essa declaração de árvore binária é estranha
    não devia ser um facto (i.e. sem corpo)?
    e.g. algo do género arvbin(nodo(1,arvbin(nodo(2,vazia,vazia)),arvbin(nodo(3,vazia,vazia))). que resulta em:
    Código:
                 1
               /   \
             2      3
    

    tentando responder concretamente à tua questão, podes ter algo do género:

    altura(arvbin(nodo(_,E,D)),N):-altura2(E,0,NE),altura2(D,0,ND),maior(NE,ND,N).

    altura2(arvbin(nodo(_,vazia,vazia)),N0,N):-N is N0+1.
    altura2(arvbin(nodo(_,E,D)),N0,N):-
    N1 is N0+1,altura2(E,N1,NE),altura2(D,N1,ND),maior(NE,ND,N).

    maior(NE,ND,N):-NE >= ND, N is NE.
    maior(NE,ND,N):-ND > NE, N is ND.

    acho que seria algo desta forma, estou a fazer de cabeça (mas sinto que falta alguma coisa..).. mas isto, assumindo que a definição da árvore é como aquela que usei

    edit: ah sim, faltam os casos quando nao ha 1 dos filhos, é código copy paste :p
     
    Última edição: 24 de Julho de 2007
  14. Reptil

    Reptil Power Member

    Agradeço a tua ajuda,mas ao ver a tua versao pensei nesta:
    altura(vazia,0).
    altura(nodo(x,vazia,vazia),1).
    altura(nodo(x,e,d),n):-N1 is N-1,altura(e,N1),altura(d,N1).

    Tambem da?
     
  15. legerdemain

    legerdemain Power Member

    na parte a negrito: o N não é suposto ser uma variável?
    se for uma variável, a instrução "N1 is N-1" falha
    se for uma constante, o que é que o predicado altura retorna?

    e não esquecer,
    minúsculas = constantes
    maiúsculas = variáveis
     
  16. Reptil

    Reptil Power Member

    Sim,todas as minuscula que pus ai eram de facto maisculas ou seja variaveis.Enganei me so ao teclar.
    Mas entao porque é que o N1 is N-1 falha?
    e no teu caso N1 is N0+1,dava?nao é parecido?
     
  17. legerdemain

    legerdemain Power Member

    edit: por variável, eu queria dizer variável instanciada

    N1 = N - 1

    qual é o valor de N nesta operação? se não estiver instanciada, não consegues realizar cálculos

    no meu caso, o N0 está instanciada
    repara no seguinte:
    altura(arvbin(nodo(_,E,D)),N):-altura2(E,0,NE),altura2(D,0,ND),maior(NE,ND,N).

    estou a instanciar N0 com o valor de 0 na chamada ao predicado altura2
     
    Última edição: 24 de Julho de 2007
  18. Reptil

    Reptil Power Member

    ok ja entendi.Mas durante um exame nunca me lembraria de algo assim:s
    Obrigado
     
  19. Reptil

    Reptil Power Member

    Vou reabrir este topico:P
    Pois é..acabei por nao passar no tal exame,amanha tenho a epoca especial referente a mesma materia.Vou so deixar aqui 2 exercicios que tinha que fazer..gostaria da vossa opiniao de como se poderia resolver,que é para ver se resolvi bem.
    -Definir o predicado posFirst(+elem,+list,?pos) que dado um elem Elem e uma lista List,determine a primeira posição onde ocorre Elem em List(0 se não ocorrer)

    -Uma forma simples de descrever um algoritmo de ordenação é:encontrar uma permutação da lista dada que esteja ordenada.Essa descrição pode ser directamente codificado em prolog usando o Generate-and-test.Codificiar o predicado slowSort/2

    Agradeço qualquer ajuda..é so uma forma de ver se resolvi,ou tentei resolver,da maneira corecta.
     
  20. Baderous

    Baderous Banido

    1º Exercício:

    posFirst(E,L,X):-append(L1,[E|_],L),length(L1,N),X is N+1,!.
    posFirst(_,_,0).

    Já vou fazer o 2º. Afinal também tenho exame amanhã! FMM is the 0ne! xD

    EDIT: Não percebo o 2º. Mas encontrei isto:

    slowsort(X,Y):-perm(X,Y),sorted(Y).

    sorted([]).
    sorted([X|[]]).
    sorted([X|[Y|Z]]):-X @=< Y, sorted([Y|Z]).

    perm([],[]).
    perm([X|Y],[U|V]):-delete(U,[X|Y],Z),perm(Z,V).

    delete(X,[X|Y],Y).
    delete(X,[Y|Z],[Y|W]):-delete(X,Z,W).

    Não sei para que precisas de usar o slowSort, eu quando quero ordenar uso o quickSort.
     
    Última edição: 13 de Setembro de 2007

Partilhar esta Página