A) Define los siguientes predicados: es la concatenación de las

Anuncio
Examen de LABORATORIO IV
Junio de 2001
UNIVERSIDAD DE MÁLAGA
Departamento de Lenguajes y Ciencias de
la Computación
Apellidos................................................................................Nombre ...........................................
Especialidad:
Gestión [ ]
Grupo: A [ ]
Sistemas [ ]
B [ ]
PROGRAMACIÓN LÓGICA
A) Define los siguientes predicados:
concatena(Xs,Ys,XsYs) XsYs es la concatenación de las listas Xs e Ys.
selecciona(X,AsXBs,AsBs) AsBs es la lista AsXBs con una aparición menos del
elemento X.
suma(Xs,N) N es la suma de todos los elementos de la lista Xs.
todosmayores(Xs,N) todos los elementos de la lista Xs son mayores que N.
concatena([],Ys,Ys).
concatena([X|Xs],Ys,[X|Zs]):concatena(Xs,Ys,Zs).
selecciona(X,[X|Xs],Xs).
selecciona(X,[Y|Ys],[Y|Zs]):selecciona(X,Ys,Zs).
suma([],0).
suma([X|Xs],N):suma(Xs,N1),
N is X+N1.
todosmayores([],_N).
todosmayores([X|Xs],N):X>N,
todosmayores(Xs,N).
B) Define un predicado premax(PsRs,N,Ps,Rs) que devuelva en Ps el prefijo no
vacío más largo posible de la lista PsRs, tal que la suma de sus elementos no supere
el valor N, y devuelva en Rs el resto de PsRs. Ejemplo:
?- premax([3,6,2,1,6,4],10,Ps,Rs).
Ps = [3,6] Rs = [2,1,6,4]
?- premax([13,6,2,1,6,4],10,Ps,Rs).
No
premax([X|Xs],N,[X|Xs],[]):suma([X|Xs],M),
M=<N.
premax([X|Xs],N,[A|As],[Y|Ys]):concatena([A|As],[Y|Ys],[X|Xs]),
suma([A|As],M),
M =< N,
M+Y > N.
C) Define un predicado partir(Ls,N,Es) que devuelva en Es la lista de las sublistas
lo más largas posible de Ls tales que la suma de sus elementos no supere el valor N.
Ejemplos:
?- partir([3,6,2,1,6,4],10,Es).
Es = [[3,6],[2,1,6],[4]]
?- partir([3,6,2,12,6,4],10,Es).
No
partir([],_,[]).
partir([X|Xs],N,[As|Yss]):premax([X|Xs],N,As,Bs),
partir(Bs,N,Yss).
D1) Define un predicado selecmax(Ls,N,Xs,Rs) que devuelva en Xs una lista no
vacía de elementos de Ls tal que la suma de éstos se acerque lo más posible a N sin
superarlo, y en Rs devuelve el resto de elementos de Ls. Ejemplo:
?- selecmax([3,6,2,1,6,4],10,Es,Rs).
Es = [3, 6, 1]
Rs = [2, 6, 4] ;
Es = [6, 1, 3]
Rs = [2, 6, 4] ;
Es = [6, 2, 1]
Rs = [3, 6, 4] ;
...
selecmax(Xs,N,[],Xs):todosmayores(Xs,N),
!.
selecmax(Xs,N,[X|Ys],Rs):selecciona(X,Xs,Ls),
X =< N,
N1 is N-X,
selecmax(Ls,N1,Ys,Rs).
(El orden en que obtengas las soluciones no tiene que coincidir con el del ejemplo)
D2) Define un predicado reparte(Ls,N,Xss) que reparta los elementos de la lista Ls
en una lista de listas Xss tal que la suma de los elementos de cada lista de Xss se
acerque lo más posible a N sin superarlo. Ejemplo:
?- reparte([3,6,2,1,6,4],10,Xss).
Xss = [[3,6],[6,4],[2,1]];
Xss = [[6,3],[6,4],[1,2]];
Xss = [[6,2,1],[6,3],[4]];
...
(El orden en que obtengas las soluciones no tiene que coincidir con el del ejemplo)
reparte([],_,[]).
reparte([X|Xs],N,[As|Yss]):selecmax([X|Xs],N,As,Ls),
reparte(Ls,N,Yss).
PROGRAMACIÓN FUNCIONAL
Sea el tipo data Elemento = E String Int deriving Show
para representar una palabra y un contador asociado a ella.
A) Los datos de este tipo debe poder compararse y ordenarse por el campo de tipo
String lexicográficamente. Define funciones de igualdad y orden (Se recomienda la
definición de las instancias correspondientes).
instance Eq Elemento where
(E s n) == (E s' n') = s == s'
instance Ord Elemento where
(E s n) <= (E s' n') = s <= s'
B) Sea el tipo
data Árbol a = Vacío | Nodo (Árbol a) a (Árbol a) deriving Show
y sea el sinónimo de tipo
type Dic = Árbol Elemento
Queremos que los datos de Dic representen un árbol binario de búsqueda cuya
información son datos de tipo Elemento. El orden de inclusión viene determinado por el
definido en el apartado anterior. Define las siguiente función:
insertar :: Elemento -> Dic -> Dic
insertar :: Elemento -> Dic -> Dic
insertar e'@(E s' n') Vacío = Nodo Vacío e' Vacío
insertar e'@(E s' n') (Nodo i e@(E s n) d)
| e' == e
= Nodo i (E s (n+n')) d
| e' < e
= Nodo (insertar e' i) e d
| otherwise = Nodo i e (insertar e' d)
que inserta un elemento en el árbol teniendo en cuenta que si ya está, debe actualizar el
contador con la suma de ambos y si no, creará un nuevo nodo.
C) Utilizando map y foldr, define una función creaDic para que, a partir de una lista
de palabras (posiblemente repetidas), genere la correspondiente lista de elementos y, a
partir de ella, cree un árbol binario de búsqueda que almacene toda la información de la
lista.
creaDic :: [String] -> Dic
creaDic :: [String] -> Dic
creaDic = foldr insertar Vacío . map (\s -> E s 1)
D.1) Define una función de plegado, foldÁrbol, para el tipo Árbol a. Usando este
plegado, crea una función listado que genere una lista ordenada de elementos a partir
de un árbol binario de búsqueda.
foldÁrbol :: (b -> a -> b -> b) -> b -> Árbol a -> b
foldÁrbol f z Vacío
= z
foldÁrbol f z (Nodo i r d) =
f (foldÁrbol f z i) r (foldÁrbol f z d)
listado :: Dic -> [Elemento]
listado = foldÁrbol (\i r d -> i ++ [r] ++ d) []
D.2) Define una función que devuelva una lista con el/los elemento/s más citado/s (con
mayor contador) de un árbol binario de búsqueda. (Se recomienda hacerla usando
foldÁrbol). Ejemplo, siendo:
l = ["pepe","juan","pedro","pedro","pepe","pedro","luis","pepe"])
entonces
Main> másCitados (creaDic l)
[E "pepe" 3, E "pedro" 3] :: [Elemento]
másCitados :: Dic -> [Elemento]
másCitados = foldÁrbol (\i r d -> une [r] (une i d)) []
where
une xs@(E s n:_) xs'@(E s' n':_)
| n == n'
= xs ++ xs'
| n > n'
= xs
| otherwise = xs'
Descargar