Funções são cidadãos do primeiro classe

Podemos passar elas como argumentos :


(defn m2 [x] (* 2 x))

(defn meu-map [f xs]
(lazy-seq
(if (empty? xs) '()
(cons (f (first xs)) (meu-map f (rest xs)) ))))

(meu-map m2 '(1 2 3 4 5))

Podemos produzir elas utilizando partial pra "customizar" funções que já existe :


(meu-map (partial * 2) '(1 2 3 4 5))

partial 'e um funciao que aceita um outra funciao como argumento, pre-encha algumas argumentos dele, e devolver o funciao meia pronto pra utilizar, esperando so que esta faltando.

Por exemplo. Nos temos o funciao "meu-map" que percore uma lista e aplica um outro funciao como m2.

Podemos utilizar "partial" pra criar um funciao que sempre percore uma lista e aplicar um dobro pra todos os numeros.


(def meu-dobro (partial meu-map (partial * 2)))

(meu-dobro '(1 2 3 4 5))

Obs : "partial" 'e um coisa muito comon em programacao funcional. Mas muitas vezes esta chamada "curry" (e a atividade, em ingles, chamada "currying")

Funções Anônimos

Como nos queremos passar muitos pequenos funções como argumentos para outros funções, temos a capacidade definir funções anônimos (tambem chamada lambdas)

Em Clojure, escreve assim, usando a fn :


(meu-map (fn [x] (* x 3)) '(1 2 3 4 5))

Tambem existe um jeito mais curto, usando o #


(meu-map #(* %1 3) (range 9))

Em realidade, nao precisamos definir nossa funciao "meu-map". A biblioteca padrão contem varias funções pra tratar listas com outras funções

Map


(map (partial * 4) '(1 2 3 4 5))

Filter


(filter (fn [x] (< x 5)) (range 10))

Fold / Reduce


(reduce * 1 '(1 2 3 4 5))

Zip (using


(map vector (range 10) (range 10))

Exercício 6

  • 6.1 - Escrever um funciao que calcular o raiz quadrada de cada elemento duma lista utilizando o map proprio do Clojure. Raiz quadrada 'e (.sqrt js/Math 3)


O funciao iterate cria um sequencia infinita com um valor inicial x e o funciao, f e produz um sequence x f(x) (f (f x)) (f (f (f x))) etc.



(take 10 (iterate #(+ % 1) 0))
  • 6.2 - Escrever um funciao que produz o sequence '(1 4 7 10 13 16 19 22 25 ...)


  • 6.3 - Escrever um funciao rqs que produz a lista preguisoza (possivalmente infinito) de numeros com suas raizes quadrados. eg.
(rqs) -> ([0 0]
[1 1]
[2 1.4142135623730951]
[3 1.7320508075688772]
[4 2]
[5 2.23606797749979]
[6 2.449489742783178]
[7 2.6457513110645907]
[8 2.8284271247461903]
[9 3] ... )


(take 40 (rqs))

  • 6.3 - Escrever um funciao de ordenacao duma lista como "quicksort" utilizando filter e recursividade.



Vai ao Pagina 4