Struct 长生不老药结构真的是不可变的吗?
我目前正在学习Elixir,我正在阅读《Elixir、OTP和Phoenix的功能性Web开发》,imo是一本很棒的书。 在“状态机”一章中,我提出了以下代码:Struct 长生不老药结构真的是不可变的吗?,struct,erlang,elixir,elixir-mix,elixir-iex,Struct,Erlang,Elixir,Elixir Mix,Elixir Iex,我目前正在学习Elixir,我正在阅读《Elixir、OTP和Phoenix的功能性Web开发》,imo是一本很棒的书。 在“状态机”一章中,我提出了以下代码: defmodule IslandsEngine.Rules do alias __MODULE__ defstruct state: :initialized def new(), do: %Rules{} def check(%Rules{state: :initialized} = rules, :add_pl
defmodule IslandsEngine.Rules do
alias __MODULE__
defstruct state: :initialized
def new(), do: %Rules{}
def check(%Rules{state: :initialized} = rules, :add_player), do:
{:ok, %Rules{rules | state: :players_set}}
def check(_state, _action), do: :error
end
上面的代码应该作为一个功能齐全的状态机工作。
我将在上面粘贴几个iex命令:
iex(1)> alias IslandsEngine.Rules
IslandsEngine.Rules
iex(2)> rules = Rules.new()
%IslandsEngine.Rules{state: :initialized}
iex(3)> {:ok, rules} = Rules.check(rules, :add_player)
{:ok, %IslandsEngine.Rules{state: :players_set}}
iex(4)> rules.state
:players_set
如您所见,状态结构已从:initialized
更改为:add_player
。太好了
我的问题是:state:
struct真的是不可变的吗?我的意思是,方法check/1
返回一个带有state::players\u set
语句的结构副本,该语句遵循正确的函数模式。。。但是它如何在不直接修改的情况下“覆盖”当前状态呢
非常感谢 Elixir数据结构确实是不可变的。但实际情况是,函数调用返回一个全新的值(这与原始值不同,具体取决于调用的函数) 至于“更改变量值”,在
Elixir
中(在原始Erlang
语言上)。变量的值实际上没有改变,只是重新绑定到新的变量。旧的垃圾由Erlang VM自动垃圾收集。
在你的例子中:
#返回一个全新的`%Rules{}`结构并重新绑定
#新术语的“rules”变量
{:好的,规则}=规则。检查(规则:添加球员)
刚刚意识到,有一个现有的问题和答案更详细地涵盖了这一点:另一个有趣的Q/A可能会澄清更多事情: