程式錯誤型別及其處理

老司機的詩和遠方發表於2020-04-06

程式在設計除錯甚至執行都難免出現錯誤,我們要做的是檢測錯誤。

程式庫錯誤

指的是程式庫實現錯誤,當然,程式庫的提供者在程式庫釋出之前,肯定想盡可能多地檢測和糾正錯誤,但是任何比較大的程式庫在釋出的時候,都是肯定會包含錯誤的。

使用者錯誤

主要是使用者操作不當,指如何使用程式庫方面的錯誤

系統錯誤

指使用者程式和該程式所執行的系統之間發生互動時所引發的錯誤。這種錯誤部分是系統的責任,部分是使用者的責任。

錯誤檢測

一般會額外的注入檢測程式碼,使得程式的穩定性得到提高,我們稱為不變性檢測,例如
char* p=某陣列;
int i;
//…….經過某些操作
if(i<0 || i >=strlen(p))
{
//不變性不滿足條件,失敗!
//執行錯誤異常處理方案
}
char c = p[i];
為了檢測錯誤,會額外的增加測試程式碼,時間複雜度從原來的常數級上升為現在的與陣列長度線性相關,也就是說,錯誤檢測通常和執行時間相互制約。

函式前提條件檢測
可以簡潔的說就是對函式的傳入引數的有效性安全性檢測!這一點對於函式設計很重要,因為要是傳入不合理的引數,從源頭制止給程式就會造成天大的錯誤。
表示不變性
指的是這個類的特性對於這個類的任何合法和或者合理的物件,這個特性總是能成立。

資源限制錯誤

1、堆疊溢位
注意是否有遞迴或者死迴圈引起的記憶體分配不足
2、用完空閒儲存空間
健壯的解決方案:
(1)嘗試分配更小的空間,不斷的減半申請空間,直到申請成功
(2)刪除儲存區的某些東西,然後繼續嘗試分配
3、檔案系統限制
使用者機器有個檔案系統,而且檔案系統已經用完了所有的空間,那麼任何希望增加檔案的操作都將失敗。

錯誤處理

程式庫應該具有幾種不同變數:
開發變數:用於開發和除錯程式庫本身;
除錯變數:用於開發和除錯使用者程式碼;
優化變數:用於獲得高效的執行效率。
(1)當檢測到錯誤的時候,程式可以根據檢測到的錯誤型別進行糾正錯誤。
(2)程式退出或者中止,雖然是最安全的做法,但是很多使用者無法接受這種做法,因此C++的很多程式庫永遠不會退出或者中止程式
(3)丟擲異常,優雅的處理方式。丟擲異常也存在幾點不足之處:並不是所有的C++編譯器都支援如上面程式碼的異常處理機制,任何丟擲異常的程式庫將不再具有系統移植性,某些系統根本不存在支援異常處理的C++實現。而且很多編譯器支援異常處理就會產生很多又大又慢的程式碼(異常處理需要額外的開銷)
(4)異常處理被新增到C++之前,一個處理錯誤普遍的方法就是返回錯誤值。但也存在不足,不是所有函式都可以很容易的返回bool標記,第二個缺點就是使用者可能未能檢查這些錯誤值,程式開發者很容易忘記錯誤的檢測。
(5)把一些無效資料解釋為有效資料

異常安全性

C++異常處理的同時,可重用程式碼的編寫者必須確定他們的程式碼是異常安全的,即使丟擲異常的時候,他們的程式碼仍然可以正常執行,一旦異常丟擲,堆疊是一直展開的,直到找到了異常的處理語句。

相關文章