Unquote результат функции, определенной макросом - PullRequest
0 голосов
/ 19 октября 2018

У меня есть следующее определение моего макроса

defmacro defverified(sign, body) do 
  {name, _, [param]} = sign
  quote do
    def unquote(name)(unquote(param)) do  
      unquote(param) = verify! param
      unquote(body)
    end
  end
end

Были verify!/1 возвращает его параметры, если он проверен как правильный параметр

И моя функция определяется следующим образом

defverified toto(p) do 
  IO.inspect p 
end 

И проверка содержимого p верна, но возвращение функции является формой моей переменной в кавычках.

iex(3)> res = Toto.toto(1)
1
[do: 1]
iex(4)> res
[do: 1]

Можно ли иметь форму без кавычек для возврата моей функции или я должен отменить кавычки вручную?
Я ожидаю следующий вывод моей функции

iex(3)> res = Toto.toto(1)
1
1
iex(4)> res
1

1 Ответ

0 голосов
/ 19 октября 2018

Это происходит потому, что конструкция do ... end является своеобразным кусочком синтаксического сахара.Например, это:

def toto(p) do 
  IO.inspect p 
end 

эквивалентно:

def toto(p), do: IO.inspect p 

, которое, поскольку ключевые слова в конце аргумента передаются в виде списка ключевых слов, эквивалентно:

def(toto(p), [do: IO.inspect(p)])

Поскольку ваш макрос defverified ожидает только блок do и никаких других параметров ключевого слова, мы можем явно сопоставить фактическое тело:

defmacro defverified(sign, [do: body]) do 
...

Перед этим последнийФорма в функции toto буквально будет иметь вид:

[do: IO.inspect param]

, который будет вызывать IO.inspect, как ожидается, но затем будет возвращать список ключевых слов вместо простого значения.

...