模式匹配用於自檢斷言代碼,而不僅僅是爲了快速獲取值。您的代碼將檢查映射中是否包含所有指定的鍵。如果你不需要這樣的檢查,那麼不要使用模式匹配。例如,我們首先將結果分配給一個變量(實際上它並不隨Elixir變化)。
groups = Enum.group_by(my_list, fn x -> x.param end)
然後讓deсide我們想要與此有關。我們想要處理羣組嗎?讓我們這樣做:
Enum.map(groups, fn({name, list}) -> process_group(name, list) end)
我們是否需要處理缺失的組?沒問題:
missing_groups = Enum.filter(["a", "b", "c"], &(!Map.has_key?(groups, &1)))
Enum.map(missing_groups, fn(name) -> process_missing_group(name) end)
想按鍵過濾嗎?這也不是問題:
# First variant:
filtered_groups = Enum.into(Enum.filter(groups, fn({k, v}) -> k in ["a", "b", "c"] end), %{})
# Second variant:
filtered_groups = Map.drop(groups, ["d", "e", "f", "g", "h"])
你真的想添加丟失的鍵嗎?好吧,如果這樣的話,讓我們做到這一點:是不是真的需要任何這個動作的
all_groups = Enum.into(["a", "b", "c"], %{}, &({&1, Map.get(groups, &1)}))
process_all_groups(all_groups)
正如你所看到的,模式的地圖匹配。實際上,你根本不需要變量,它們只是爲了可讀性。
現在你可以說「好吧,好吧,但我想爲不同的團體做不同的動作」。如果需要,這也是您可以使用模式匹配功能的地方。
def process_group(name, nil), do: action_empty(name)
def process_group("a", list), do: action_a(list)
def process_group("b", list), do: action_b(list)
def process_group(name, [x]), do: single_lement_action(name, x)
def process_group(name, list), do: another_action(name, list)
這看起來像你需要什麼?
模式匹配_will_失敗的關鍵。您可以將'%{「a」=> nil,「b」=> nil,「c」=> nil}'與Enum.group_by的結果合併,但這可能比您提到的替代方案更糟。你也可以創建一個類似於'Map.take'的函數,它返回給定鍵的值,如果鍵不存在則返回'nil',並使用它:'[a,b,c] = my_take(Enum。 group_by(...),[「a」,「b」,「c」])''。 – Dogbert
你所要求的東西是不被支持的,但是如果你稍微擴展你的問題(你想要怎麼處理這些數據?你爲什麼要返回'nil'?輸入列表是什麼樣的? )你可以得到一些更廣泛的建議。 –