在网络(http,ftp等)中使用了术语协议,我对它在Elixir中的用法感到困惑。对于例如有对Enum模块和Enumerable Protocol的引用。 Elixir文档说Protocols are a mechanism to achieve polymorphism in Elixir
。
Aren他们只是一个带有一组方法/功能的模块?有什么区别吗?
答案 0 :(得分:4)
将协议视为Python中Java /抽象类中的接口(实际上,java接口,特别是python抽象类更多地是@behaviour
,但无论如何。)
defprotocol Sound do
def make_sound(data)
end
defmodule Dog do
defstruct name: "Donny"
end
defimpl Sound, for: Dog do
def make_sound(data) do
"#{data.name} barks “woof”"
end
end
defmodule Cat do
defstruct name: "Hilly"
end
defimpl Sound, for: Cat do
def make_sound(data) do
"#{data.name} murrs “meow”"
end
end
并在代码中:
%Dog{} |> Sound.make_sound
#⇒ "Donny barks “woof”"
或:
pet = .... # complicated code loading a struct
pet |> Sound.make_sound # here we don’t care what pet we have
此机制用于字符串插值:
"#{5}"
上述方法有效,因为Integer
具有String.Chars
的实现。实现只是调用
WHATEVER_IN_#{} |> String.Chars.to_string
获取二进制文件。例如。对于前面提到的Dog
模块,我们可以实现String.Chars
:
defimpl String.Chars, for: Dog do
def to_string(term) do
"#{term.name} barks “woof”"
end
end
现在可以插入狗:
"#{%Dog{}}"
#⇒ "Donny barks “woof”"