摘要:本文是作者的一堂實(shí)際課程的教學(xué)案例,通過檢查學(xué)生作業(yè)的形式,引出本堂課的講授內(nèi)容。隨著對(duì)作業(yè)中問題的層層提問與解決,引出軟件測(cè)試概念,并把軟件測(cè)試思想融合到程序語(yǔ)言的設(shè)計(jì)過程中,旨在培養(yǎng)學(xué)生在初學(xué)程序語(yǔ)言設(shè)計(jì)時(shí)就養(yǎng)成良好的編程習(xí)慣,建立軟件測(cè)試的思想。
關(guān)鍵詞:軟件測(cè)試;C語(yǔ)言;測(cè)試用例;語(yǔ)法錯(cuò)誤;邏輯錯(cuò)誤
中圖分類號(hào):G642文獻(xiàn)標(biāo)識(shí)碼:B
文章編號(hào):1672-5913 (2007) 20-0106-04
1教學(xué)目標(biāo)
1. 通過教師的啟發(fā)引導(dǎo),使學(xué)生理解軟件測(cè)試的基本概念;
2 通過對(duì)程序案例的過程講解,使學(xué)生掌握基本控制語(yǔ)句switch、break的使用;
3. 通過對(duì)程序案例的錯(cuò)誤排除,讓學(xué)生了解語(yǔ)法錯(cuò)誤和邏輯錯(cuò)誤的概念;
4. 了解軟件測(cè)試在程序中的作用。
2教學(xué)重點(diǎn)及難點(diǎn)
1 軟件測(cè)試思想的建立;
2 使學(xué)生養(yǎng)成良好的編程習(xí)慣;
3教學(xué)過程
3.1以點(diǎn)帶線,導(dǎo)出概念
(課件:請(qǐng)大家查閱書籍和網(wǎng)上搜索,了解軟件錯(cuò)誤給我們帶來(lái)的危害。)
師:這是我們上次課后給同學(xué)們布置的作業(yè),讓大家通過查閱書籍和網(wǎng)上搜索,給出這問題的解釋。現(xiàn)在請(qǐng)同學(xué)們舉手發(fā)言。
生1:1996年6月4日,阿麗亞娜5型火箭第一次鑒定發(fā)射,因火箭導(dǎo)航電腦軟件系統(tǒng)發(fā)生故障而失??;
生2:2003年4月,一個(gè)軟件故障因?yàn)橛行C(jī)票的價(jià)格被誤定為1.86美元而導(dǎo)致美國(guó)航空集團(tuán)公司損失數(shù)千美元;
生3:2003年5月4日,俄羅斯“聯(lián)盟—TMA1”載人飛船返回地球途中,由于飛船的導(dǎo)航計(jì)算機(jī)軟件設(shè)計(jì)中的錯(cuò)誤引起飛船偏離了降落目標(biāo)地點(diǎn)約460公里;
生4:2004年12月21日,美國(guó)空軍一架F/A-22“猛禽”戰(zhàn)斗機(jī)進(jìn)行戰(zhàn)術(shù)和訓(xùn)練工作時(shí)墜毀。飛行員安全彈射,飛機(jī)墜毀,事故與飛機(jī)的飛行控制軟件有關(guān);
生5:美國(guó)商務(wù)部的國(guó)立標(biāo)準(zhǔn)技術(shù)研究所(NIST:National Institute of Standards and Technology)有關(guān)軟件缺陷的損失調(diào)查報(bào)告表示,“據(jù)推測(cè),由于軟件缺陷而引起的損失額每年高達(dá)595億美元。這一數(shù)字相當(dāng)于美國(guó)國(guó)內(nèi)生產(chǎn)總值的0.6%”。
師:通過剛才大家的踴躍發(fā)言,老師了解到大家在課后都做了很充分的準(zhǔn)備。如此看來(lái),軟件設(shè)計(jì)中的錯(cuò)誤給我們帶來(lái)的危害是相當(dāng)沉重的。那么,如何去規(guī)避這些錯(cuò)誤的發(fā)生?如何去發(fā)現(xiàn)這個(gè)錯(cuò)誤?這就是軟件工程中的軟件測(cè)試思想。請(qǐng)同學(xué)們總結(jié)一下,軟件測(cè)試具體做什么工作?
生:找出軟件中的錯(cuò)誤。
師:軟件測(cè)試就是找出軟件中存在的問題,我們把軟件中存在的問題稱為缺陷(bugs)。如何查找這些缺陷?
(設(shè)計(jì)思路:?jiǎn)栴}是最好的老師,是學(xué)生學(xué)習(xí)的引導(dǎo)者,沒有問題便沒有深入。在教學(xué)中,我們經(jīng)常發(fā)現(xiàn)學(xué)生問不出問題,其原因在于學(xué)生沒能消化知識(shí),不能靈活運(yùn)用。因此教師在教學(xué)過程中,應(yīng)當(dāng)有意設(shè)置一些問題,引導(dǎo)學(xué)生在問題的解決過程中學(xué)習(xí),即提出問題,留給學(xué)生時(shí)間思考、討論、解決問題。在這個(gè)環(huán)節(jié)中,將問題以課后作業(yè)的形式布置下去,啟發(fā)引領(lǐng)學(xué)生充分利用網(wǎng)上資源和圖書館資源查閱信息,使學(xué)生養(yǎng)成自學(xué)與分析問題的能力,逐層導(dǎo)出軟件測(cè)試的概念,為軟件測(cè)試方法的引入進(jìn)行鋪墊。通過課堂提問,活躍了課堂氣氛,使學(xué)生在輕松愉悅的環(huán)境中學(xué)習(xí)。)
3.2引用案例,明確概念,步步遞進(jìn),解決問題
(課件:?jiǎn)栴}描述)用C語(yǔ)言程序完成如下功能:輸入某年某月某日,判斷這一天是這一年的第幾天。(學(xué)生通過網(wǎng)絡(luò)將作業(yè)提交給老師,老師審閱后,發(fā)現(xiàn)學(xué)生作業(yè)中存在的問題)
師:這是上次課后布置的作業(yè)。
師:現(xiàn)將一個(gè)學(xué)生作業(yè)做為本次課程的教學(xué)案例。請(qǐng)同學(xué)們看屏幕。
(教師進(jìn)入Turbo C for windows 集成實(shí)驗(yàn)與學(xué)習(xí)環(huán)境,展示學(xué)生編寫的程序結(jié)構(gòu),邊操作邊演示)
程序內(nèi)容如下:
main()
{
int day,month,year,sum,leap;
printf(\"\please input year,month,day\\");
scanf(\"%d,%d,%d\",year,month,day);
switch(month)
/*先計(jì)算某月以前月份的總天數(shù)*/
{
case 1:sum=0;
case 2:sum=31;
case 3:sum=59;
case 4:sum=90;
case 5:sum=120;
case 6:sum=151;
case 7:sum=181;
case 8:sum=212;
case 9:sum=243;
case 10:sum=273;
case 11:sum=304;
case 12:sum=334;
default:printf(\"data error\");
}
sum=sum+day;/*再加上某天的天數(shù)*/
printf(\"It is the %dth day.\",sum);}
師:請(qǐng)同學(xué)根據(jù)這個(gè)程序,說(shuō)出該程序的設(shè)計(jì)思想。
生:要判斷輸入日期在一年中的第幾天,首先要計(jì)算此日期前的月份包含多少天,以3月5日為例,應(yīng)該先把前兩個(gè)月的加起來(lái),然后再加上5天即本年的第幾天。
師:第一步,看一下這個(gè)程序的結(jié)構(gòu)是否合理。
首先,大家知道在編寫程序時(shí),遇到具有按不同情況分轉(zhuǎn)的多路問題,一般采用C語(yǔ)言提供的if-else-if的嵌套結(jié)構(gòu)和開關(guān)語(yǔ)句來(lái)實(shí)現(xiàn)。這里雖可用嵌套if-else-if語(yǔ)句來(lái)實(shí)現(xiàn),但if-else-if語(yǔ)句使用不方便,并且容易出錯(cuò)。針對(duì)本案例,多分支的入口執(zhí)行語(yǔ)句因具有規(guī)律性,可按輸入的月份進(jìn)行選擇執(zhí)行,因此選擇開關(guān)語(yǔ)句結(jié)構(gòu)解決該問題是適合的。
師:(接下來(lái)復(fù)習(xí)switch開關(guān)語(yǔ)句)。
執(zhí)行switch開關(guān)語(yǔ)句時(shí),是將變量逐個(gè)與case后的常量進(jìn)行比較,若與其中一個(gè)相等,則執(zhí)行該常量下的語(yǔ)句,若不與任何一個(gè)常量相等,則執(zhí)行default后面的語(yǔ)句。
師:第二步,我們運(yùn)行程序,檢查程序的正確性。
(多媒體機(jī)房演示,將程序運(yùn)行結(jié)果投影在大屏幕上)
運(yùn)行程序,輸入測(cè)試用例:2007,3,8
運(yùn)行結(jié)果如圖1所示。
師:請(qǐng)同學(xué)們注意,程序運(yùn)行的結(jié)果與實(shí)際問題的結(jié)果是否一致?
生:不一致。不應(yīng)該是342天。
師:該問題出現(xiàn)的原因是缺少了break語(yǔ)句。
師:(接下來(lái)復(fù)習(xí)break開關(guān)語(yǔ)句)。
break語(yǔ)句通常用在循環(huán)語(yǔ)句和開關(guān)語(yǔ)句中。當(dāng)break用于開關(guān)語(yǔ)句switch中時(shí),可使得程序在執(zhí)行完選中的分支后,跳出整個(gè)switch語(yǔ)句(即跳到switch接的一對(duì){}之后),完成switch。如果沒有這個(gè)break,程序?qū)⒃诶^續(xù)前進(jìn)到下一分支,直到遇到后面的break或者switch完成。
下面請(qǐng)同學(xué)們對(duì)上面的程序進(jìn)行改進(jìn)。
生:(在計(jì)算機(jī)上改進(jìn)原程序)
改進(jìn)后的程序如下:
main()
{
int day,month,year,sum,leap;
printf(\"\please input year,month,day\\");
scanf(\"%d,%d,%d\",year,month,day);
switch(month)
/*先計(jì)算某月以前月份的總天數(shù)*/
{
case 1:sum=0;break;
case 2:sum=31;break;
case 3:sum=59;break;
case 4:sum=90;break;
case 5:sum=120;break;
case 6:sum=151;break;
case 7:sum=181;break;
case 8:sum=212;break;
case 9:sum=243;break;
case 10:sum=273;break;
case 11:sum=304;break;
case 12:sum=334;break;
default:printf(\"data error\"); break;
}
sum=sum+day; /*再加上某天的天數(shù)*/
printf(\"It is the %dth day.\",sum);}
師:下面我們對(duì)剛才改進(jìn)的程序來(lái)運(yùn)行一下。
運(yùn)行程序,輸入測(cè)試用例:2007,3,8
程序運(yùn)行結(jié)果如圖2所示。
生1:這次程序運(yùn)行結(jié)果是正確的。
生2:如果是閏年呢?比如我們輸入:2000,3,8,結(jié)果會(huì)是什么呢?
師:我們可以進(jìn)一步測(cè)試一下。
運(yùn)行程序,輸入測(cè)試用例:2000,3,8
程序運(yùn)行結(jié)果如圖3所示。
生:這次的結(jié)果是不正確的。
師:由此看來(lái),上次對(duì)程序的改進(jìn)仍是不完善的。請(qǐng)同學(xué)們思考一下,如何進(jìn)一步改進(jìn)這個(gè)程序?
生:對(duì)于這個(gè)案例,如果是閏年且輸入月份大于3時(shí)需考慮多加一天,那么此程序還要根據(jù)輸入的年份判斷是否為閏年。閏年的判斷規(guī)則為:如果此年份能被400整除,則是閏年;如果此年份能被4整除,而不能被100整除,則是閏年;否則不是。
師:請(qǐng)同學(xué)們根據(jù)剛才這位同學(xué)的思想,對(duì)程序做進(jìn)一步修改。
生:(在計(jì)算機(jī)上改進(jìn)原程序)
改進(jìn)后的程序如下:
#include
void main()
{
int day,month,year,sum,leap;
printf(\"\please input year,month,day\\");
scanf(\"%d,%d,%d\",year,month,day);
switch(month) /*先計(jì)算某月以前月份的總天數(shù)*/
{
case 1:sum=0;break;
case 2:sum=31;break;
case 3:sum=59;break;
case 4:sum=90;break;
case 5:sum=120;break;
case 6:sum=151;break;
case 7:sum=181;break;
case 8:sum=212;break;
case 9:sum=243;break;
case 10:sum=273;break;
case 11:sum=304;break;
case 12:sum=334;break;
default:printf(\"data error\");break;
}
sum=sum+day;/*再加上某天的天數(shù)*/
if(year%400 = = 0||(year%4 = = 0year%100!=0))/*判斷是不是閏年*/
leap=1;
else
leap=0;
if(leap = = 1month>2) /*如果是閏年且月份大于2,總天數(shù)應(yīng)該加一天*/
sum++;
printf(\"It is the %dth day.\",sum);}
師:運(yùn)行修改后的程序;
輸入測(cè)試用例:2000,3,8
運(yùn)行結(jié)果如圖4所示。
生:這次程序運(yùn)行結(jié)果與實(shí)際是一致的。
師:經(jīng)過對(duì)上面的案例分析,結(jié)合以前我們學(xué)習(xí)過的知識(shí),我們將C程序的錯(cuò)誤可以分為兩種:語(yǔ)法錯(cuò)誤和邏輯錯(cuò)誤
(1) 語(yǔ)法錯(cuò)誤
這是C語(yǔ)言初學(xué)者出現(xiàn)最多的錯(cuò)誤,比如,分號(hào)“;”是每個(gè)C語(yǔ)句的結(jié)束的標(biāo)志,在C語(yǔ)句后忘記寫“;”就是語(yǔ)法錯(cuò)誤。發(fā)生語(yǔ)法錯(cuò)誤的程序,編譯是通不過的,用戶須通過軟件的提示信息來(lái)修改。
(2) 邏輯錯(cuò)誤
邏輯錯(cuò)誤就是用戶編寫的程序已經(jīng)沒有語(yǔ)法錯(cuò)誤,可以運(yùn)行,但得不到所期望的結(jié)果(或正確的結(jié)果),也就是說(shuō)由于程序設(shè)計(jì)者的原因,程序并沒有按照程序設(shè)計(jì)者的思路來(lái)運(yùn)行。比如我們這堂課的例子就是這樣:我們的目的是求輸入某年某月某日,判斷這一天是這一年的第幾天。但由于沒有考慮到對(duì)輸入年份進(jìn)行是否為閏年的判斷,就是導(dǎo)致運(yùn)行結(jié)果的錯(cuò)誤。象這種情況這就是邏輯錯(cuò)誤。
編譯軟件對(duì)有邏輯錯(cuò)誤的程序是發(fā)現(xiàn)不了,要用戶不斷輸入測(cè)試數(shù)據(jù)、跟蹤程序的運(yùn)行過程才能發(fā)現(xiàn)程序中的邏輯錯(cuò)誤,這是最不容易修改的。比如軟件的BUG就是邏輯錯(cuò)誤,發(fā)行補(bǔ)丁程序就是修改邏輯錯(cuò)誤;如大家最常見的就是Windows操作系統(tǒng)經(jīng)常發(fā)布的補(bǔ)丁程序了。在這節(jié)課,我們通過學(xué)生案例,將軟件測(cè)試思想運(yùn)用到了程序設(shè)計(jì)當(dāng)中,是想讓同學(xué)們?cè)陂_始學(xué)習(xí)程序設(shè)計(jì)語(yǔ)言時(shí),就養(yǎng)成良好的編程習(xí)慣,規(guī)范編程思想,善于用軟件測(cè)試的方法去調(diào)試和修改自己的程序。
(設(shè)計(jì)思路:教學(xué)是一門藝術(shù),更是教師的創(chuàng)造性、能動(dòng)性和教學(xué)水平的綜合體現(xiàn),在教學(xué)過程中要將學(xué)生的積極性和潛能充分發(fā)揮出來(lái),這樣才能達(dá)到最佳的教學(xué)效果。通過引用學(xué)生作業(yè),讓學(xué)生不斷地對(duì)案例進(jìn)行修正,將軟件測(cè)試思想融入到程序設(shè)計(jì)當(dāng)中。一方面,對(duì)激發(fā)學(xué)生求知欲望和創(chuàng)造性思維,對(duì)提高學(xué)生的程序設(shè)計(jì)能力和水平具有積極的作用;在遵循以人為本的素質(zhì)教育理念指導(dǎo)下,讓教師成為學(xué)生獲取綜合知識(shí)的引導(dǎo)者,成為學(xué)生自主學(xué)習(xí)的指導(dǎo)者,成為學(xué)生創(chuàng)造能力的培育者;另一方面,通過對(duì)案例的分析與講解,強(qiáng)化了軟件工程中的軟件測(cè)試?yán)碚摚瑸閷W(xué)生后續(xù)課的學(xué)習(xí)進(jìn)行了鋪墊。)
4回顧總結(jié),強(qiáng)化認(rèn)知
師:通過本節(jié)課的學(xué)習(xí),大家學(xué)到了什么?
生1:軟件測(cè)試思想的建立。
生2:軟件測(cè)試的測(cè)試方法。
生3:在復(fù)習(xí)與鞏固C語(yǔ)言知識(shí)的同時(shí),了解了編程過程中測(cè)試的重要性。知道了在程序開發(fā)的過程中,測(cè)試是一個(gè)不可缺少的重要環(huán)節(jié)。
師:同學(xué)們總結(jié)的非常好。通過今天的學(xué)習(xí),我們知道了“三分編程七分測(cè)試”,說(shuō)明程序測(cè)試的工作量要比編程大得多。
測(cè)試程序是一個(gè)艱苦、心細(xì)、又有技巧的事,只有經(jīng)常上機(jī)多調(diào)試程序,才能不斷地積累經(jīng)驗(yàn)、提高程序調(diào)試技能。
一個(gè)優(yōu)秀的程序員是在改進(jìn)自己所編寫程序的過程中,不斷地積累經(jīng)驗(yàn)、逐步完善,并走向成功的。請(qǐng)同學(xué)們記?。褐辉诎哆吙炊幌滤娜耸怯肋h(yuǎn)學(xué)不會(huì)游泳的。要想達(dá)到賣油翁的“油自錢孔入而錢不濕”的高超技巧,必須多測(cè)試程序,這樣才能成為一名優(yōu)秀的程序員。
作者簡(jiǎn)介
張輝(1970-),女,陜西省華縣人,講師,本科,研究方向:軟件技術(shù)、網(wǎng)絡(luò)技術(shù)
通信地址:河南省開封市東京大道西段黃河水利職業(yè)技術(shù)學(xué)院信息工程系,475003
電話:13849128689
E-mail:kfzhanghui@163.com
基金項(xiàng)目:國(guó)家示范性高等職業(yè)院校建設(shè)項(xiàng)目06-14
河南省教育科學(xué)“十一五”規(guī)劃課題 課題編號(hào):2006-JKGHAG-189