



















Estude fácil! Tem muito documento disponível na Docsity
Ganhe pontos ajudando outros esrudantes ou compre um plano Premium
Prepare-se para as provas
Estude fácil! Tem muito documento disponível na Docsity
Prepare-se para as provas com trabalhos de outros alunos como você, aqui na Docsity
Encontra documentos específicos para os exames da tua universidade
Prepare-se com as videoaulas e exercícios resolvidos criados a partir da grade da sua Universidade
Responda perguntas de provas passadas e avalie sua preparação.
Ganhe pontos para baixar
Ganhe pontos ajudando outros esrudantes ou compre um plano Premium
Aula 8° Listas infinitas - Programação Funcional
Tipologia: Notas de aula
1 / 27
Esta página não é visível na pré-visualização
Não perca as partes importantes!




















Pedro Vasconcelos DCC/FCUP
Podemos dar um nome novo a um tipo existente usando uma declaração de sinónimo.
Exemplo (do prelúdio-padrão):
type String = [Char]
As declarações de sinónimos também podem ter parâmetros.
Exemplo: associações entre chaves e valores.
type Assoc ch v = [(ch,v)] -- tabela de associações
idades :: Assoc String Int idades = [("Pedro", 41), ("João", 27), ("Maria", 19)]
emails :: Assoc String String emails = [("Pedro", "[email protected]"), ("João", "[email protected]")]
Os sinónimos podem ser usados noutras definições:
type Pos = (Int,Int) type Cells = [Pos] -- OK
Mas não podem ser usados recursivamente:
type List a = (a,List a) -- ERRO
A declaração data enumera as alternativas separadas por barras verticais. Cada alternativa deve ter um construtor (ex.: True e False). O nome dos tipos e construtores deve ser começar por uma letra maiúscula. Cada construtor só pode ser usado num único tipo.
Podemos definir funções sobre novos tipos usando padrões.
Exemplo: um tipo para as direções ortogonais (esquerda, direita, cima, baixo).
data Dir = Esq | Dir | Cima | Baixo
Vamos definir algumas funções...
Os construtores podem também ter parâmetros.
Exemplo:
data Figura = Circ Float -- raio | Rect Float Float -- largura, altura
quadrado :: Float -> Figura quadrado h = Rect h h
area :: Figura -> Float area (Circ r) = pir^ area (Rect w h) = wh
Os construtores podem ter diferentes números de parâmetros Os parâmetros podem ser de tipos diferentes Podemos usar os construtores de duas formas: como funções para construir um valor Circ :: Float -> Figura Rect :: Float -> Float -> Figura em padrões no lado esquerdo de equações area (Circ r) = pir^ area (Rect w h) = wh
Podemos definir igualdade e conversão para texto automaticamente usando “deriving”:
data Figura = Circ Float | Rect Float Float deriving (Eq, Show) Exemplo de uso:
> Circ 2 Circ 2.
> Rect 2 1 == Rect 1 2 False
A igualdade é sintática: dois valores são iguais se e só se têm o mesmo construtor e argumentos.
As declarações de novos tipos também podem ter parâmetros.
Exemplo:
data Maybe a = Nothing | Just a -- do prelúdio-padrão
safediv :: Int -> Int -> Maybe Int safediv _ 0 = Nothing safediv n m = Just (ndivm)
safehead :: [a] -> Maybe a safehead [] = Nothing safehead xs = Just (head xs)
Alguns valores de Nat:
Zero -- zero Suc Zero -- um Suc (Suc Zero) -- dois Suc (Suc (Suc Zero)) -- três .. .
Em geral: n é obtido aplicado n vezes Succ a Zero.
Suc (Suc (... (Suc Zero)...)) -- n aplicações
Usando recursão, podemos definir funções que convertem entre inteiros e naturais: int2nat :: Int -> Nat int2nat 0 = Zero int2nat n | n>0 = Suc (int2nat (n-1))
nat2int :: Nat -> Int nat2int Zero = 0 nat2int (Suc n)= 1+nat2int n
Em alternativa, podemos definir a soma usando recursão sobre naturais. add :: Nat -> Nat -> Nat add Zero m = m add (Suc n) m = Suc (add n m)
Estas duas equações traduzem as seguintes igualdades algébricas:
0 + m = m ( 1 + n) + m = 1 + (n + m)
Exemplo:
Suc (Suc (Suc Zero))