Rud*_*koŭ 0 struct elixir pattern-matching
使用{:typed_struct, "~> 0.2.1"}库我有以下结构:
defmodule RequestParams do
use TypedStruct
typedstruct do
field :code, String.t()
field :name, String.t()
end
end
Run Code Online (Sandbox Code Playgroud)
我正在尝试将函数参数模式匹配到结构:
def do_handle(params %RequestParams{}, _context) do
# instead of
# def do_handle(%{ "code" => code, "name" => name}, _context) do
Run Code Online (Sandbox Code Playgroud)
但我得到例外:
Run Code Online (Sandbox Code Playgroud)cannot find or invoke local params/2 inside match. Only macros can be invoked in a match and they must be defined before their invocation.
怎么了?是否有可能将函数参数与结构相匹配?
在elixir中,函数调用中的括号不是强制性的(尽管是可取的)。也就是说,代码def foo(bar baz) do ...正在被解析和处理def foo(bar(baz)) do ...,因为解析器建议在函数调用中省略括号bar。您应该收到编译器发出的警告,准确说明这一点。应该阅读并消除警告。
正如@peaceful-james 所指出的,括号内的模式匹配就可以了。
\ndef do_handle(%RequestParams{} = params, _context) do\nRun Code Online (Sandbox Code Playgroud)\n你写了
\ndef do_handle(params %RequestParams{}, _context) do\n# instead of\n# def do_handle(%{ "code" => code, "name" => name}, _context) do\nRun Code Online (Sandbox Code Playgroud)\n即使语法正确,上面的代码也不等同于下面的代码。下面的代码将接受任何具有两个键"code"和 的映射"name",而上面的代码允许RequestParamsonly 的实例。还可以使下面的代码更加严格:
def do_handle(%RequestParams{code: code, name: name}, _) do\nRun Code Online (Sandbox Code Playgroud)\n但是Elixiratom中的结构除了作为键之外不能有任何东西。也就是说,如果您的初始代码被接受%{"code" => _}则无法在不修改调用代码的情况下将其转变为接受结构。
类型并不是丹药中的一等公民。我个人觉得合适。您应该从理解语言、OTP 原则、语言范式开始,然后才决定您是否想要和/或需要类型。
\n