第13章程序調試與常見錯誤分析_第1頁
第13章程序調試與常見錯誤分析_第2頁
第13章程序調試與常見錯誤分析_第3頁
第13章程序調試與常見錯誤分析_第4頁
第13章程序調試與常見錯誤分析_第5頁
已閱讀5頁,還剩56頁未讀, 繼續(xù)免費閱讀

下載本文檔

版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領

文檔簡介

1、第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析13.1 程序調試程序調試13.2 常見錯誤分析常見錯誤分析第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析13.1 程序調試13.1.1 程序調試的步驟 所謂程序調試,是指對程序的查錯和排錯。調試程序一般應經過以下幾個步驟。1. 人工檢查,即靜態(tài)檢查 在寫好一個程序以后,不要匆匆忙忙上機,而應對紙面上的程序進行人工檢查。這一步是十分重要的,它能發(fā)現程序設計人員由于疏忽而造成的多處錯誤。而這一步驟往往容易被忽視。有的用戶總希望把一切推給計算機系統(tǒng)去做,但這樣就會多占用機

2、器時間。第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析而且,作為一個程序設計人員應當養(yǎng)成嚴謹科學的作風,每一步都要嚴格把關,不要把問題留給后面的工序。為了更有效地進行人工檢查,所編的程序應力求做到以下幾點: (1) 應當采用結構化程序方法編程,以增加可讀性。 (2) 盡可能多地加注釋,以幫助理解每段程序的作用。 (3) 在編寫復雜的程序時,不要將全部語句都寫在main函數中,而要多利用函數,用一個函數來實現一個單獨的功能。這樣既易于閱讀,也便于調試,各函數之間除用參數傳遞數據外,數據間應盡量少出現耦合關系,以便于分別檢查和處理。第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤

3、分析2. 上機調試,即動態(tài)檢查 在人工(靜態(tài))檢查無誤后,才可以上機調試。通過上機發(fā)現的錯誤稱之為動態(tài)檢查。在編譯時,系統(tǒng)會給出語法錯誤的信息(包括哪一行有錯以及錯誤類型),用戶可以根據提示的信息具體找出程序中出錯之處并進行修改。應當注意的是:有時提示的出錯行并不是真正出錯的行,如果在提示出錯的行上找不到錯誤的話,應當到上一行再找。另外,有時提示出錯的類型并非絕對準確,由于出錯的情況繁多而且各種錯誤互有關聯,因此要善于分析,找出真正的錯誤,而不要死抱住提示的出錯信息不放,鉆牛角尖。 第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析如果系統(tǒng)提示的出錯信息多,應當從上到下逐一改正。有時顯

4、示出一大片錯誤信息往往使人感到問題嚴重,無從下手。其實可能只有一兩個錯誤。例如,對所用的變量未定義,編譯時就會對所有含該變量的語句發(fā)出出錯信息。這時只要加上一個變量定義,那么所有錯誤就都消除了。3. 運行程序,試驗數據 在改正語法錯誤(包括“錯誤”error和“警告”warning)后,程序經過鏈接(link)就得到可執(zhí)行的目標程序。運行程序,輸入程序所需數據,就可得到運行結果。應當對運行結果作分析,看它是否符合要求。有的初學者看到輸出運行結果就認為沒問題了,不作認真分析,這是危險的。 第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析 有時,數據比較復雜,難以立即判斷結果是否正確???/p>

5、以事先考慮好一批“試驗數據”,輸入這些數據 , 可 以 判 斷 結 果 正 確 與 否 。 例 如 , 解 方 程ax2+bx+c=0,輸入a、b、c的值分別為1、-2、1時,根x的值是1。這是容易判斷的,若根不等于1,程序顯然有錯。但是,用“試驗數據”時,程序運行結果正確,還不能保證程序完全正確。因為有可能輸入另一組數據時運行結果不對。例如,用第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析 公式求根x的值,當a0和b2-4ac0時,能得出正確結果;當a=0或b2-4acb) ;printf(a is larger than bn) ; 本意為,當ab時輸出“a is larger

6、 than b”的信息。但由于在“if (ab)”后加了分號,因此if語句到分號結束。即當(ab)為真時,執(zhí)行一個空語句。本來想ab時不輸出上述信息,但現在printf函數語句并不從屬于if語句,而是與if語句平行的語句。不論ab還是ab,“a is larger than b”都被輸出出來。第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析又如:for(i = 0 ; i 10 ; i +) ;scanf ( %d , &x) ;printf( %dn , x*x) ;本意為先后輸入10個數,每輸入一個數后輸出它的平方值。由于在for ( )后加了一個分號,使循環(huán)體變成了空語

