I often find myself writing 

def func(a,b):
  g = :digraph.new

  ...

  out = some_long_multiline_expression_using_g
  :digraph.delete g
  out
end

when working with graphs. The distance between `:digraph.new` and 
`:digraph.delete` makes it harder to remember to clean up the graph ets 
tables. The little dance at the end to return a value and also clean up the 
mutable state feels a bit awkward too. This problem is common when working 
with mutex, files and other things you need to remember to clean up. Golang 
has a great solution; the `defer` statement 
<https://golang.org/ref/spec#Defer_statements>.

def func(a,b):
  g = :digraph.new
  defer :digraph.delete g
  
  ...
  
  some_long_multiline_expression_using_g
end

This minimizes the distance between declaration and cleanup statement, 
makes it harder to forget it, and also cleans up the end of the function. 
If there isn't a `defer` just after some mutable state is created, you 
immediately know that you need to figure out where the mutable state is 
cleaned up. If there is a `defer` statement there, you can read the rest of 
the code without having to think about if every branch has the proper 
clean-up code in it.

Each `defer` statement pushes a function call onto a stack, with the 
variable bindings it had when the `defer` statement was reached. When the 
function returns, the function calls on the stack are executed one by one.

-- 
You received this message because you are subscribed to the Google Groups 
"elixir-lang-core" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To view this discussion on the web visit 
https://groups.google.com/d/msgid/elixir-lang-core/2c0d8195-ec44-4112-a0c1-2f5c5f3905b2%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to