Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/elixir/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
为什么Elixir Plug使用宏将插件编译到AST中?_Elixir_Plug - Fatal编程技术网

为什么Elixir Plug使用宏将插件编译到AST中?

为什么Elixir Plug使用宏将插件编译到AST中?,elixir,plug,Elixir,Plug,如代码所示,插件定义将在宏扩展阶段编译为AST。但是为什么呢?为什么不保留plugs定义并使用Enum.reduce\u while或递归逐个调用plugs?我可以想到两个原因: 表演。考虑这两个代码段做相同的事情,但是使用编译函数调用来完成,而另一个使用枚举。Reals< /Cord>和应用< /C> >: defmodule A do def add1(x), do: x + 1 def sub1(x), do: x - 1 def compiled(x) do x

如代码所示,插件定义将在宏扩展阶段编译为AST。但是为什么呢?为什么不保留plugs定义并使用
Enum.reduce\u while
或递归逐个调用plugs?

我可以想到两个原因:

  • 表演。考虑这两个代码段做相同的事情,但是使用编译函数调用来完成,而另一个使用<代码>枚举。Reals< /Cord>和<代码>应用< /C> >:

    defmodule A do
      def add1(x), do: x + 1
      def sub1(x), do: x - 1
    
      def compiled(x) do
        x
        |> add1()
        |> sub1()
        |> add1()
        |> sub1()
        |> add1()
        |> sub1()
        |> add1()
        |> sub1()
      end
    
      @pipeline [
        {A, :add1},
        {A, :sub1},
        {A, :add1},
        {A, :sub1},
        {A, :add1},
        {A, :sub1},
        {A, :add1},
        {A, :sub1}
      ]
      def runtime(x) do
        Enum.reduce(@pipeline, x, fn {module, function}, acc ->
          apply(module, function, [acc])
        end)
      end
    end
    
    一个简单的基准测试表明,运行时实现的速度慢了5倍

    IO.inspect(
      :timer.tc(fn ->
        for _ <- 1..1_000_000, do: A.compiled(123)
        :ok
      end)
      |> elem(0)
    )
    
    IO.inspect(
      :timer.tc(fn ->
        for _ <- 1..1_000_000, do: A.runtime(123)
        :ok
      end)
      |> elem(0)
    )
    
  • 在编译时捕获bug。如果将一个模块传递给
    plug
    ,而该模块未实现
    call/2
    ,则在编译时会出现错误,而不是在运行时执行所有操作时通常会出现的运行时错误

  • 82800
    433198