This is probably colored from my own experience of going from Python (mainly) to Elixir (mainly). As a toy example, imagine having to remove all the negative numbers from a list in the middle of a function.
Most python programmers would reach for a list comprehension after learning about list comprehensions (which is great because they are more FP)
my_list = [number for number in my_list if number >= 0]
So you pick up Elixir and you are trying to do the equivalent thing after reading through the docs my_list = for number <- my_list, number >= 0, do: number
And that works fine, it's my_list is exactly what you expect, no negative numbers.Let's try the same thing in Erlang
MyList = [X || X <- MyList, X >= 0].
** exception error: no match of right hand side value
As a new user coming to the language, trying to do something so simple and getting a somewhat opaque error message is a significant degree of friction.I have found that when I want the old value of a variable to no longer be available rebinding the name is a great way to ensure that. If in the future I decide that I need the old value later on in the function I can always just change the bind to some other name easily enough, but it prevents me from using state when I meant to use updated_state.
Not to say one way is better than the other, I just found this use of rebinding to work well for me by making it "impossible" to use the old / stale / out-of-date value.
def foo(bar) do
bar = decorate(bar)
{:ok, bar}
end
I like that better than calling it something like `new_bar`. I kind of wish there was prime syntax along the lines of `bar' = decorate(bar)` but I can deal with re-binding when only used like this (and really, the stakes are low). More complex cases can generally always be handled with piping. def foo(bar!) do
bar! = decorate(bar!)
bar! = some_more(bar!)
{:ok, bar!}
end def foo(bar) do
bar =
bar
|> decorate()
|> some_more()
{:ok, bar}
end bar
|> decorate()
|> some_more()
|> case do
result ->
{:ok, result}
endI 100% guarantee you don't miss "immutable variables" in your REPL.
Pid = module:start_link(...).
oh crap. start_link/n returns {:ok, _}, not naked pid. {ok, PidForRealThisTime} = Pid.