黎自強 羅翠英
摘要:本文討論了C語言的前綴++(前綴--)與后綴++(后綴--)運算符的優(yōu)先級、C程序設(shè)計和調(diào)試的幾點技巧,更好地讓學生進一步學好C語言,掌握C語言程序設(shè)計,提高學生的軟件開發(fā)能力。
關(guān)鍵詞:C語言程序設(shè)計;運算符;優(yōu)先級;二維數(shù)組
中圖分類號:G642 文獻標識碼:B
1引言
“C語言程序設(shè)計”課程對理工科專業(yè)學生來說,是一門非常重要的基礎(chǔ)課程,但初學起來十分困難。其主要原因是:(1) C語言的數(shù)據(jù)類型和運算符多、表達式復雜;(2) 初學者在學習過程中必須暫時保留人的思維形式,使用計算機的程序模式工作。為了使學生學習好“C語言程序設(shè)計”這門課程,許多教育工作者對教學方法進行了深入的探索,積累了豐富的教學經(jīng)驗。例如:文獻[1]介紹了C語言程序設(shè)計的案例教學方法,文獻[2]討論了C語言程序設(shè)計中關(guān)于自增和自減運算符的理解和編程要點。盡管如此,如何使學生能更好地掌握C語言程序設(shè)計仍然值得教育工作者進一步探索。本文將自增和自減運算符分為優(yōu)先級不同的前綴++(前綴--)與后綴++(后綴--)兩種運算符,給出若干程序設(shè)計和調(diào)試的技巧,使學生更好地掌握C語言程序設(shè)計。
2關(guān)于自增和自減運算符
如果C語言表達式存在自增或自減運算符,則其值的計算和表達式中變量值的改變很容易弄錯。文獻[3~5]規(guī)定前綴自增(自減)和后綴自增(自減)運算符的優(yōu)先級相同,都大于算術(shù)運算符,結(jié)合方向是自右向左。它們的區(qū)別是:前綴自增(自減)是在使用前增加或自減少1,而后綴自增(自減)是在使用后增加或自減少1。作者在教學實踐中發(fā)現(xiàn):學生按上述規(guī)則并不容易讀懂程序和編寫程序。本文把前綴自增(自減)和后綴自增(自減)運算符看成兩種運算符,且規(guī)定前綴自增(自減)運算符的優(yōu)先級大于算術(shù)運算符,后綴自增(自減)運算符的優(yōu)先級低于賦值運算符,僅高于逗號運算符。本文的這一規(guī)則比較適合我們常常使用的Turbo C編譯系統(tǒng),也容易被學生理解和掌握。
例1:若i=3,則執(zhí)行賦值語句j=++i;時是將i的值先變?yōu)?,再賦值給j,j的值變?yōu)?;而執(zhí)行賦值語句j=i++;時是先將i的值賦給j,j的值為3,然后i的值先變?yōu)?。
例2:若i=3,則執(zhí)行賦值語句j=(i++)+(i++)+(i++);時是將三個i的值先加得12賦給j,j的值變12,然后i的值再三次增1變?yōu)?;而執(zhí)行賦值語句j=(++i)+(++i)+(++i);時是先將i的值再三次增1變?yōu)?,然后將三個i的值相加得18賦給j,j的值為18。
例3:若i=3,則執(zhí)行賦值語句printf(“%d”, -i++);時是將先輸出i的相反數(shù)-3,然后i的值再增1變?yōu)?;而執(zhí)行賦值語句printf(“%d”, -++i);時根據(jù)優(yōu)先級相同的負號與前綴自增運算符為自右向左的結(jié)合方向,則是先將i的值增1變?yōu)?,然后再輸出i的相反數(shù)-4。
值得注意的兩個問題:
(1) 當一個變量出現(xiàn)在一個函數(shù)的多個參數(shù)中時,不能將自增或自減運算符作用于該變量,否則用本文規(guī)則不能正確計算表達式的值和輸出結(jié)果。例如:若i=3,則執(zhí)行賦值語句printf(“%d, %d”, i,i*i++);時其輸出結(jié)果為(4,12);而執(zhí)行賦值語句printf(“%d ,%d”, i*i++,i);時其輸出結(jié)果為(12,3)。
(2) 當自增或自減運算符出現(xiàn)在邏輯表達式中時,自增或自減運算可能不被計算。例如:
若i=1,j=1,k=1,在計算表達式++i||++j&&++k時,因++i非0,不再計算++j&&++k部分,直接得到整個表達式的值為1,因此,計算表達式后,變量i的值為2,而j和k沒有執(zhí)行自增加運算,其值都為1。
基金項目:2006年湘潭大學校級精品課程基金(湘大教發(fā)[2007]20)。
作者簡介:黎自強(1963-),男,教授,博士,研究方向為計算機圖形學,計算機視覺,智能計算。羅翠英(1966-),女,湖南益陽人,湖南工業(yè)大學講師,研究方向為計算機圖形學。
3關(guān)于scanf()函數(shù)和實型二維數(shù)組
在C語言程序設(shè)計中,常常利用scanf()函數(shù)對二維實型數(shù)組賦值,例如:下面的程序段是從鍵盤輸入10個數(shù)到二維實型數(shù)組x中。
voidmain()
{ int i,j;
float x[5][2];
for(i=1;i<5;i++)
for(j=1;j<2;j++)
scanf(“%f”,&x[i][j]);
for(i=1;i<5;i++)
for(j=1;j<2;j++)
printf(“%f”,x[i][j]);
}
上述程序在Turbo C2.0集成開發(fā)環(huán)境下編譯和連接是沒有錯誤的,但運行時出現(xiàn)如下錯誤信息:
scanf:floating point formats not linked
Abnormal program termination
解決的方法有兩種,方法一:
(1) float x[10][2]—>float x[10][2], t;
(2) scanf(“%f”,&x[i][j]);—>{scanf (“%f ”, &t);x[i][j]=t;}
方法二:在scanf()函數(shù)的%f前面保留一個空格,即:scanf(“_%f”,&x[i][j]);
4關(guān)于getch()的妙用
4.1查看顯示結(jié)果
一般,在Turbo C2.0集成開發(fā)環(huán)境下,運行C程序后即刻返回到編輯狀態(tài)。如果想看到程序執(zhí)行的結(jié)果,就必須按Alt+F5鍵。如果在程序的結(jié)束行前加一個語句getch();則程序運行暫停在顯示結(jié)果的界面,按任意鍵才返回編輯狀態(tài)。這樣能讓程序員更簡捷地查看結(jié)果。
4.2調(diào)試程序
一個能夠編譯、連接和運行的C程序,只有在沒有結(jié)構(gòu)上的錯誤的前提下才能保證其結(jié)果正確。這一步是靠調(diào)試程序來完成。對于初學C語言程序設(shè)計的學生來說,迅速找出程序結(jié)構(gòu)上的錯誤是一個至關(guān)重要的問題。一個簡單、可行方法就是利用printf()和getch()的組合語句在關(guān)鍵點跟蹤程序的執(zhí)行。
例如:程序段1-14是求1+2+3+…+n的和(正整數(shù)n由文件輸入)。
1#include
2main()
3{
4int i=0,n=0;
5long sum=0;
6FILE *fp=NULL;
7fp=fopen("in2.txt","r");
8if(fp!=NULL)
9 fscanf(fp,"%d",&n);
10 for(i=1;i<=n;i++);
11 sum=sum+i;
12printf("%ld ",sum);
13fclose(fp);
14}
當文件in2.txt中的數(shù)據(jù)為10時,運行程序得到的結(jié)果為11,不正確。為了迅速找到錯誤所在,在9行與10行之間插入兩行語句:
printf("n=%d ",n);
getch();
再次運行程序,若屏幕上沒有顯示n=10,則就檢查1-9行程序,直到屏幕上顯示n=10為止;否則程序的錯誤是在10-13行,這時去掉在9行與10行之間插入的兩行語句并將11行語句改成:
{ sum=sum+i;
printf("%ld ",sum);
getch();
}
再次運行程序,結(jié)果發(fā)現(xiàn)只要擊一次鍵就會返回編輯狀態(tài),這就說明循環(huán)語句沒有起到循環(huán)作用。檢查出第10行末尾多了個“;”,去掉“;”并運行程序得正確值55。
4.3用于菜單選擇
getchar()和getch()都可以從鍵盤接收字符,它們的區(qū)別是:(1)前者是一個函數(shù),后者是一個宏名;(2)前者接收字符時,會將鍵入的字符回顯到屏幕上;后者則不會將鍵入的字符回顯,很適合于在菜單中進行選擇。下面的程序段引自文獻[2],它是判斷某年是否為潤年,但在標號語句處有一個結(jié)構(gòu)錯誤,文獻[2]是將標號為error 的語句改為getchar(),ch=getchar();,本文給出一種不同的修改方法:將標號為error 的語句改為getch()。
# include
main( )
{
int ch;
int year;
do {
printf("please input year: ");
scanf("%d", &year);
if(year%4 ==0 && year% 100!=0||year%400== 0)
printf("YES %d ",year);
else
printf("NO%d ", year);
printf("Y--continue, any key--exit ");
error: ch=getchar ( ) ;
} while (ch = = ‘Y || ch = = ‘y);
}
4結(jié)束語
C語言程序的編寫和調(diào)試是初學者學習“C語言程序設(shè)計”課程中遇到的難點中的兩個。掌握C語言運算符的優(yōu)先級和結(jié)合方向是初學者正確編寫C語言程序代碼的前
提。本文通過把前綴++(前綴--)與后綴++(后綴--)運算符理解為優(yōu)先級不同的兩個運算符,能使初學者,尤其是非計算機專業(yè)的學生,更好地掌握其表達式的計算,進而正確設(shè)計出高效的C程序。同時,介紹的幾點C程序調(diào)試技巧能在一定程度上提高初學者的程序調(diào)試能力。
參考文獻:
[1] 徐萍,宮麗華. “C語言程序設(shè)計”課程教學改革的實踐和探討[J]. 電腦知識與技術(shù),2008,4(1):160-162.
[2] 陳仲民. 關(guān)于C語言教學方法和程序設(shè)計的探討[J]. 計算機教育[J]. 2007(6):3-6.
[3] Kernighan B W, Ritchie D M. The C Programming Language[M]. 2nd ed. Pearson Educatin,2006.8.
[4] 譚浩強. C程序設(shè)計[M]. 2版. 北京:清華大學出版社,1999.
[5] 王秀貴,曹江連. C語言程序設(shè)計教程[M]. 北京:中國鐵道出版社,2007.