Recently I found myself wanting to replace certain characters in a string with others (similar to "tr" shell command).
In my case I wanted to replace any of the characters in :;<=>?@[\]^_` with the corresponding character from ABCDEFGabcdef.
I'm not sure what the most idiomatic way to write this would be in Elixir but I used:
Enum.map_join(input, &my_replace/1)
defp my_replace(":"), do: "A"
defp my_replace(";"), do: "B"
defp my_replace("<"), do: "C"
defp my_replace("="), do: "D"
defp my_replace(">"), do: "E"
defp my_replace("?"), do: "F"
defp my_replace("@"), do: "G"
defp my_replace("["), do: "a"
defp my_replace("\\"), do: "b"
defp my_replace("]"), do: "c"
defp my_replace("^"), do: "d"
defp my_replace("_"), do: "e"
defp my_replace("`"), do: "f"
defp my_replace(char), do: char
This
works, is readable, but not concise. My proposal would thus be to open a discussion on the way to implement a
more concise way to do this, unless there is already a concise way to
do this that I'm not aware of and if people agree that it's worth implementing.
Here are some reference implementations in other languages, to open up ideas:
PHP:
strtr($input, ":;<=>?@[\]^_`", "ABCDEFGabcdef")
Ruby:
input.tr!(
':;<=>?@[\\]^_`',
'ABCDEFGabcdef')
Go has an implementation that is not concise but does allow multiple char/string translation:
r := strings.NewReplacer(
":", "A",
";", "B",
"<", "C",
// and so on...
)
r.Replace(input)
Python (3) requires creation of a "translation map" first:
table = str.maketrans(":;<=>?@[\]^_`", "ABCDEFGabcdef")
input.translate(table)
A lot of these implementations also allow other uses, besides simple character translations.