【发布时间】:2019-04-06 02:05:45
【问题描述】:
我目前正在学习 Elixir,正在阅读“使用 Elixir、OTP 和 Phoenix 进行功能性 Web 开发”,这是一本很棒的书。 在状态机章节工作,我想出了以下代码:
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: 结构真的不可变吗?我的意思是,check/1 方法返回带有 state: :players_set 语句的结构副本,该语句遵循正确的功能模式......但是它如何“覆盖”当前状态而不直接修改它?
非常感谢!
【问题讨论】:
-
刚刚意识到有一个现有问题的答案可以更详细地介绍这一点:Are Elixir variables really immutable?
-
另一个有趣的问答可能会澄清更多事情:Elixir: Rationale behind allowing rebinding of variables
标签: struct erlang elixir elixir-mix elixir-iex