Upload
benita-ines
View
6
Download
1
Embed Size (px)
Citation preview
Prolog V 1
V. E/S en Prolog
Jorge Cabrera GámezDepartamento de Informática y Sistemas
Universidad de Las Palmas de Gran Canaria
Prolog V 2
Índice.El modelo de E/S
Comunicación con ficherosStreams de entrada/salida implícitosStreams de entrada/salida explícitos
Predicados de E/S orientados a caracteres
Lectura de Programas
Sumario
Prolog V 3
Terminal
Programa
Prolog
Fichero 1
Fichero 2
...
Fichero 4
Fichero 3
...
useruser
inputstreams
outputstreams
El modelo de E/S
Prolog V 4
Modos de Comunicación con ficheros
Streams de entrada/salida implícitos(Estándar)
Streams de entrada/salida explícitos
Prolog V 5
Streams de entrada/salida implícitos
Idea básica: Durante la ejecución de un programa Prolog sólo dos ficheros están activos: uno de entrada y otro de salida
see(NombreFichero)...see(fichero1),lee_de_fichero(Datos),see(user),...
tell(NombreFichero)
stream de entradastream de salida
...tell(fichero1),escribe_en_fichero(Datos),tell(user),...
seen
told
Prolog V 6
Streams de entrada/salida implícitos
see(+SrcDest) Convierte a SrcDest en el stream de entrada activo. Si SrcDest ya había sido abierto con see/1 y no había sido cerrado, la lectura del fichero se retoma desde la posición actual del puntero. En otro caso, el fichero se abre y el puntero se sitúa al comienzo del mismo.
tell(+SrcDest) Idem. Nótese que en este caso si el fichero no existía se crea y si existía se trunca.
append(+File) Similar a tell/1, pero posiciona el puntero de fichero al final del mismo en vez de truncar un fichero ya existente.
Prolog V 7
Streams de entrada/salida implícitos
seeing(?SrcDest) Unifica el nombre del stream de entrada activo con SrcDest
telling(?SrcDest) Unifica el nombre del stream de salida activo con SrcDest
Prolog V 8
Streams de entrada/salida explícitos
open(+SrcDest, +Modo, -Stream, +Opciones)
* Stream: manejador del stream. * Modo: read, write, append o update. * Opciones: una lista de opciones.
type(Type): text (defecto) o binary.alias(Atom): Fija un nombre para el stream.
?- open(foo, read, S, [alias(in)]). buffer(Buffering): Opciones de buffering de la salida. fullf (defecto): buffering completo.
line: buffering por líneasfalse: no se realiza buffering
close(+Stream)
Prolog V 9
Streams de entrada/salida explícitos
seek(+Stream, +Offset, +Método, -NuevaPosición)
Reposiciona el puntero del stream a la posición dada. Offset: Indica el número de bytes del desplazamiento. Método: bof (desde el principio) current (desde la posición actual) eof (desde el final) NuevaPosición: El nuevo offset desde el comienzo del stream
Prolog V 10
Streams de entrada/salida explícitos
set_input(+Stream) Convierte Stream en el stream de entrada activo.
open(file, read, Stream), set_input(Stream). es equivalente a:
see(file). set_output(+Stream)
current_input(-Stream)
current_output(-Stream)
Prolog V 11
Read/Write
read(X)Predicado predefinido que permite leer un términodel stream de entrada.
Si el argumento de read no es unificable con el término a leer, read falla.
read es determinista: si read falla, no se intentaleer otro término en el backtracking.
write(X)Predicado predefinido que permite escribir un términoen el stream de salida.
Prolog V 12
Read/Write
Ejemplo:
cubo :-write(´Siguiente item: ´),read(X),procesa(X).
procesa(stop) :- !.
procesa(N) :-C is N*N*N, tab(3),write(´El cubo de ´),write(N),write(´ is ´), write(C), nl,cubo.
?- cubo.Siguiente item: 3. El cubo de 3 is 27Siguiente item: 34. El cubo de 34 is 39304Siguiente item: stop.
Yes
Prolog V 13
Read/Write
Ejemplo:
barras( [ ] ).
barras( [ L| LL] ) :-estrellas(L), nl,barras(LL).
estrellas(N) :-N > 0,write(*),N1 is N-1,estrellas(N1).
estrellas(N) :- N =< 0.
?- barras([1,2,5,3,4]).***************
Yes
?- barras([1,2,5,3,4]).
Prolog V 14
Read/Write
Ejemplo:
escribe_lista( [ ] ).
escribe_lista( [ L| LL] ) :-una_linea(L), nl,escribe_lista(LL).
una_linea( [ ] ).
una_linea( [ X | L ] ) :-write(X), tab(1),una_linea(L).
?- escribe_lista([[2],[a,d],[q,w]]).
2 a d q w
Yes
?- escribe_lista([a, b]).
No
?- escribe_lista([[2],[a,d],[q,w]]).
Prolog V 15
Read/Write
Ejemplo:
pp_lista(L) :- pp(L,0).
pp([H|T], I) :- !, J is I+3, pp(H,J), ppx(T,J), nl.
pp(X, I) :- tab(I), write(X), nl.
ppx([ ], _).ppx([H|T], I) :-
pp(H, I), ppx(T, I).
?- pp_lista([[a,s],[1,[2],3]]). a s
1 2
3
Yes
?- pp_lista([ [a,s], [1, [2], 3] ]).
Prolog V 16
Read/Write
Ejemplo:
pp_palabras([ ]) :- nl.pp_palabras([H|T]) :- write(H),
T == [], !, write(.);tab(1), pp_palabras(T).
?- pp_palabras([mi, mamá, me, ama ]).mi mamá me ama .
Yes
?- pp_palabras([mi, mamá, me, ama ]).
Prolog V 17
Read/Write
Ejemplo:
pp_palabras([ ]) :- nl.pp_palabras([W|Ws]) :-
write(W), Ws == [] -> write_ln(.);tab(1), pp_palabras(Ws).
?- pp_palabras([mi, mamá, me, ama ]).mi mamá me ama .
Yes
?- pp_palabras([mi, mamá, me, ama ]).
Prolog V 18
Ejemplo:
pp_palabras([]) :- nl.pp_palabras([H|T]) :-
name(H,[A|B]), es_letra(A,C), name(H1,[C|B]),palabras_aux([H1|T]).
pp_palabras(L) :- palabras_aux(L).
palabras_aux([]) :- nl.palabras_aux([H|T]) :-
write(H), T == [] -> write_ln(.);tab(1), palabras_aux(T).
es_letra(A,A1) :-A =< 122, A >= 97, !, A1 is A-32;A =< 90, A >= 65, A1 is A.
?- pp_palabras([mamá,me, mima]).Mamá me mima .Yes
?- pp_palabras([‘Mamá’,me, mima]).Mamá me mima .Yes
Prolog V 19
Una utilidad: Cómo leer del teclado una línea sin tener que terminarla en un punto final.
% read_line(-Line)% Reads characters from the keyboard until % it reaches an eof or a new line.read_line([Char | List]) :-
get0(Char),Char =\= -1, % EOFChar =\= 10, % New line!,read_line(List).
read_line([]).
?- read_line(Line).|: holaX = [104, 111, 108, 97].
Prolog V 20
Otra utilidad: Cómo leer todas las líneas de texto de un fichero, devolviendo el contenido como una lista de caracteres.
% read_file(File,Charlist) % Equivalent to read_file_to_codes(File,CharList,[]) % which is a predefined in SWI-Prologread_file(File, CharList) :-
see(File),read_list(CharList),seen.
% read_list(-List)% Reads characters from the the input % it reaches an eof.read_list([Char | List]) :-
get0(Char),Char =\= -1,!,read_list(List).
read_list([]).
Prolog V 21
..., see(fichero), procesar_fichero, see(user), ...
procesar_fichero :-read(Term),procesar_termino(Term).
procesar_termino(end_of_file) :- !. % Fin
procesar_termino(Term) :-treat(Term), % Se trata el términoprocesar_fichero. % Resto del fichero
Esquema básico para procesar un fichero de términos
Prolog V 22
browse(File) :- seeing(Old), /* Lo salvamos para después */ see(File), /* Abrimos este fichero */
repeat, read(Data), /* Leemos del fichero */ process(Data), !, seen, /* Cerramos el fichero */ see(Old). /* Volvemos al primero */
process(end_of_file) :- !. process(Data) :-
write(Data), nl, fail.
?- browse('browse.pl').browse(_G249):-seeing(_G251), see(_G249), repeat, read(_G255), process(_G255), !, seen, see(_G251).
process(end_of_file):-!
process(_G249):-write(_G249), nl, fail
Yes
Prolog V 23
Predicados de E/S orientados a caracteres.
put(C) Escribe el carácter C en el stream de salida
C es el código ASCII del carácter o el propio carácter.
?- put('B'), put(66), put(b), put(98).BBbbYesget0(C) Lee el siguiente carácter del stream de entrada. C es el código ASCII del carácter?- get0(X).| 1X = 49 Yes
get(C) Lee el siguiente carácter del stream de entrada diferente del espacio. C es el código ASCII del carácter.?- get(X).|| 2X = 50 Yes
Aquí espacio en blanco + [ENTER]
Prolog V 24
put/get
Ejemplo:
corrige :-get0(C),put(C),haz_el_resto(C).
haz_el_resto(46) :- !. % Codigo ASCII del punto (.)
haz_el_resto(32) :- % Codigo ASCII del blanco!,get(C), % No consideramos otros blancosput(C), haz_el_resto(C).
haz_el_resto(Letra) :- corrige.
Elimina múltiples espacios entre palabras de una frase terminada por un punto
?- corrige.| Erase una vez un . Erase una vez un .Yes
Prolog V 25
Lo que hay que hacer:
1.Leer el texto del fichero2.Agrupar caracteres en palabras (“Tokenize”)3.Ordenar (sin eliminar duplicados)4.Contar los duplicados
El resultado debe ser una lista de pares del tipo:
[Apariciones, Palabra]
Ejercicio:
Contar el número de ocurrencias de una palabra en un texto
Prolog V 26
Solución:
:-ensure_loaded('tokenize.pl').
word_counter( MyFile, UnigramList):-
% Leer el texto del ficheroread_file_to_codes(MyFile, CharacterList,[]),
%Agrupar caracteres en palabras (“Tokenize”)tokenizes(CharacterList,TokenList),
%Ordenar (sin eliminar duplicados)msort(TokenList, OrderedTokens),
%Contar los duplicadoscount_duplicates(OrderedTokens, UnigramList).
Prolog V 27
% tokenize(+Chars, -Tokens)% breaks a list of characters into a list of tokens.% It uses blanks/2 that removes the blank characters from% the head of the list and token/3 that builds one% token from the characters of the head of the list.tokenize([], []) :- !.tokenize(Chars, Tokens) :-
blanks(Chars, RemainingChars),tokenize(RemainingChars, Tokens),!.
tokenize(Chars, [Token | Tokens]) :-token(Chars, Token, RemainingChars),tokenize(RemainingChars, Tokens).
% blanks(+Chars, -RemainingChars)% Removes the blank characters from the head of the list of Chars% RemainingChars contains the rest of the list.blanks([Char1, Char2 | Chars], [Char2 | Chars]) :-
Char1 =< 32, % blank = 32, non-printable chars < 32Char2 > 32,!.
blanks([], []) :- !.blanks([Char | Chars], RemainingChars) :-
Char =< 32,blanks(Chars, RemainingChars).
Prolog V 28
% token(+Chars, -Token, -RemainingChars)% Builds one token from the characters of the head of the list.% Token is the built token and RemainingChars is the rest of the listtoken(Chars, Token, RemainingChars) :-
alphanumeric_token(Chars, TokenChars, RemainingChars),name(Token, TokenChars),!.
token(Chars, Token, RemainingChars) :-others(Chars, TokenChar, RemainingChars),name(Token, [TokenChar]).
% alphanumeric_token(+Chars, -TokenChars, -RemainingChars)% Returns the characters of the first token on the head% of the list.alphanumeric_token([Char1, Char2 | Chars], [Char1], [Char2 | Chars]) :-
alphanumeric(Char1),\+ alphanumeric(Char2),!.
alphanumeric_token([], [], []) :- !.alphanumeric_token([Char | Chars], [Char | TokenChars], RemainingChars) :-
alphanumeric(Char),!,alphanumeric_token(Chars, TokenChars, RemainingChars).
Prolog V 29
% alphanumeric(+Char)% Checks whether Char is alphanumeric. There are several cases:
% Lower-case letters without accentalphanumeric(Char) :- 97 =< Char, Char =< 122, !.
% Upper-case letters without accentalphanumeric(Char) :- 65 =< Char, Char =< 90, !.
% Accented characters. The values 215 and 247 correspond to% the multiplication and division: × ÷alphanumeric(Char) :-
192 =< Char, Char =< 255,Char =\= 215, Char =\= 247,!.
% Digitsalphanumeric(Char) :-
48 =< Char, Char =< 57,!.
% The oe, OE, and Y" lettersalphanumeric(Char) :-
(Char =:= 140 ; Char =:= 156 ; Char =:= 159),!.
others([Char | Chars], Char, Chars).
Prolog V 30
% Cuenta el número de veces que un elemento aparece de forma% consecutiva en una lista
count_duplicates(OrderedList, CountedList) :-count_duplicates(OrderedList, 1, [], CountedListRev),reverse(CountedListRev, CountedList).
count_duplicates([X, X | Ordered], N, Counting, Counted) :-N1 is N + 1,!,count_duplicates([X | Ordered], N1, Counting, Counted).
count_duplicates([X | Ordered], N, Counting,Counted) :-!,count_duplicates(Ordered, 1, [[N, X] | Counting], Counted).
count_duplicates([], _, L, L).
Prolog V 31
nl nl(+Stream)
put(+Char) put(+Stream, +Char)
tab(+Espacios) tab(+Stream, +Espacios)
flush flush(+Stream)
get0(-Char) get0(+Stream,-Char)
get(-Char) get(+Stream,-Char)
peek_byte(-Char) peek_byte(+Stream,-Char)
skip(+Char) skip(+Stream,+Char)
write(+Term) write(+Stream,+Term)
read(-Term) read(+Stream,-Term)
Prolog V 32
name(?Atom, ?List)
atom_chars(?Atom, ?String)
atom_char(?Atom, ?ASCII)
atom_length(+Atom,-Length)
string_to_atom(?String, ?Atom)
string_to_list(?String, ?List)
string_length(+String, -Length)
string_concat(?String1, ?String2, ?String3)
?- string_to_atom("Hola que tal", A).A = 'Hola que tal' Yes?- string_to_list("Hola que tal",L).L = [72, 111, 108, 97, 32, 113, 117, 101, 32, 116, 97, 108] Yes
?- atom_chars(pepelu, A).A = [112, 101, 112, 101, 108, 117]Yes?- atom_char(p, C).C = 112Yes
Prolog V 33
write_nl(+Term)
writef (+Format, +Arguments)
swritef (-String, +Format,+Arguments)
format(+Format, +Arguments)
?- X is 17.2, Y is 238, format('Runtime: ~`.t ~2f~34| Inferences: ~`.t ~D~72|~n', [X,Y]).
Runtime: ................... 17.20 Inferences: .................... 238
Prolog V 34
Lectura de programas
consult(+Fichero)
[Fichero1, Fichero2]
reconsult(+Fichero)
No es necesario,(no existe)en SWI-Polog.
Prolog V 35
Sumario.
• E/S implícita y explícita. [user_input],
[user_output]
como flujos de entrada salida por defecto.
• read/write para leer y escribir términos.
• get/put para leer y escribir caracteres.
• SWI-Prolog oferta una gran variedad de
predicados
para producir una salida con formato.
• Para leer programas Prolog usar consult
Prolog V 36
Problemas
10. Implementar en Prolog los siguientes predicados que operan sobre conjuntos:A) permutacion(Xs, Ys), que devuelva en Ys las permutaciones posibles de la lista Xs (nota: cada permutación se consideraría como una solución).B) combinacion(Xs, N, Ys), que devuelva en Ys las combinaciones posibles de los elementos de Xs cuando éstos se toman de N en N.C) diferencia(Xs, Ys, Zs), que devuelva el Zs el conjunto diferencia de los conjuntos (listas) Xs e Ys. El conjunto diferencia debe contener los elementos que aparecen en sólo uno de los conjuntos.D) union(Xs, Ys, Zs), que devuelve en Zs la union (sin duplicados) de los conjuntos Xs e Ys.E) interseccion(Xs, Ys, Zs), que devuelve en Zs la intersección de los conjuntos Xs e Ys.
Prolog V 37
%Problema 10, A% extract(X,Ys,Zs) Genera la lista Zs extrayendo de la % lista Ys una ocurrencia de X
extract(X,[X|Xs],Xs).
extract(X,[Y|Ys],[Y|Zs]):- extract(X,Ys,Zs).
% permutation(Xs, Zs) % Devuelve en Zs una permutación de los elementos% de la lista Xs. La idea es generar las permutaciones% de los n elementos extrayendo uno de los elementos% mediante extract/3 y generando las permutaciones de % orden inferior (n-1 elementos) a las que se añade % por la cabeza el elemento seleccionado con extract/3.
permutation(Xs, [Z|Zs]):- extract(Z, Xs, Ys), permutation(Ys,Zs).
permutation([ ], [ ]).
Prolog V 38
2 ?- extract(X,[a,b,c],Xs).
X = a,Xs = [b, c] ;
X = b,Xs = [a, c] ;
X = c,Xs = [a, b] ;
No
Prolog V 39
[debug] ?- permutation([a,b],Z). T Call: (7) permutation([a, b], _G394) T Call: (8) extract(_G446, [a, b], _G478) T Exit: (8) extract(a, [a, b], [b]) T Call: (8) permutation([b], _G447) T Call: (9) extract(_G449, [b], _G481) T Exit: (9) extract(b, [b], []) T Call: (9) permutation([], _G450) T Call: (10) extract(_G452, [], _G484) T Fail: (10) extract(_G452, [], _G484) T Redo: (9) permutation([], _G450) T Exit: (9) permutation([], []) T Exit: (8) permutation([b], [b]) T Exit: (7) permutation([a, b], [a, b])
Z = [a, b] ;
Prolog V 40
T Fail: (9) permutation([], _G450) T Redo: (9) extract(_G449, [b], _G481) T Call: (10) extract(_G449, [], _G453) T Fail: (10) extract(_G449, [], _G453) T Fail: (9) extract(_G449, [b], _G481) T Fail: (8) permutation([b], _G447) T Redo: (8) extract(_G446, [a, b], _G478) T Call: (9) extract(_G446, [b], _G450) T Exit: (9) extract(b, [b], []) T Exit: (8) extract(b, [a, b], [a]) T Call: (8) permutation([a], _G447) T Call: (9) extract(_G452, [a], _G484) T Exit: (9) extract(a, [a], []) T Call: (9) permutation([], _G453) T Call: (10) extract(_G455, [], _G487) T Fail: (10) extract(_G455, [], _G487) T Redo: (9) permutation([], _G453) T Exit: (9) permutation([], []) T Exit: (8) permutation([a], [a]) T Exit: (7) permutation([a, b], [b, a])Z = [b, a] Yes
Prolog V 41
/*************************************************************** Una solución equivalente basada en la idea de insertar elementos****************************************************************/insert(L, X,[X|L]).insert([H|T],X,[H|L]):- insert(T,X,L).
permutation2([ ],[ ]).permutation2([X|Xs],Zs):-
permutation2(Xs,Ys),insert(Ys,X,Zs).
4 ?- insert([1,2],a,L).
L = [a, 1, 2] ;
L = [1, a, 2] ;
L = [1, 2, a] ;
No
Prolog V 42
%Problema 10, B/***************************************************B) combination(Xs, N, Ys), que devuelva en Ys las combinaciones posibles de los elementos de Xs cuando éstos se toman de N en N.****************************************************/
combination(_,0,[ ]).
combination(Xs,1,[X]):- extract(X,Xs,_).
combination([X|Xs],N,[X|Zs]):-N > 1,N1 is N-1,combination(Xs,N1,Zs).
combination([_|Xs],N,Zs):-N > 1,combination(Xs,N,Zs).
7 ?- combination([1,2,3],2,Cs).
Cs = [1, 2] ;
Cs = [1, 3] ;
Cs = [2, 3] ;
No
Prolog V 43
% Problema 10, CC) difference(Xs, Ys, Zs), que devuelva el Zs el conjunto diferencia de los conjuntos (listas) Xs e Ys. El conjunto diferencia debe contener los elementos que aparecen en sólo uno de los conjuntos.
difference(Xs,Ys,Zs):-list_to_set(Xs,Xs1), % Eliminar duplicadoslist_to_set(Ys,Ys1), % Eliminar duplicadosdif_aux(Xs1,Ys1,Zs).
dif_aux([ ],Zs,Zs).dif_aux([X|Xs],Ys,Zs):-
(memberchk(X,Ys), !, extract(X,Ys,Ys1);Ys1 = [X|Ys] ),dif_aux(Xs,Ys1,Zs).
Prolog V 44
%Problema 10, D
set_union(Xs, Ys, Zs), que devuelve en Zs la union (sin duplicados) de los conjuntos Xs e Ys.
set_union([ ], Ys, Zs):- list_to_set(Ys,Zs).set_union([X|Xs],Ys,Zs):-
\+member(X,Ys),!, set_union(Xs,[X|Ys],Zs);set_union(Xs,Ys,Zs).
% Alternativaset_union2(Xs,Ys,USs):-
append(Xs,Ys,ULs),list_to_set(ULs,USs).
Prolog V 45
set_intersection(Xs,Ys,Zs):- list_to_set(Xs,Xs1),inter_aux(Xs1,Ys,[ ],Zs).
inter_aux([ ], _, Zs, Zs).
inter_aux([X|Xs],Ys,Ws,Zs):-member(X,Ys),!, inter_aux(Xs,Ys,[X|Ws],Zs);inter_aux(Xs,Ys,Ws,Zs).
% Problema 10, E
E) set_intersection(Xs, Ys, Zs), que devuelve en Zs la intersección de los conjuntos Xs e Ys.
Prolog V 46
11. Implementar el predicado max_lista(Xs, Y) que permita recuperar en Y el máximo de los números contenidos en la lista Xs.
% Problema 11. max_lista([X],X) :- !. % Este cut evita una
% llamada inutil con [ ] max_lista([X|S],M) :-
max_lista(S,P), X < P, !, M is P;M is X.
SWI-Prolog
Prolog V 47
12. Dada una lista conteniendo números enteros, devolver dos listas conteniendo respectivamente los números positivos (incluido el cero) y los números negativos. Realizar dos implementaciones de este predicado: una sin emplear el predicado cut (!) y otra que sí lo utilice.
% Problema 12.separa([ ], [ ], [ ]).separa([X|S], [X|P], N) :- X >= 0, separa(S, P, N).separa([X|S], P, [X|N]) :- X < 0, separa(S, P, N).
Problemas
SWI-Prolog
separa_cut([ ], [ ], [ ]).separa_cut([X|S], [X|P], N) :- X >= 0, !, separa_cut(S, P, N).separa_cut([X|S], P, [X|N]) :- separa_cut(S, P, N).
Prolog V 48
?- separa([1,2,-3,4,0,-2],P,N).T Call: ( 7) separa([1, 2, -3, 4, 0, -2], _G250, _G251)T Call: ( 8) separa([2, -3, 4, 0, -2], _G386, _G251)T Call: ( 9) separa([-3, 4, 0, -2], _G389, _G251)T Redo: ( 9) separa([-3, 4, 0, -2], _G389, _G251)T Call: ( 10) separa([4, 0, -2], _G389, _G392)T Call: ( 11) separa([0, -2], _G395, _G392)T Call: ( 12) separa([-2], _G398, _G392)T Redo: ( 12) separa([-2], _G398, _G392)T Call: ( 13) separa([], _G398, _G401)T Exit: ( 13) separa([], [], [])T Exit: ( 12) separa([-2], [], [-2])T Exit: ( 11) separa([0, -2], [0], [-2])T Exit: ( 10) separa([4, 0, -2], [4, 0], [-2])T Exit: ( 9) separa([-3, 4, 0, -2], [4, 0], [-3, -2])T Exit: ( 8) separa([2, -3, 4, 0, -2], [2, 4, 0], [-3, -2])T Exit: ( 7) separa([1, 2, -3, 4, 0, -2], [1, 2, 4, 0], [-3, -2])P = [1, 2, 4, 0]N = [-3, -2] ;
T Redo: ( 11) separa([0, -2], _G395, _G392)T Fail: ( 11) separa([0, -2], _G395, _G392)T Redo: ( 10) separa([4, 0, -2], _G389, _G392)T Fail: ( 10) separa([4, 0, -2], _G389, _G392)T Fail: ( 9) separa([-3, 4, 0, -2], _G389, _G251)T Redo: ( 8) separa([2, -3, 4, 0, -2], _G386, _G251)T Fail: ( 8) separa([2, -3, 4, 0, -2], _G386, _G251)T Redo: ( 7) separa([1, 2, -3, 4, 0, -2], _G250, _G251)T Fail: ( 7) separa([1, 2, -3, 4, 0, -2], _G250, _G251)
No
?- separa_cut([1,2,-3,4,0,-2],P,N).T Call: ( 8) separa_cut([1, 2, -3, 4, 0, -2], _G274, _G275)T Call: ( 9) separa_cut([2, -3, 4, 0, -2], _G410, _G275)T Call: ( 10) separa_cut([-3, 4, 0, -2], _G413, _G275)T Redo: ( 10) separa_cut([-3, 4, 0, -2], _G413, _G275)T Call: ( 11) separa_cut([4, 0, -2], _G413, _G416)T Call: ( 12) separa_cut([0, -2], _G419, _G416)T Call: ( 13) separa_cut([-2], _G422, _G416)T Redo: ( 13) separa_cut([-2], _G422, _G416)T Call: ( 14) separa_cut([], _G422, _G425)T Exit: ( 14) separa_cut([], [], [])T Exit: ( 13) separa_cut([-2], [], [-2])T Exit: ( 12) separa_cut([0, -2], [0], [-2])T Exit: ( 11) separa_cut([4, 0, -2], [4, 0], [-2])T Exit: ( 10) separa_cut([-3, 4, 0, -2], [4, 0], [-3, -2])T Exit: ( 9) separa_cut([2, -3, 4, 0, -2], [2, 4, 0], [-3, -2])T Exit: ( 8) separa_cut([1, 2, -3, 4, 0, -2], [1, 2, 4, 0], [-3, -2])P = [1, 2, 4, 0]N = [-3, -2] ;No
Prolog V 49
Problemas13. Definir los operadores ‘if’, ‘then’, ‘else’ y ‘:=’ de manera que el siguiente término sea sintácticamente correcto:
if X >Y then Z:= X else Z:= Y
Elegir las precedencias de forma que ‘if’ sea el functor principal. Defina la relación ‘if’ como un pequeño intérprete para una expresión del tipo ‘if-then-else’ de la forma:
if Val1 > Val2 then Var:= Val3 else Var:= Val4
donde Val1, Val2, Val3 y Val4 son números, o variables instanciadas en
números, y Var es una variable. Lo que sigue es un ejemplo de cómo
debería utilizarse este intérprete:
?- X = 2, Y = 3, Val2 is 2*X, Val4 is 4*X,
if Y > Val2 then Z:= Y else Z:= Val4,
if Z > 5 then W:= 1 else W:= 0.
X = 2 Y = 3 Z = 8 W = 1 Val2 = 4 Val4 = 8 SWI-Prolog
Prolog V 50
% Problema 13.:- op(900, fx, if).:- op(800, xfx, then).:- op(700, xfx, else).:- op(600, xfx, :=).
if Val1 > Val2 then Var:= Val3 else Var:= Val4 :-Val1 > Val2, !, Var = Val3;Var = Val4.
SWI-Prolog
Prolog V 51
14. Definir el predicado freq(Xs, Ys) de manera que ante una lista de números enteros (Xs) obtenga una lista (Ys) que contenga las frecuencias de aparición de los diferentes elementos de la lista Xs. Por ejemplo:
?- freq([3,3,2,2,1,1,2,2,3,3], A).
A = [2*1,4*2,4*3]
donde la nomenclatura empleada en la lista A indica que existen 2 ocurrencias de 1, 4 de 2 y 4 de 3. Nota: El que la lista resultado salga ordenada puede facilitar la obtención de la solución.
Problemas
SWI-Prolog
Prolog V 52
% Problema 14.freq(L, S) :- freq(L, [], S).freq([], S, S).freq([N|L], S1, S3) :- actualiza(N, S1, S2), freq(L, S2, S3).
% actualiza(clave, listaentrada, listasalida)actualiza(N, [], [1*N]).actualiza(N, [F*N|S], [F1*N|S]) :- !, F1 is F+1.actualiza(N, [F*M|S], [1*N,F*M|S]) :- N < M, !.actualiza(N, [F*M|S], [F*M|S1]) :- N \== M, actualiza(N,S,S1).
?- freq([3,3,2,2,1,1,2,2,3,3], A).
A = [2*1,4*2,4*3]
SWI-Prolog