目前正在尝试理解 Elixir 中的“^”运算符。 来自网站:
The pin operator ^ can be used when there is no interest in rebinding a variable but rather in matching against its value prior to the match:
来源 - http://elixir-lang.org/getting_started/4.html
考虑到这一点,您可以为符号附加一个新值,如下所示:
iex> x = 1 # Outputs "1"
iex> x = 2 # Outputs "2"
我还可以:
iex> x = x + 1 # Outputs "3"!
所以我的第一个问题是; Elixir 变量是可变的吗? 如果是这样的话,看起来确实如此......这在函数式编程语言中不应该是可能的吗?
现在我们来看看“^”运算符...
iex> x = 1 # Outputs "1"
iex> x = 2 # Outputs "2"
iex> x = 1 # Outputs "1"
iex> ^x = 2 # "MatchError"
iex> ^x = 1 # Outputs "1"
我认为“^”的作用是将“x”锁定到与其绑定(bind)的最后一个值。这就是全部内容了吗? 为什么不像 Erlang 本身一样确保所有“匹配”/赋值都是不可变的呢?
我刚刚习惯了......
最佳答案
Elixir 中的数据仍然是不可变的,但有一些简写,可以让您减少输入次数,或者不用担心找到新名称。在 Erlang 中,你经常会看到这样的代码:
SortedList = sort(List),
FilteredList = filter(SortedList),
List3 = do_something_with(FilteredList),
List4 = another_thing_with(List3)
在 Elixir 中,你可以这样写:
list = sort(list)
list = filter(list)
list = do_something_with(list)
list = another_thing_with(list)
这完全一样,但看起来更好一点。当然最好的解决方案是这样写:
list |> sort |> filter |> do_something |> another_thing_with
每次,您将新事物分配给 list
变量时,您都会获得新实例:
iex(1)> a = 1
1
iex(2)> b = [a, 2]
[1, 2]
iex(3)> a = 2
2
iex(4)> b
[1, 2] # first a did not change, it is immutable, currently a just points to something else
你只是说,你不再对旧的a
感兴趣并让它指向其他东西。如果您有 Erlang 背景,您可能知道 shell 中的 f
函数。
A = 1.
f(A).
A = 2.
在 Elixir 中,您不必编写 f
。它会自动为您完成。这意味着,每次模式匹配左侧有变量时,都会为其分配新值。
如果没有 ^
运算符,您将无法在模式匹配的左侧拥有变量,因为它将从右侧获取新值。 ^
表示不要为该变量分配新内容 - 将其视为文字值。
这就是 Elixir 的原因
x = 1
[1, x, 3] = [1, 2, 3]
在 Erlang 中相当于:
X = 1,
[1, CompletelyNewVariableName, 3] = [1, 2, 3]
和:
x = 1
[1, ^x, 3] = [1, 2, 3]
相当于:
x = 1
[1, 1, 3] = [1, 2, 3]
在 Erlang 中是:
X = 1,
[1, X, 3] = [1, 2, 3]
关于functional-programming - "pin"运算符的用途是什么?Elixir 变量是否可变?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27971357/