Elixir 錯誤

2023-12-16 20:47 更新

錯誤(或 異常 )用于代碼中發(fā)生異常時.當試圖將一個數(shù)字與原子相加,就可得到一個錯誤的例子:

iex> :foo + 1
** (ArithmeticError) bad argument in arithmetic expression
     :erlang.+(:foo, 1)

一個運行時錯誤可有?raise/1?引發(fā):

iex> raise "oops"
** (RuntimeError) oops

其它錯誤可以由?raise/2?引發(fā),通過傳送錯誤名稱和一個關鍵詞列表作為參數(shù):

iex> raise ArgumentError, message: "invalid argument foo"
** (ArgumentError) invalid argument foo

你也可以通過在一個模塊中使用?defexception?結(jié)構(gòu)來定義你自己的錯誤;這時你創(chuàng)造了一個與模塊同名的錯誤.最常用的場景是定義一個帶信息場的異常:

iex> defmodule MyError do
iex>   defexception message: "default message"
iex> end
iex> raise MyError
** (MyError) default message
iex> raise MyError, message: "custom message"
** (MyError) custom message

錯誤可以被解救,通過try/rescue結(jié)構(gòu):

iex> try do
...>   raise "oops"
...> rescue
...>   e in RuntimeError -> e
...> end
%RuntimeError{message: "oops"}

上述例子將運行時錯誤解救,并返回錯誤本身,然后將其打印到?iex?中.

如果錯誤對你毫無用處,你可以不顯示它:

iex> try do
...>   raise "oops"
...> rescue
...>   RuntimeError -> "Error!"
...> end
"Error!"

實際中,Elixir開發(fā)者很少用到try/rescue結(jié)構(gòu).例如,當文件無法被打開時,許多語言會強制你解救這個錯誤.作為替代,Elixir中提供了File.read/1函數(shù),其會返回一個包含文件是否被成功打開的信息的元組.

iex> File.read "hello"
{:error, :enoent}
iex> File.write "hello", "world"
:ok
iex> File.read "hello"
{:ok, "world"}

這里沒有try/rescue.如果你想要處理打開文件時的不同輸出,你可以簡單地使用case來進行模式匹配:

iex> case File.read "hello" do
...>   {:ok, body}      -> IO.puts "Success: #{body}"
...>   {:error, reason} -> IO.puts "Error: #{reason}"
...> end

最終,打開文件時發(fā)生的錯誤是否為異常將由你的應用來決定.這就是Elixir為何不給File.read/1和其它許多函數(shù)強加異常.而是留給開發(fā)者來選擇最好的處理方式.

當你確信一個文件存在(缺失文件確實是錯誤的),你可以簡單地使用File.read!/1:

iex> File.read! "unknown"
** (File.Error) could not read file unknown: no such file or directory
    (elixir) lib/file.ex:305: File.read!/1

標準庫中的許多函數(shù)遵循對應的異常引發(fā)模式,而非返回匹配元組.函數(shù)foo會返回{:ok, result}{:error, reason}元組,而另一個函數(shù)(foo!,同名但帶有!)雖然接受與foo同樣的參數(shù),但遇到錯誤時會拋出異常.如果一切正常,foo!會返回(沒有被元組包裹的)結(jié)果.File模塊就是很好的例子.

在Elixir中,我們避免使用try/rescue,因為我們不在控制流中使用錯誤.我們這樣解釋錯誤:它們是預留給意料外或異常的情形的.當你需要使用控制流結(jié)構(gòu)時,應該使用拋出.下面我們將講到.


以上內(nèi)容是否對您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號
微信公眾號

編程獅公眾號