7、句,因此,只能輸入一個整數并輸出它的平方值。 第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(10) 輸入變量時忘記使用地址符。 例如:scanf(%d %d , a , b) ; 這是許多初學者剛學習C語言時一個常見的疏忽,或者說是習慣性的錯誤,因為在其他語言中在輸入時只需要寫出變量名即可,而C語言要求指示:“向哪個地址標識的單元送值”,應寫成scanf(%d %d , &a , &b) ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(11) 括弧不配對。 當一個語句中使用多層括弧時常出現括弧不配對的錯誤,純屬粗心所致。例如:while( c=get

8、char ( ) ! = # )putchar( c ) ; 少了一個右括弧。第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(12) switch語句的各分支中漏寫break語句。 例如:switch (score) case 5 : printf (Very good ! ) ; case 4 : printf (Good ! ) ; case 3 : printf (Pass ! ) ; case 2 : printf (Fail ! ) ; default : printf(data error ! ) ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析上述swit

9、ch語句的作用是希望根據score(成績)打印出評語。但當score的值為5時,輸出為:Very Good ! Good ! Pass ! Fail ! data error !原因是漏寫了break語句。case只起標號的作用,而不起判斷作用,因此在執(zhí)行完第一個printf函數語句后接著執(zhí)行第二、三、四、五個printf函數語句。應改為第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析switch(score) case 5 : printf (Very good ! ) ; break ; case 4 : printf (Good ! ) ; break ; case 3 : p

10、rintf (Pass ! ) ; break ; case 2 : printf (Fail ! ) ; break ; default : printf(data error ! ) ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(13) 引用數組元素時誤用了圓括弧。 例如:main( ) int i , a(10) ; for( i = 0 ; i10 ; i+) scanf ( %d , &a(i) ; C語言中對數組的定義或引用數組元素時必須用方括弧。第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析14) 對應該有花括弧的復合語句,忘記加花括弧。 例如

11、:sum=0 ;i= 1 ;while( i = 100 ) sum = sum + i ; i +;本意是實現1+2+100,即。但上面的語句只是重復了sum+i的操作,而且循環(huán)永不終止。因為i的值始終沒有改變。錯誤在于沒有寫成復合語句形式。因此while語句的范圍到其后第一個分號為止。語句“i +;”不屬于循環(huán)體范圍之內。應改為第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析while ( i = 100) sum=sum+i ; i+ ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(15) 在用標識符時,忘記了大寫字母和小寫字母的區(qū)別。 例如:main( ) in

12、t a , b , c ; a=2 ; b=3 ; C=A+B ; printf (%d + %d = %, A , B , C) ;編譯時出錯。編譯程序把a和A認作是兩個不同的變量名處理,同樣,b和B,c和C都分別代表兩個不同的變量。第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(16) 在定義數組時,將定義的“元素個數”誤認為是“可使用的最大下標值”。 例如:main( ) static int a 10 =1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 , 9 , 10 ; int i ; for( i=1 ; i y? x : y ) ;第第13章章 程序調試與

13、常見錯誤分析程序調試與常見錯誤分析這個程序乍看起來沒有什么問題,但在編譯時有出錯信息。原因是,max函數是實型的,而且在main函數之后才定義,也就是max函數的定義位置在main函數中的調用max函數之后。改錯的方法可以用下面兩種方法之一。 在main函數中增加一個對max函數的說明,即main( ) float max( ) ; /* 說明將要用到的max函數為實型 */ float x , y , z ; x = 3.5 ; y =-7.6 ; z =max( x , y ) ; printf(%fn , z) ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析 將max函數的

14、定義位置調到main函數之前。即float max (x , y )float x , y ; return ( z = x y? x : y ) ; main ( ) float x , y , z ; x = 3.5 ; y =-7.6 ; z =max ( x , y ) ; printf (%fn , z) ;這樣,編譯時不會出錯,程序運行結果是正確的。第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(23) 將函數的形參和函數中的局部變量一起定義。 例如:max (x , y)int x , y , z ; z = x y ? x : y ; return (z) ;形參應

15、該在函數體之前定義,而函數中用到的局部變量應在函數體中定義。應改為第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析max (x , y)int x , y ; int z ;z = x y ? x : y ; return (z) ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(24) 函數的實參和形參類型不一致。 例如:main( ) int a=3 ; b=4 ; c = fun (a , b) ; fun (x , y) float x , y; 實參a、b為整型,形參x、y為實型。a和b的值傳遞給x和y時,x和y的值并非3和4。C要求實參與形參的類型一致。 第第

16、13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(25) 沒有注意函數參數的求值順序。 例如:i = 3 ;printf (%d , %dn , i ,+ i , + i ) ;許多人認為輸出必然是 3 , 4 , 5實際不盡然。在許多系統(tǒng)中輸出是 5 , 5 , 4因為許多系統(tǒng)是采取自右至左的順序求函數參數值的。先求出最右面一個參數(+ + i)的值為4,再求出第2個參數(+ + i)的值為5,最后求出最左面的參數(i)的值為5。 第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析C標準沒有具體規(guī)定函數參數求值的順序是自左而右還是自右而左。但每個C編譯程序都有自己的順序,在有些

17、情況下,從左到右求解和從右到左求解的結果是相同的。例如:fun1 (a + b , b + c , c + a ) ; fun1是一個函數名,a + b、b + c、c + a是3個實參表達式。在一般情況下,自左至右地求這三個表達式的值和自右至左地求它們的值是一樣的,但在前面的例子中卻不相同。因此,建議最好不用會引起二義性的用法。如果在上例中,希望輸出“3 , 4 , 5”時,可以改用i = 3 ; j = i + 1 ; k = j + 1 ;printf (%d , %d , %dn , i , j , k) ; 第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(26) 混淆數組

18、名與指針變量的區(qū)別。 例如:main( ) int i , a 5 ; for ( i = 0 ; i 5 ; i +) scanf(%d , a +) ; 企圖通過a的改變使指針下移,每次指向欲輸入數據的數組元素。它的錯誤在于:不了解數組名代表數組首地址,它的值是不能改變的,用a + +是錯誤的,應當用指針變量來指向各數組元素。即第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析int i , a5 , * p ;p = a ;for (i = 0 ; i 5 ; i + +)scanf (%d , p + +) ;或者int a 5 , * p ;for ( p = a ; p a

19、 +5 ; p + +) scanf(%d , p) ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(27) 誤認為形參值的改變會影響實參的值。 例如:main( ) int a , b ; a=3 ; b=4 ; swap ( a , b ) ; printf (%d , %dn,a , b ) ;swap (x , y)int x , y ; int t ; t=x ; x=y ; y=t ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析原意是通過調用swap函數使a和b的值對換,然后在main函數中輸出已對換了值的a和b。但是這樣的程序是達不到目的的,因為x和y

20、值的變化是不傳送回實參a和b的,main函數中的a和b值并未改變。 如果想從函數得到一個以上的變化了的值,應該用指針變量。用指針變量作函數參數,使指針變量所指向的變量的值發(fā)生變化。此時變量的值改變了,主調函數中可以利用這些已改變的值。如:第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析main( ) int a , b , * P1 , * P2 ; a=3 ; b=4 ; p1=&a ; p2=&b ; swap ( p1 , p2 ) ; printf (%d , %dn ,a , b ) ; /* a和b的值已對換 */swap (pt1 , pt2)int *

21、pt1 , * pt2 ; int t ; t= * pt1 ; *pt1= * pt2 ; *pt2=t ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(28) 混淆結構體類型與結構體變量的區(qū)別,對一個結構體類型賦值。 例如:struct worker long int num ; char name20 ; char sex ; int age ; ;worker.num = 187045 ;strcpy( , Zhang Fan) ;worker.sex = M ;worker.age =18 ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分

22、析這是錯誤的,只能對變量賦值而不能對類型賦值。上面只定義了struct worker類型而未定義變量。應改為struct worker long int num ; char name20 ; char sex ; int age ; ;第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析struct worker worker _ 1 ;worker _ 1.num = 187045 ;strcpy (worker _ 1 .name , Zhang Fan) ;worker _ 1 .sex = M ;worker _ 1.age =18 ;今定義了結構體變量worker _ 1,并對其中的各成員賦值。第第13章章 程序調試與常見錯誤分析程序調試與常見錯誤分析(29) 使用文件時忘記打開,或打開方式與使用情況不匹配。 例如:if ( ( fp = fopen (test ,

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯系上傳者。文件的所有權益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網頁內容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
  • 4. 未經權益所有人同意不得將文件中的內容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網僅提供信息存儲空間,僅對用戶上傳內容的表現方式做保護處理,對用戶上傳分享的文檔內容本身不做任何修改或編輯,并不能對任何下載內容負責。
  • 6. 下載文件中如有侵權或不適當內容,請與我們聯系,我們立即糾正。
  • 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論