I’d go for stdlib (EDIT: I left - on purpose
- a little error in the code as an exercise for the reader)
test "test" do
[
["a", "01.01.-02.01."],
["b", "04.03."],
["b", "06.03."],
["b", "08.03."],
["c", "09.09. - 01.10."]
]
|> Enum.group_by(fn [h | _] -> h end, fn [_ | t] -> t end)
|> Enum.map(fn {k, v} -> [k, join_last_special(v, ",", " and ")] end)
|> dbg
end
defp join_last_special([single], _, _) do
single
end
defp join_last_special(list, joiner, last_joiner) do
head_slice = Enum.slice(list, 0..-2)
last = List.last(list)
head_joined = Enum.join(head_slice, joiner)
Enum.join([head_joined, last], last_joiner)
end
so we have no recursion (visible) and we can follow the code easily.
[
["a", "01.01.-02.01."],
["b", "04.03."],
["b", "06.03."],
["b", "08.03."],
["c", "09.09. - 01.10."]
] #=> [
["a", "01.01.-02.01."],
["b", "04.03."],
["b", "06.03."],
["b", "08.03."],
["c", "09.09. - 01.10."]
]
|> Enum.group_by(fn [h | _] -> h end, fn [_ | t] -> t end) #=> %{
"a" => [["01.01.-02.01."]],
"b" => [["04.03."], ["06.03."], ["08.03."]],
"c" => [["09.09. - 01.10."]]
}
|> Enum.map(fn {k, v} -> [k, join_last_special(v, ",", " and ")] end) #=> [
["a", ["01.01.-02.01."]],
["b", "04.03.,06.03. and 08.03."],
["c", ["09.09. - 01.10."]]
]
I always try solutions in this order:
stdlib > handmade*
comprehension** (if applicable) > map > reduce > recursion
*) not true if you are learning. Implementing Enum
functions by hand is a good (but hard) exercise.
**) with the arrival of dbg
map became more sexy.