Best way to access a value of a Nested Map with variables

Hello. I am having troubles accessing maps keys.
I have this map:

%{
      BRL => %{
        currency: "Brazilian Real",
        rate: %{
          AED: 0.699986,
        }
      }
    }

setted in a variable called currency

With this function, how can I access the value inside rate dynamically?
Ex: i’m calling currencyConverter({ "BRL", "AED" })

def currencyConverter({ from, to }) do
  currency[?]
end

Yes you can access using the get_in/2 method.

currency = %{
  BRL: %{
    currency: "Brazilian Real",
    rate: %{
      AED: 0.699986
    }
  }
}

defmodule CurrencyConverter do
  def convert(currency, { from, to }) do
    from = String.to_atom(from)
    to = String.to_atom(to)

    get_in(currency, [from, :rate, to])
  end
end

I converted the String to Atom because your map has atom keys, but your from and to are Strings.

1 Like

Cool!
Thank you very much brow!

1 Like

In addition to @thiagogsr answer another way to access the values in nested maps is to use square brackets currency["BRL"][:rate][:AED]

defmodule CurrencyConverter do

  def convert(currency, from, to) do
    to = String.to_atom(to)
    currency[from][:rate][to]
  end

end
iex(1)> currency = %{"BRL" => %{currency: "Brazilian Real", rate: %{AED: 0.699986}}}
%{"BRL" => %{currency: "Brazilian Real", rate: %{AED: 0.699986}}}
iex(2)> CurrencyConverter.convert(currency, "BRL", "AED")
0.699986

BRL is an alias, expanding to the atom Elixir.BRL, :AED is directly an atom, "BRL" and "AED" are strings.

Your input map does not contain any of the strings.

Please choose a single encoding for your currency symbols and stick to it through your entire application. Converting from string close to the edges of your application.

Once you have settled on a uniform keyencoding, the get_in approach already mentioned by other posters should just work.


0.699986 is a float, you shall not use it for currency. Not for encoding the currency amount, not for encoding any conversion rates.

3 Likes