How do you define constants in Elixir modules?
Solution 1:
You can prepend your variable name with @
:
defmodule MyModule do
@my_favorite_number 13
end
Here are the docs
Solution 2:
Another approach to defining constants is one that I took with the wxErlang header files. That is, you can simply define a single line function that returns the constant value for you. Like so:
def wxHORIZONTAL, do: 4
def wxVERTICAL, do: 8
def wxBOTH, do: (wxHORIZONTAL ||| wxVERTICAL)
and here's another example from the same source code:
# From "defs.h": wxDirection
def wxLEFT, do: 16
def wxRIGHT, do: 32
def wxUP, do: 64
def wxDOWN, do: 128
def wxTOP, do: wxUP
def wxBOTTOM, do: wxDOWN
def wxNORTH, do: wxUP
def wxSOUTH, do: wxDOWN
def wxWEST, do: wxLEFT
def wxEAST, do: wxRIGHT
def wxALL, do: (wxUP ||| wxDOWN ||| wxRIGHT ||| wxLEFT)
As you can see it makes it a little easier to define a constant in terms of another constant. And when I want those constants in a different module all I need to do is to require WxConstants
at the top of the module. This makes it much easier to define a constant in one place and use it in several others--helps a lot with DRY.
By the way, you can see the repo here if you're curious.
As I say, I add this answer mostly for sake of completeness.
Solution 3:
Looking around github I see this being used which appeals to me. Allows the constant to be accessed from other modules.
ModuleA
@my_constant 23
defmacro my_constant, do: @my_constant
ModuleB
Require ModuleA
@my_constant ModuleA.my_constant
Yet again simple and facinating elixir solution
Solution 4:
Maybe you define a constants module file and in it you can define macros for this like so
defmodule MyApp.Constants do
defmacro const_a do
quote do: "A"
end
end
You use it by importing it into any other module
defmodule MyApp.ModuleA do
import MyApp.Constants
def get_const_a do
const_a()
end
end
The benefit is also that you don't incur any runtime cost as well as the advantage of using it in case matches
case something do
const_a() -> do_something
_ -> do_something_else
end
Solution 5:
Elixir modules can have associated metadata. Each item in the metadata is called an attribute and is accessed by its name. You define it inside a module using @name value
. And is accessed as @name
defmodule Example
@site 'StackOverflow' #defining attribute
def get_site do
@site #access attribute
end
end
Remeber this works only on top level of a module and you cannot set a module attribute inside a function definition.