檢視原始碼 case、cond 和 if
在本章節中,我們將學習 case
、cond
和 if
控制流程結構。
case
case
允許我們將值與多個模式進行比較,直到找到一個匹配的模式
iex> case {1, 2, 3} do
...> {4, 5, 6} ->
...> "This clause won't match"
...> {1, x, 3} ->
...> "This clause will match and bind x to 2 in this clause"
...> _ ->
...> "This clause would match any value"
...> end
"This clause will match and bind x to 2 in this clause"
如果您想針對現有變數進行模式比對,則需要使用 ^
算子
iex> x = 1
1
iex> case 10 do
...> ^x -> "Won't match"
...> _ -> "Will match"
...> end
"Will match"
子句也允許透過防護裝置指定額外條件
iex> case {1, 2, 3} do
...> {1, x, 3} when x > 0 ->
...> "Will match"
...> _ ->
...> "Would match, if guard condition were not satisfied"
...> end
"Will match"
僅當 x
為正數時,上面的第一個子句才會匹配。
請記住,防護裝置中的錯誤不會外洩,只會使防護裝置失敗
iex> hd(1)
** (ArgumentError) argument error
iex> case 1 do
...> x when hd(x) -> "Won't match"
...> x -> "Got #{x}"
...> end
"Got 1"
如果沒有子句匹配,則會引發錯誤
iex> case :ok do
...> :error -> "Won't match"
...> end
** (CaseClauseError) no case clause matching: :ok
Kernel
模組的文件在側邊欄中列出所有可用的防護裝置。您也可以參閱完整的 模式和防護裝置 參考以取得深入的文件。
cond
當您需要針對不同的值進行比對時,case
會很有用。然而,在許多情況下,我們想要檢查不同的條件,並找到第一個不會評估為 nil
或 false
的條件。在這種情況下,可以使用 cond
iex> cond do
...> 2 + 2 == 5 ->
...> "This will not be true"
...> 2 * 2 == 3 ->
...> "Nor this"
...> 1 + 1 == 2 ->
...> "But this will"
...> end
"But this will"
在許多命令式語言中,這相當於 else if
子句,儘管在 Elixir 中使用頻率較低。
如果所有條件都傳回 nil
或 false
,則會引發錯誤 (CondClauseError
)。因此,可能需要新增一個最終條件,等於 true
,它將永遠匹配
iex> cond do
...> 2 + 2 == 5 ->
...> "This is never true"
...> 2 * 2 == 3 ->
...> "Nor this"
...> true ->
...> "This is always true (equivalent to else)"
...> end
"This is always true (equivalent to else)"
最後,請注意 cond
將除了 nil
和 false
之外的任何值都視為 true
iex> cond do
...> hd([1, 2, 3]) ->
...> "1 is considered as true"
...> end
"1 is considered as true"
if/unless
除了 case
和 cond
之外,Elixir 還提供了 if/2
和 unless/2
,當您需要只檢查一個條件時,它們會很有用
iex> if true do
...> "This works!"
...> end
"This works!"
iex> unless true do
...> "This will never be seen"
...> end
nil
如果提供給 if/2
的條件傳回 false
或 nil
,do
-end
之間提供的內文不會執行,而會傳回 nil
。使用 unless/2
時則相反。
它們也支援 else
區塊
iex> if nil do
...> "This won't be seen"
...> else
...> "This will"
...> end
"This will"
這也是討論 Elixir 中變數範圍的好時機。如果在 if
、case
和類似的建構中宣告或變更任何變數,宣告和變更只會在建構內可見。例如
iex> x = 1
1
iex> if true do
...> x = x + 1
...> end
2
iex> x
1
在這些情況中,如果你要變更值,你必須從 if
傳回值
iex> x = 1
1
iex> x = if true do
...> x + 1
...> else
...> x
...> end
2
if
和unless
是巨集關於
if/2
和unless/2
的一個有趣備註是,它們在語言中實作為巨集:它們並非如許多語言中的特殊語言建構。你可以查看文件和它們的來源以取得更多資訊。
我們已經結束 Elixir 中最基本的控制流程建構的介紹。現在讓我們來學習程式碼和資料在匿名函式中相遇的地方。