Aumente O Poder Das Suas Macros Usando Unquote Splicing
No post anterior, aprendemos a criar macros que aumentam significativamente a legibilidade do nosso código. Porém, deixamos um detalhe importante para trás: Unquote Splicing
No final do último post criamos uma macro chamada unless
, que basicamente executa múltiplas expressões caso uma determinada condição seja false
.
Usamos a função macroexpand
para exibir qual código será evaluated. Mas se tentarmos executar este código, além da string If invertido
, a famosa NullPointerException
será lançada. Mas por que isso acontece?
Neste caso, o Clojure está tentando fazer evaluate do resultado da chamada a função println
, que é nil
. Olhando a expressão com mais cuidado (do ((println "If invertido"))))
, dá para perceber que existe um parantêses a mais na história, de maneira que o que é passado para a macro do
é exatamente o valor nil
: (do (nil))
.
Isso acontece porque quando fizemos o unquote do argumento branches
, no exemplo (println "If invertido")
, a lista foi evaluated e colocada no retorno da macro, como num processo similar a variáveis em um template, uma substituição é feita com o valor exato que foi evaluated.
O Unquote Splicing foi criado exatamente para resolver este tipo de situação. A diferença principal é que diferentemente do unquote ele permite que múltiplos forms sejam inseridos no lugar de um único unquote splicing:
Devemos usá-lo para resolver o problema da macro unless
:
Ao invocá-la não receberemos mais a exceção NullPointerException
:
Comentários: