一般為了收集PHP的異常資訊做後續處理都會去設定一個exception的handler或是去繼承基底類別去寫exception的子類,我這裡用的是註冊了exception的handler。其中遇到了幾個不太懂的問題
1:拋出異常後,程式會終止,但是隱約記得以前哪裡看到過在某些特定情況下拋出異常後程序不會終止, 這種特定情況給忘記了,請大神在給科普一下。
2:如果註冊了exception的handler後,程式碼段去try這個拋出的異常,註冊的函數不會被執行,我不太記得這種情況是為什麼了,請大神再給科普一下。
3:關於異常的設計,為了方便收集一些日誌,一般都是怎麼去收集異常的日誌的,我是註冊了exception的handler,然後用這個函數去做整理和收集,但是try了以後,這個函數不被執行,所以不知道該怎麼去做這塊收集日誌的設計。 請大神給科普一下。
一般為了收集PHP的異常資訊做後續處理都會去設定一個exception的handler或是去繼承基類去寫exception的子類,我這裡用的是註冊了exception的handler。其中遇到了幾個不太懂的問題
1:拋出異常後,程式會終止,但是隱約記得以前哪裡看到過在某些特定情況下拋出異常後程序不會終止, 這種特定情況給忘記了,請大神在給科普一下。
2:如果註冊了exception的handler後,程式碼段去try這個拋出的異常,註冊的函數不會被執行,我不太記得這種情況是為什麼了,請大神再給科普一下。
3:關於異常的設計,為了方便收集一些日誌,一般都是怎麼去收集異常的日誌的,我是註冊了exception的handler,然後用這個函數去做整理和收集,但是try了以後,這個函數不被執行,所以不知道該怎麼去做這塊收集日誌的設計。 請大神給科普一下。
thinkphp的E方法,就是exception,這個主要是為了直接拋錯、終止。
我就知道try的用法,捕抓到異常,把異常之後要乾的活寫裡面就好了。
<code><?php try { $mgr = new CommandManager(); $cmd = $mgr->getCommandObject("realcommand"); $cmd->execute(); } catch (Exception $e) { print $e->getMessage(); exit(); } ?></code>
1、我目前知道的就是在try catch捕獲到異常,那麼程序就可以不終止
2、手冊中有對於set_exception_handler 的說明
設置默認的異常處理程序,用於沒有用try/catch 塊來捕獲的異常。 在 exception_handler 呼叫後異常會中止。
3、既然catch捕獲了異常,那麼exception_handler自然沒辦法在對應的程式碼段收集到異常。
function _exception_handler($exception)
<code>{ $_error =& load_class('Exceptions', 'core'); $_error->log_exception('error', 'Exception: '.$exception->getMessage(), $exception->getFile(), $exception->getLine()); // Should we display the error? if (str_ireplace(array('off', 'none', 'no', 'false', 'null'), '', ini_get('display_errors'))) { $_error->show_exception($exception); } exit(1); // EXIT_ERROR } </code>
上面是CI框架中自帶的異常自訂函數,所以日誌無非就是收集getMessage以及錯誤發生的程式碼檔案和行號。舉例CI,還能捕捉程式碼發生時的controller和action
異常(Exception)是一種更完善的錯誤處理機制,相較於錯誤(Error),異常有更完善的棧式處理方式。
這也決定了,處理異常後,程式時不會回到原來的位置繼續執行(這點對於錯誤來說是可以的)。
為什麼不能繼續執行,這是異常和錯誤的處理機制不相同所造成的:
錯誤處理,是在出現錯誤的位置中斷,跳到錯誤處理函數,處理完成後再跳回中斷出,所以能夠繼續執行。
異常處理,是向上退棧,尋找能夠捕捉異常的程式段,來處理異常。因為棧已經清理,所以已經不能回歸原來的執行位置。
異常的handler函數,是PHP為了相容函數式程式設計而建立的函數。但這其實並不符合標準的異常處理方式。異常處理,最好是使用try {} catch {}來實作。
至於你說的想要異常能夠突破內層的catch,被外層的catch捕捉到,你可以在內層的catch中,再使用throw $e拋出即可。