|
在下面的代碼裡,在調用一個已經被刪除了的對象(b:TBitmap)事件後,一個Access violation出現了: var b:TBitmap; begin b:=TBitmap.Create; try //對b對象進行一些操作 finally b.free; end; ... //由於b已經被釋放,一個Access violation錯誤將會出現 b.Canvas.TextOut(0,0,’這是一個 Access Violation’); end; 2. 不存在的API參數 如果你試圖給Win API函數傳遞一個不存在的參數將會出現一個Access violation錯誤。解決此類Access violation錯誤的最好方法是查閱Win API協助,看看這個API函數調用的參數資訊以及參數類型。例如,總是保證不給一個緩衝參數傳遞一個無效指標 3. 讓Delphi釋放 當一個對象擁有另一個對象時,讓它給你做刪除工作。因為預設情況下,所有的表單(自動建立的)都屬於Application對象。當一個應用程式結束時,它釋放了Application對象,也就釋放了所有表單。例如,如果你在程式開始時自動建立了兩個表單(Form1/Unit1和Form2/Unit2),下面的代碼就會導致Access violation錯誤的出現: unit Unit1; ... uses unit2; ... procedure TForm1.Call_Form2 begin Form2.ShowModal; Form2.Free; //Access violation錯誤將會出現 Form2.ShowModal; end; 4. 殺死異常 永遠不要破壞臨時異常對象(E),處理一個異常會自動釋放異常對象。如果你自己手動釋放了異常對象,程式會試圖再次釋放它,那麼就會出現Access violation錯誤: Zero:=0; try dummy:= 10 / Zero; except on E: EZeroDivide do MessageDlg(’不能用0做除數!’,mtError, [mbOK], 0); E.free. ////Access violation錯誤將會出現 end; 5. 檢索一個Null 字元串 一個Null 字元串是沒有任何資料的。就是說,檢索一個Null 字元串相當於訪問一個不存在的對象,這將導致Access violation錯誤: var s: string; begin s:=’’; s[1]:=’a’; //Access violation錯誤將會出現 end; 6. 直接引用指標 你必須間接引用指標,否則你會改變指標地址並可能會破壞其他儲存單元 : procedure TForm1.Button1Click(Sender: TObject); var p1 : pointer; p2 : pointer; begin GetMem(p1, 128); GetMem(p2, 128); //下一行導致Access violation錯誤 Move(p1, p2, 128); //下一行方法正確 Move(p1^, p2^, 128); FreeMem(p1, 128); [Page] FreeMem(p2, 128); end; 這些就是我對運行期Access Violation錯誤的全部建議,我希望你們也能對你們程式出現的Access Violation錯誤提出一些看法。 老貓點評:相信所有讀者都遇到過“Access violation” 的錯誤,如果不是自己的程式,我們有很多人就把責任都推在Bill Gates的頭上。如果你自己的程式出現了這個尷尬的錯誤,面對使用者的詢問,我們該如何解釋?本文就是最好的答案。 |