C接口與實現---C裏面的異常處理機制

咱們的程序爲何老是bug不斷?

咱們的程序一般會出現三個錯誤: 用戶輸入錯誤, 運行期錯誤以及異常。對於用戶輸入錯誤咱們會進行不少的合法性檢查,通常都是能夠避免的,對於運行期錯誤就比較難辦了,咱們是最但願把bug在前期的過程的發現,若是需求期的一個bug流入到生產環境中的話那麼損失就是沒法估量的,客戶可能會直接懷疑你家的設計能力。儘管咱們都在層層的把關,仍是有不少的bug會遺留到生產系統上去。java

對運行期錯誤咱們能作的是就是作儘可能多的測試(UT/FT/ST 等等),儘量的去測試各類user case。也作了不少的測試可是線上系統仍是有不少處理不完的bug,agile是否是正的適合大型軟件的開發,真的是否是每一個人都能成爲真正的全能手。這章主要是程序的異常處理和斷言。怎樣讓系統檢測到異常後進行合理的結束,並非直接的crash,這裏仍是有不少的學問, 不一樣與erlang中的 let it crash, C裏面提供了不少的異常處理機制,下面咱們就來看看C中有那些合理的處理機制。測試

第一個就是longjmp和setjmp, 一個結構化的異常處理,setjmp設置一個異常處理點,而後發生異常的時候longjmp到以前set的地方,下面是一個簡單的例子,咱們檢測除法異常若是除數爲0咱們則jmp到以前set的地方。設計

#include <setjmp.h>
#include <stdlib.h>
#include <stdio.h>

int div_by_zero_handled = 0;
jmp_buf Div_Failed;

int div(int n, int m) {
  if (m == 0) {
    if (div_by_zero_handled) {
      longjmp(Div_Failed, 1);
    }
  }
  return n / m;
}

int main() {
  div_by_zero_handled = 1;
  if (setjmp(Div_Failed)) {
    printf("can't div by zero \n");
    exit(EXIT_FAILURE);
  }
  
  int n = div(2, 0);
  printf("----->%d\n", n);

  return 0;
}

這裏若是在div裏面咱們檢測到除數是0, 那麼longjump到以前set的地方, 程序的輸出以下:code

can't div by zero

下面就來看看在C語言裏面這樣經過longjmp和setjmp和宏實現一個相似C++ java中 try catch的功能。但這裏須要強調一點的是異常處理要儘可能的少用,正如書中所講的通常只在大型應用程序中少許的使用,若是異常愈來愈多,這一般說明程序有更嚴重設計問題。開發

C++/java中的try catch 的語法是這樣的:it

try 
    S
catch (e1)
    S1
catch (e2)
    S2
catch (en)
    Sn
Else
    So

在e1, e2, en的地方咱們經過setjmp建立了異常處理程序,若是S沒有觸發異常,將跳過程序程序,若是在S執行過程當中產生了異常e,而且e是在e1...en之間的一個,那麼S的執行被中斷,控制當即轉給相對應的Except從句總的語句。io

最後仍是要切記,在代碼中異常處理要儘可能少用。軟件

-END-erlang

相關文章
相關標籤/搜索