Lua - 錯誤處理



錯誤處理的必要性

錯誤處理非常重要,因為現實世界的操作通常需要使用複雜的操作,包括檔案操作、資料庫事務和 Web 服務呼叫。

在任何程式設計中,都需要進行錯誤處理。錯誤可以分為兩種型別:

  • 語法錯誤

  • 執行時錯誤

語法錯誤

語法錯誤是由於不正確地使用各種程式元件(如運算子和表示式)造成的。下面顯示了一個簡單的語法錯誤示例。

a == 2

如你所知,“等於”和“等於等於”之間是有區別的。使用一個代替另一個會導致錯誤。“等於”表示賦值,“等於等於”表示比較。類似地,表示式和函式有其預定義的實現方式。

另一個語法錯誤示例如下:

main.lua

for a= 1,10
   print(a)
end

輸出

執行上述程式時,我們將得到以下輸出:

lua: main.lua:2: 'do' expected near 'print'

語法錯誤比執行時錯誤更容易處理,因為 Lua 直譯器比執行時錯誤更清晰地定位錯誤。從上面的錯誤中,我們可以很容易地知道,根據 Lua 的結構,需要在 print 語句之前新增一個 do 語句。

執行時錯誤

對於執行時錯誤,程式能夠成功執行,但由於輸入錯誤或函式處理不當,可能會導致執行時錯誤。下面顯示了一個簡單的執行時錯誤示例。

main.lua

function add(a,b)
   return a+b
end

add(10)

輸出

構建程式時,它將成功構建並執行。執行後,會顯示執行時錯誤。

lua: main.lua:2: attempt to perform arithmetic on local 'b' (a nil value)
stack traceback:
	main.lua:2: in function 'add'
	main.lua:5: in main chunk
	[C]: ?

這是一個執行時錯誤,這是由於沒有傳遞兩個變數造成的。預期引數 b 為空,因此會產生錯誤。

assert 和 error 函式

為了處理錯誤,我們經常使用兩個函式:asserterror。下面顯示了一個簡單的示例。

local function add(a,b)
   assert(type(a) == "number", "a is not a number")
   assert(type(b) == "number", "b is not a number")
   return a+b
end

add(10)

輸出

執行上述程式時,我們將得到以下錯誤輸出。

lua: main.lua:3: b is not a number
stack traceback:
	[C]: in function 'assert'
	main.lua:3: in function 'add'
	main.lua:6: in main chunk
	[C]: ?

error (message [, level]) 函式終止最後一次呼叫的受保護函式,並返回 message 作為錯誤訊息。此函式 error 永遠不會返回。通常,error 會在訊息開頭新增一些關於錯誤位置的資訊。level 引數指定如何獲取錯誤位置。使用 level 1(預設值),錯誤位置是在呼叫 error 函式的地方。level 2 將錯誤指向呼叫 error 函式的函式的呼叫位置;以此類推。傳遞 level 0 將避免在訊息中新增錯誤位置資訊。

pcall 和 xpcall

在 Lua 程式設計中,為了避免丟擲這些錯誤並處理錯誤,我們需要使用 pcall 或 xpcall 函式。

pcall (f, arg1, ...) 函式以保護模式呼叫請求的函式。如果函式 f 中發生某些錯誤,它不會丟擲錯誤。它只返回錯誤的狀態。下面顯示了一個使用 pcall 的簡單示例。

main.lua

function myfunction ()
   n = n/nil
end

if pcall(myfunction) then
   print("Success")
else
	print("Failure")
end

輸出

執行上述程式時,我們將得到以下輸出。

Failure

xpcall (f, err) 函式呼叫請求的函式並設定錯誤處理程式。f 內部的任何錯誤都不會傳播;相反,xpcall 會捕獲錯誤,使用原始錯誤物件呼叫 err 函式,並返回狀態程式碼。

下面顯示了一個 xpcall 的簡單示例。

main.lua

function myfunction ()
   n = n/nil
end

function myerrorhandler( err )
   print( "ERROR:", err )
end

status = xpcall( myfunction, myerrorhandler )
print( status)

輸出

執行上述程式時,我們將得到以下輸出。

ERROR:	main.lua:2: attempt to perform arithmetic on global 'n' (a nil value)
false

作為程式設計師,最重要的是確保你在編寫的程式中處理好錯誤。使用錯誤處理可以確保處理超出邊界條件的意外情況,而不會影響程式的使用者。

廣告
© . All rights reserved.