




版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認(rèn)領(lǐng)
文檔簡介
1、技術(shù)創(chuàng)新,變革未來面向?qū)ο蟮能浖y試技術(shù)概述目錄1 面向?qū)ο蟮幕靖拍? 面向?qū)ο蟮能浖y試與傳統(tǒng)軟件測試3 面向?qū)ο筌浖y試模型4 面向?qū)ο蟮膯卧獪y試5 面向?qū)ο蟮募蓽y試6 面向?qū)ο蟮南到y(tǒng)測試7 GUI測試面向?qū)ο筌浖哂懈鼑?yán)重的潛在的測試問題:由于面向?qū)ο蠹夹g(shù)開發(fā)的軟件代碼重用率高,更需要嚴(yán)格測試,避免錯誤的繁衍。 序 面向?qū)ο蠹夹g(shù)是一種全新的軟件開發(fā)技術(shù),正逐漸代替被廣泛使用的面向過程開發(fā)方法,被看成是解決軟件危機的新興技術(shù)。面向?qū)ο蟮奶卣魇欠庋b、繼承、多態(tài);面向?qū)ο笤O(shè)計的目的是達(dá)到最大限度的重用;面向?qū)ο蠹夹g(shù)產(chǎn)生更好的系統(tǒng)結(jié)構(gòu),更規(guī)范的編程風(fēng)格,極大的優(yōu)化了數(shù)據(jù)使用的安全性;6.1
2、面向?qū)ο蟮幕靖拍顚ο箢愊⒔涌诜庋b繼承多態(tài)面向?qū)ο笏枷氲挠蓙怼皩ο蟆币辉~在現(xiàn)實生活中經(jīng)常會遇到,它表示現(xiàn)實世界中的某個具體的事物。隨著計算機的普及應(yīng)用,人們越來越希望能更直接與計算機進行交互,而不需要經(jīng)過專門學(xué)習(xí)和長時間訓(xùn)練后才能使用它。這一強烈愿望使軟件設(shè)計人員的負(fù)擔(dān)越來越重,也為計算機領(lǐng)域自身的發(fā)展提出了新的要求。傳統(tǒng)的程序設(shè)計思想無法滿足這一要求,人們就開始尋求一種更能反映人類解決問題的自然方法,面向?qū)ο蠹夹g(shù)就是在這樣的情況下產(chǎn)生的。面向?qū)ο笈c結(jié)構(gòu)化開發(fā)方法現(xiàn)實世界為對象世界OOAOODOOP結(jié)構(gòu)化分析結(jié)構(gòu)化設(shè)計結(jié)構(gòu)化編程順序存儲指令計算機過程世界面向?qū)ο箝_發(fā)方法結(jié)構(gòu)化開發(fā)方法OOA/
3、OOD/OOP是一種從概念上更為直接的路徑。面向過程的結(jié)構(gòu)化方法存在著與現(xiàn)實世界之間的巨大差距。面向?qū)ο蟮幕靖拍頟eter Coad 和 Edward Yourdon 提出下列等式認(rèn)識面向?qū)ο蠓椒ǎ?面向?qū)ο?對象(Object) 分類(Classification) 繼承(Inheritance) 通過消息的通信 (Communication with message)采用這四個概念開發(fā)的軟件系統(tǒng)是面向?qū)ο蟮摹C嫦驅(qū)ο蠹夹g(shù)面向?qū)ο蠓椒ǖ某霈F(xiàn),實際上是程序設(shè)計方法發(fā)展的-個返樸歸真過程。面向?qū)ο蟮膶嵸|(zhì):從系統(tǒng)的組成上來進行分解。對問題自然分割,利用類及對象作為基本構(gòu)造單元,以更接近人類思維的
4、方式建立問題域模型,從而使設(shè)計出的軟件盡可能直接地描述現(xiàn)實世界,構(gòu)造出模塊化的、可重用的、可維護性好的軟件,并能控制軟件的復(fù)雜性降低開發(fā)維護費用。對象對象是指包含了一組屬性以及對這些屬性的操作的封裝體。對象之間存在著一定的關(guān)系,對象之間的交互與合作構(gòu)成更高級的行為。王五由他的頭、胳膊、腿和身體組成汽車是一種交通工具對象間的由分解所構(gòu)成的關(guān)系,part of層次;具有代表一種一般特性的對象之間的聚合關(guān)系,is a層次;代表更一般的對象間在物理上或概念上有關(guān)的相關(guān)關(guān)系。人乘坐或駕駛汽車對象是軟件開發(fā)期間測試的直接目標(biāo)。面向?qū)ο筌浖y試所關(guān)注的焦點: (1)對象的行為是否符合它的規(guī)定說明; (2)該
5、對象與和它相關(guān)的對象是否協(xié)同工作。類類是具有相同屬性和相同行為的對象的集合。面向?qū)ο蟪绦蜻\行的基本元素是對象,而類則是用來定義對象這一基本元素的。在面向?qū)ο蟪绦蛟O(shè)計中,類是一個獨立的程序單位,它有一個類名,還包括用于描述對象屬性的成員變量和用于描述對象行為的成員函數(shù)。類是對象的抽象定義。使用類時必須先實例化用對象名創(chuàng)建類的實例,再通過這個對象去訪問類的成員變量,去調(diào)用類的成員函數(shù)。類和對象之間關(guān)系類似于程序設(shè)計語言中類型和變量之間的關(guān)系。消息消息是對象的操作將要執(zhí)行的一種請求,也被稱為成員函數(shù)調(diào)用或者方法調(diào)用。面向?qū)ο蟮某绦虻膱?zhí)行實際上是執(zhí)行一個由消息連接起來的方法序列。 “發(fā)送消息M到對象N
6、” =“調(diào)用N對象的M方法” 消息傳遞是對象間通信息的手段。一個消息通常包括接收對象名、調(diào)用的操作名和適當(dāng)參數(shù)(如有必要)。消息只告訴接收對象需要完成什么操作,但并不指示接收者怎樣去完成操作。消息完全由接收者解釋,接收者獨立決定采用什么方法來完成所需操作。消息(續(xù))從測試的角度看,關(guān)于消息有下面的結(jié)論:(1)消息的發(fā)送者決定何時進行發(fā)送消息,可能會做出錯誤的決定;(2)消息的接收者可能收到非預(yù)期的特定消息,并做出不正確地反映;(3)消息可能含有參數(shù)。在處理一條消息時,參數(shù)能被接收者使用或修改。若傳遞的參數(shù)是對象,那么在消息被處理前和處理后,對象必須處于正確的狀態(tài),而且必須是接收者所期望的接口。
7、 接口接口是行為聲明的集合。接口是由一些規(guī)范構(gòu)成的,規(guī)范定義了類的一套完整的公共行為。是一種非常有效的編程工具,可以在不破壞現(xiàn)有應(yīng)用程序情況下使對象得以發(fā)展。從測試的角度,關(guān)于接口有下面的結(jié)論:(1)接口封裝了操作的說明。如果這一接口包含的行為和類的行為不相符,那么這一接口的說明就有問題。(2)接口非孤立,它與其它的接口和類有一定的關(guān)系。封裝封裝:是一種信息隱蔽技術(shù),用戶只能看到對象封裝界面上的信息,對象內(nèi)部的實現(xiàn)對用戶是隱蔽的。防止外界未被授權(quán)地訪問一些信息和功能。封裝的目的使對象的使用者和設(shè)計者產(chǎn)生分離使對象的定義和實現(xiàn)分開例:檔風(fēng)玻璃雨刷系統(tǒng)某些檔風(fēng)玻璃雨刷是由帶刻度盤的控制桿控制的。控
8、制桿有4個位置:停止、間歇、低速、高速;刻度盤有3個位置:1、2、3。刻度盤位置指示三種間歇速度,刻度盤的位置只有當(dāng)控制桿在間歇位置上時才有意義。以下決策表給出了擋風(fēng)玻璃雨刷對應(yīng)控制桿和刻度盤的工作速度:C1控制桿C2刻度盤停止間歇1間歇2間歇3低速高速A1雨刷046123060關(guān)間歇低速高速123每分鐘0次擺動每分鐘4次擺動每分鐘6次擺動每分鐘12次擺動每分鐘30次擺動每分鐘60次擺動檔風(fēng)玻璃雨刷類的行為控制桿雨刷刻度盤 定義(類):控制桿CLASS lever(lever position; private senseLeverUp(), Private senseLeverDown()刻
9、度盤CLASS dial(dial position; private senseDialUp(), private senseDialDown)雨刷器CLASS wiper(wiperSpeed; setWiperSpeed(new Speed)控制桿和刻度盤永遠(yuǎn)報告各自的位置,雨刷類成為“主程序”。類之間的耦合很小的封裝最大限度提高重用的潛力,使合成和測試更容易。繼承繼承繼承是類間的基本關(guān)系,是基于層次關(guān)系的不同類共享數(shù)據(jù)和操作的一種機制。繼承允許一個新的類在一個已有的類的基礎(chǔ)上進行定義。一個父類可以有多個子類,這些子類都是父類的特例。父類描述了這些子類的公共屬性和操作,子類中還可以定義它
10、自己的屬性和操作。單一繼承:一個子類只有唯一的一個父類多重繼承:一個子類有一個以上的父類從測試的角度來看,繼承包含以下內(nèi)容:(1)繼承提供一種機制,通過這種機制,潛在的錯誤能夠從一個類傳遞到它的派生類。(2)子類是從父類繼承過來的,子類也就繼承了父類的屬性和操作。因此,可以用測試父類的方法對子類進行測試。繼承使類作為單元測試的選擇變得復(fù)雜;使用“扁平類” 的單元測試可解決繼承的問題,即一個類經(jīng)過擴充包括全部所繼承的屬性和操作的原始類的類。例,SATM系統(tǒng)部分的UML繼承圖accountaccountNumberbalanceGetbalance()Setbalance()checkingAcc
11、ountcheckProcessingChargecheckNumberpostCharge()savingsAccountinterestRatepostInterest()checkingAccountaccountNumberbalancecheckProcessingChargecheckNumberGetbalance()Setbalance()postCharge()savingsAccountaccountNumberbalanceinterestRateGetbalance()Setbalance()postInterest()類繼承扁平化處理類多態(tài)多態(tài)是指同一個操作作用于不同
12、的對象可以有不同的解釋,產(chǎn)生不同的執(zhí)行結(jié)果。是面向?qū)ο蟪绦蛟O(shè)計語言的基本機制,是將一個方法名與不同方法關(guān)聯(lián)的能力。消息的發(fā)送者不需要知道接收對象的類;接收對象可以屬于任意的類。多態(tài)性是一個非常重要的特征。支持靈活的設(shè)計,同時易于維護。6.2 面向?qū)ο笈c傳統(tǒng)軟件的測試面向?qū)ο蠹夹g(shù)所獨有的封裝、繼承、多態(tài)等新特點給測試帶來一系列新的問題,增加了測試的難度。與傳統(tǒng)的面向過程的程序設(shè)計相比,面向?qū)ο蟪绦蛟O(shè)計產(chǎn)生錯誤的可能性增大,或者使得傳統(tǒng)軟件測試中的重點不再那么突出,使原來測試經(jīng)驗和實踐證明的次要方面成為了主要問題。例如:函數(shù) y = Function(x) 如果該函數(shù)寫在傳統(tǒng)的面向過程的程序中,通
13、常考慮的是函數(shù)Function()本身的行為特點。但若寫在面向?qū)ο蟮某绦蛑校筒坏貌煌瑫r考慮基類函數(shù)Base:Function() 的行為和派生類函數(shù)Derived:Function()的行為。面向?qū)ο蠹夹g(shù)的特點給測試帶來的新問題具體表現(xiàn)為:(1)封裝把數(shù)據(jù)及對數(shù)據(jù)的操作封裝在一起,限制了對象屬性對外的透明性和外界對它的操作權(quán)限,在某種程度上避免了對數(shù)據(jù)的非法操作,有效防止了故障的擴散。但同時,封裝機制也給測試數(shù)據(jù)的生成、測試路徑的選取以及測試結(jié)構(gòu)的分析帶來了困難。(2)繼承實現(xiàn)了共享父類中定義的數(shù)據(jù)和操作,同時也可定義新的特征。子類是在新的環(huán)境中存在,所以父類的正確性不能保證子類的正確性。繼
14、承使代碼的重用率得到了提高,但同時也使故障的傳播幾率增加。(3)多態(tài)和動態(tài)綁定增加了系統(tǒng)運行中可能的執(zhí)行路徑,而且給面向?qū)ο筌浖砹藝?yán)重的不確定性,給測試覆蓋率的活動帶來新的困難。 面向?qū)ο笈c傳統(tǒng)軟件的測試(續(xù))與傳統(tǒng)軟件相比,由于存在的諸如繼承、多態(tài)、動態(tài)綁定等關(guān)系,面向?qū)ο筌浖哂懈鼜?fù)雜的依賴關(guān)系,一個類將不可避免的依賴于其它的類,從而增加了面向?qū)ο筌浖y試的難度。傳統(tǒng)軟件中存在的依賴關(guān)系有:變量間的數(shù)據(jù)依賴;模塊間的調(diào)用依賴;變量與其類型間的定義依賴;模塊與其變量間的功能依賴。面向?qū)ο筌浖舜嬖谏鲜鲆蕾囮P(guān)系外,還存在以下的依賴關(guān)系:類與類間的依賴;類與操作間的依賴;類與消息間的依賴;
15、類與變量間的依賴;操作與變量間的依賴;操作與消息間的依賴;操作與操作間的依賴。面向?qū)ο笈c傳統(tǒng)軟件的測試(續(xù))6.3 面向?qū)ο筌浖y試模型面向?qū)ο蟮某绦蚪Y(jié)構(gòu)不再是傳統(tǒng)的功能模塊結(jié)構(gòu),作為一個整體,原有集成測試所要求的逐步將開發(fā)的模塊搭建在一起進行測試的方法已變得不可行。而且,面向?qū)ο筌浖仐壛藗鹘y(tǒng)的開發(fā)模式,已經(jīng)不可能用功能細(xì)化的觀點來檢測面向?qū)ο蠓治龊驮O(shè)計的結(jié)果。因此,傳統(tǒng)的測試模型對面向?qū)ο筌浖呀?jīng)不再適用。面向?qū)ο蟮能浖_發(fā)模型將開發(fā)過程定義為面向?qū)ο蠓治?OOA)、面向?qū)ο笤O(shè)計(OOD)和面向?qū)ο缶幊?OOP)三個階段。針對這種開發(fā)模型,應(yīng)該建立一種新的測試模型。面向?qū)ο筌浖y試模型(續(xù)
16、)面向?qū)ο蟮臏y試模型OO System TestOO Integrate TestOOAOODOOPOOA TestOOD TestOOP TestOO Unit Test面向?qū)ο?分析的測試面向?qū)ο?設(shè)計的測試面向?qū)ο?編程的測試面向?qū)ο笙到y(tǒng)測試面向?qū)ο髥卧獪y試面向?qū)ο蠹蓽y試面向?qū)ο筌浖y試模型(續(xù))OOA Test 和OOD Test 是對分析結(jié)果和設(shè)計結(jié)果的測試,主要是對分析設(shè)計產(chǎn)生的文檔進行測試,是軟件開發(fā)前期的關(guān)鍵性測試。OOP Test 主要針對編程風(fēng)格和程序代碼實現(xiàn)進行測試,主要的測試內(nèi)容在面向?qū)ο髥卧獪y試和面向?qū)ο蠹蓽y試中體現(xiàn)。面向?qū)ο髥卧獪y試針對程序內(nèi)部具體單一功能的模塊
17、進行測試,比如在C+程序中主要就是對類成員函數(shù)的測試。面向?qū)ο蠹蓽y試主要對系統(tǒng)內(nèi)部的相互服務(wù)進行測試,如成員函數(shù)間的相互作用、類間的消息傳遞等。面向?qū)ο笙到y(tǒng)測試是基于面向?qū)ο蠹蓽y試的最后階段的測試,主要以用戶需求為測試標(biāo)準(zhǔn)。面向?qū)ο蠓治龅臏y試(OOA Test)OOA的測試重點在其完整性和冗余性。對OOA階段的測試劃分為五個方面:對認(rèn)定的對象的測試;對認(rèn)定的結(jié)構(gòu)的測試;對認(rèn)定的主題的測試;對定義的屬性和實例關(guān)聯(lián)的測試;對定義的服務(wù)和消息關(guān)聯(lián)的測試。 OOA中認(rèn)定的對象:是指對問題空間中的結(jié)構(gòu)、其他系統(tǒng)、設(shè)備、被記憶的事件、系統(tǒng)涉及的人員等實際實例的抽象。面向?qū)ο笤O(shè)計的測試(OOD Test
18、)OOD是OOA的進一步細(xì)化和擴充,重點在于說明項目的實施方案,來確定類和類的結(jié)構(gòu)。對OOD的測試,應(yīng)針對功能的實現(xiàn)和重用以及對OOA結(jié)果的拓展進行,從以下三方面考慮:(1)對認(rèn)定的類的測試是否涵蓋了OOA中所有認(rèn)定的對象;是否能體現(xiàn)OOA中定義的屬性;是否能實現(xiàn)OOA中定義的服務(wù);是否對應(yīng)著一個含義明確的數(shù)據(jù)抽象;是否盡可能少的依賴其他類;類中的方法是否單用途。(2)對構(gòu)造的類層次結(jié)構(gòu)的測試類層次結(jié)構(gòu)是否涵蓋了所有定義的類;是否能體現(xiàn)OOA中定義的實例關(guān)聯(lián);是否能實現(xiàn)OOA中定義的消息關(guān)聯(lián);子類是否具有父類沒有的新特性;子類間的共同特性是否完全在父類中得以體現(xiàn)。(3)對類庫支持的測試面向?qū)ο?/p>
19、編程的測試(OOP Test)面向?qū)ο蟪绦蚴前压δ艿膶崿F(xiàn)分布在類中。能正確實現(xiàn)功能的類,通過消息傳遞來協(xié)同實現(xiàn)設(shè)計要求的功能。這種程序架構(gòu)能將出現(xiàn)的錯誤精確的確定在某一具體的類。 對OOP的測試重點集中在類功能的實現(xiàn)和相應(yīng)的面向?qū)ο蟪绦蚣軜?gòu),主要體現(xiàn)為以下兩個方面:(1)數(shù)據(jù)成員是否滿足數(shù)據(jù)封裝的要求基本原則是數(shù)據(jù)成員是否被外界直接調(diào)用。(2)類是否實現(xiàn)了要求的功能測試類的功能,不能僅滿足于代碼能無錯運行或被測試的類能提供的功能正確,應(yīng)以所做的OOD結(jié)果為依據(jù),檢測類提供的功能是否滿足了設(shè)計的要求,是否有缺陷。 取決于單元的構(gòu)成;四層:以單個操作或方法為單元:操作/方法測試:單元測試;類測試:
20、類內(nèi)的測試;集成測試:類間測試;系統(tǒng)測試:端口事件層上測試;三層:以類為單元面向?qū)ο鬁y試層次datedaymonthyear類聚合例1:NextDate面向?qū)ο蟮膶崿F(xiàn)testItDateDay dMonth mYear yDate(pDay,pMonth,pYear)Increment()printDate()CalendarUnit abstract classcurrentPos As IntegerCalendarUnit(pCurrentPos)setCurrentPos(pCurrentPos)Increment() booleanDayMonth mDay(pDay,Month,p
21、Month)setCurrentPos(pCurrentPos)getDay()Increment()YearYear(int pYear)setCurrentPos(pCurrentPos)getYear()Incrment()isLeap() booleanMonthprivate Year yprivate sizeIndex=Month(pcur,Year pYear)setCurrentPos(pCurrentPos)setMonth(pcur,Year pYear)getMonth()getMonthSize()Increment()O-oCalendar 中的類例2:貨幣轉(zhuǎn)換應(yīng)用
22、程序美圓金額等價于巴西加拿大歐共體日本計算清除退出貨幣轉(zhuǎn)換程序是事件驅(qū)動的程序,強調(diào)與GUI關(guān)聯(lián)的代碼。將美元轉(zhuǎn)換為任意四種貨幣,貨幣選擇由單選按鈕控制,相互排斥。計算按鈕將美元金額轉(zhuǎn)換為所選貨幣的等量金額清除按鈕重新設(shè)置貨幣選擇、美元金額、等量貨幣金額、相關(guān)標(biāo)簽。退出按鈕結(jié)束該應(yīng)用程序。輸入事件輸出事件ip1ip2ip2.1ip2.2ip2.3ip2.4ip3ip4ip5ip6輸入美元金額按下國家按鈕按下巴西按下加拿大按下歐共體按下日本按下計算按鈕按下清除按鈕按下退出按鈕在錯誤消息中按下OKop1op2op2.5op3op4op5op6op7op8op9op10顯示美元金額顯示貨幣名稱顯示省
23、略號指示所選國家重新設(shè)置所選國家顯示外幣值錯誤消息:必須選擇國家錯誤消息:必須輸入美元金額錯誤消息:必須選擇國家輸入美元金額重新設(shè)置美元金額重新設(shè)置等價貨幣金額貨幣轉(zhuǎn)換程序的輸入和輸出事件Ip3/op8Ip6空閑遺漏國家和美圓消息國家已選擇遺漏美圓信息兩種輸入已完成美圓金額已輸入遺漏國家消息已顯示等價金額Ip4 or ip5Ip2/op2,op3Ip3/op7Ip6Ip4 or ip 5 Op2.5,op4 op9,and op 10Ip1/op1Ip3/op5Ip2/op2,op3Ip1/op1Ip6Ip3/op6圖16-7 高層有限狀態(tài)機沒有顯示在每個狀態(tài)會發(fā)生的所有事件,按下清除和退出按
24、鈕,可以在任何狀態(tài)中發(fā)生。空閑巴西歐共體加拿大日本Ip2.1Op2.1Op3.1Ip2.2Op2.2Op3.2Ip2.3Op2.3Op3.3Op4.1Ip2.4Op2.4Op3.4Ip2.3Op2.3Op3.3Ip2.1Op2.1Op3.1Op4.3Ip2.2Op2.2Op3.2Op4.1Ip2.1Op2.1Op3.1Op4.2Ip2.3Op2.3Op3.3Op4.4Ip2.4Op2.4Op3.4Op4.3Ip2.4Op2.4Op3.4Op4.2Ip2.2Op2.2Op3.2Op4.4圖16-8 選擇國家狀態(tài)詳細(xì)視圖在存儲器中空閑遺漏國家和美圓消息國家已選擇遺漏美圓信息兩種輸入已完成美圓金額已
25、輸入遺漏國家消息已顯示等價金額Ip4Ip2/op2,op3Ip3/op8Ip6Ip3/op7Ip6Ip1/op1Ip2/op2,op3Ip3/op5Ip1/op1Ip3/op6Ip6Ip2/op2,op3Ip1/op1Ip5結(jié)束貨幣轉(zhuǎn)換應(yīng)用程序狀態(tài)圖執(zhí)行退出清除狀態(tài)轉(zhuǎn)移圖的面向?qū)ο筌浖y試面向?qū)ο笤O(shè)計方法通常采用狀態(tài)轉(zhuǎn)移圖建立對象的動態(tài)行為模型。狀態(tài)轉(zhuǎn)移圖用于刻畫對象響應(yīng)各種事件時狀態(tài)發(fā)生轉(zhuǎn)移的情況,圖中結(jié)點表示對象的某個可能狀態(tài),結(jié)點之間的有向邊通常用“事件/動作”標(biāo)出。基于狀態(tài)的測試是通過檢查對象的狀態(tài)在執(zhí)行某個方法后是否會轉(zhuǎn)移到預(yù)期狀態(tài)的一種測試技術(shù)。使用該技術(shù)能夠檢驗類中的方法是否能正
26、確地交互。 因為對象的狀態(tài)是通過對象數(shù)據(jù)成員的值反映出來,所以檢查對象的狀態(tài)實際上就是跟蹤監(jiān)視對象數(shù)據(jù)成員的值的變化。如果某個方法執(zhí)行后對象的狀態(tài)未能按預(yù)期的方式改變,則說明該方法含有錯誤。6.4 面向?qū)ο蟮膯卧獪y試面向?qū)ο鬁y試的單元定義可以編譯執(zhí)行的最小軟件組件;(和傳統(tǒng)測試一樣,但放棄了封裝的特點)由一個設(shè)計人員開發(fā)的軟件組件;只包含單一操作或方法的類或子類。(設(shè)計用例方便,使集成測試目標(biāo)清晰)以方法為單元還是以類為單元,根據(jù)具體環(huán)境確定最適合的方法。“操作”是指類函數(shù)定義,“方法”指其實現(xiàn)。面向?qū)ο蟮膯卧獪y試-以方法為單元傳統(tǒng)的單元測試是針對程序的函數(shù)、過程或完成某一特定功能的程序塊。單
27、獨的看待類的成員函數(shù),與面向過程程序中的函數(shù)或過程沒有本質(zhì)的區(qū)別,傳統(tǒng)的測試方法在面向?qū)ο髥卧獪y試中都可使用,如等價類劃分法、因果圖法、邊值分析法、邏輯覆蓋法、路徑分析法等等。面向?qū)ο缶幊痰奶匦允沟脤Τ蓡T函數(shù)的測試又不完全等同于傳統(tǒng)的函數(shù)或過程測試。不再孤立地測試單個操作,而是將操作作為類的一部分。尤其是繼承特性和多態(tài)特性,使子類繼承或重載的父類成員函數(shù)出現(xiàn)了傳統(tǒng)測試中未遇見的問題。考慮如下兩個問題:(1)繼承的成員函數(shù)是否都不需要測試?(2)對父類的測試是否能照搬到子類?面向?qū)ο蟮膯卧獪y試(續(xù))繼承的成員函數(shù)是否都不需要測試? 對父類中已經(jīng)測試過的成員函數(shù),以下兩種情況需要在子類中重新測試:
28、 a)繼承的成員函數(shù)在子類中做了改動; b)成員函數(shù)調(diào)用了改動過的成員函數(shù)的部分。例:假設(shè)存在父類Base有Inherited()和Redefined()這兩個成員函數(shù),繼承父類Base的子類Derived只對Redefined() 做了改動。那么,Derived:Redefined()就需要重新測試;對于Derived:Inherited(),若它包含了調(diào)用Redefined()的語句 (比如:x=x/Redefined()),就需要重新測試,否則就不需要。面向?qū)ο蟮膯卧獪y試(續(xù))對父類的測試是否能照搬到子類? 引用前面的假設(shè),成員函數(shù)Base:Redefined()和Derived:Red
29、efined()已經(jīng)是不同的。那么,按理應(yīng)該要對Derived:Redefined()重新測試分析,設(shè)計測試用例。但是由于面向?qū)ο蟮睦^承使得兩個函數(shù)相似,故只需要在對Base:Redefined()的測試要求和測試用例上添加對Derived:Redefined()新的測試要求和增補相應(yīng)測試用例。例 Base:Redefined()含有如下語句: If (value0) message(“l(fā)ess”); else if (value=0) message(“equal”); else message(“more”); 面向?qū)ο蟮膯卧獪y試(續(xù))例(續(xù)) 在Derived:Redefined()中定
30、義為: If (value0) message(“l(fā)ess”); else if (value=0) message(“It is equal”); else message(“more”); if (value=88) message(“l(fā)uck”); 在原有對父類Base的測試上,對Derived:Redefined()的測試只需作如下改動:將value=0的測試結(jié)果期望改動;增加value=88的測試。 設(shè)計測試用例需要能夠?qū)嵗摹皹丁鳖惡推痱?qū)動器作用的“主程序”類;方法一般比較簡單,復(fù)雜度較低;創(chuàng)建樁工作量較大;測試工作主要集中在集成測試:類內(nèi)和類間; 例:o-oCalendar的偽
31、代碼:CalendarUnit類:兩個操作(設(shè)置取值和標(biāo)志)Testlt類(測試驅(qū)動器)Date類(獲取日期,計算下一日期并打印日期)Day類(設(shè)置/獲取日期)Month 類(設(shè)置/獲取月份及天數(shù))Year類(設(shè)置/獲取年份及閏年判別)Testlt類和Date類123testIt4567Date.constructor891011121314151617181920Date.incrementDate.printDateDay類212223Day.constructorabDay.setCurrentPos232425Day.setDay2627Day.getDay282930313233Da
32、y.increment394041Month.constructorabMonth.setCurrentPos363738Month.setMonth3940Month.getMonth474849505152Month.increment414246434445Month.getMonthSizeMonth類的程序圖類:CalendarUnit class CalendarUnit abstract class currentPos As Integer CalendarUnit(pCurrnetPos) currentPos = pCurrnetPos End CalendarUnita.
33、 setCurrentPos(pCurrnetPos)b. currentPos = pCurrnetPos End setCurrentPos abstract protected boolean increment()類:testlt class testlt main()1. Date testdate(testMonth,testDay,testYear)2. testdate.increment()3. testdate.printDate() End testlt類:Date class Date private Day d private Month m private Year
34、 y4. Date(pMonth,pDay,pYear)5. Year y(pYear)6. Month m(pMonth,y)7. Day d(pDay,m) End Date constructor19.printDate()20. Output(m.getMonth()+”/”+d.getDay()+”/”+y.getYear() End printDate8. increment()9. if (NOT(d.increment()10.Then11. if(NOT(m.increment()12. Then13. y.increment()14. m.setMonth(1,y) d.s
35、etDay(1,m)15. Else16. d.setDay(1,m)17. Endif18.Endif End increment類:Day class Day is A CalendarUnit private Month m21. Day(pDay,Month pMonth)22. setDay(pDay,pMonth) End Day constructor23. setDay(pDay, pMonth)24. setCurrentPos(pDay)25. m = pMonth End setDay26. getDay()27. return currentPos End getDay
36、28. boolean increment()29. currentPos = currentPos+130. if(currentPos=m.getMonthSize()31. Then return true32. Else return false33. Endif End increment類:Month class Month is A CalendarUnit private Year y private sizeIndex=34.Month(pcur,Year pYear)35. setMonth(pcur,Year pYear) End Month constructor36.
37、setMonth(pcur,Year pYear)37. setCurrentPos(pcur)38. y=pYear End setMonth39.getMonth()40. return currentPos End getMonth41.getMonthSize()42. if(y.isleap()43. Then sizeIndex1=2944. Else sizeIndex1=2845. Endif46. return sizeIndexcurrentPos-1 End getMonthSize47.boolean increment()48. currentPos=currentP
38、os+149. if(currentPos12)50. Then return fasle51. Else return true52. Endif End increment類:Year class Year is A CalendarUnit53. Year(pYear)54. setCurrentPos(pYear) End Year constructor55. getYear()56. return currentPos End getYear57. boolean increment()58. currentPos = currentPos+159. return true End
39、 increment60. boolean isleap()61. if(currentPos MOD 4=0)AND NOT(currentPos MOD 100=0)OR(currentPos MOD 400=0)62. Then return true63. Else return false64. Endif End isleapDate.increment的單元測試三個等價類:D1=日期:1=日期月的最后日期D2=日期:日期是非12月的最后日期D3=日期:日期是12月31日 可以解決類內(nèi)集成問題;主要問題是類的繼承性、抽象類等問題;靜態(tài)視圖繼承被忽略,扁平化的類可以解決;不能測試抽象
40、類;以類為單元在沒有類的繼承性,只有內(nèi)部的復(fù)雜性時最有意義面向?qū)ο蟮膯卧獪y試-以類為單元類的功能性和結(jié)構(gòu)性測試對面向?qū)ο筌浖念悳y試相當(dāng)于傳統(tǒng)軟件中的單元測試。 類的測試用例可以先根據(jù)其中的方法設(shè)計,然后擴展到方法之間的調(diào)用關(guān)系。類測試一般也采用傳統(tǒng)的兩種測試方式:功能性測試和結(jié)構(gòu)性測試,即黑盒測試和白盒測試。功能性測試以類的規(guī)格說明為基礎(chǔ),主要檢查類是否符合其規(guī)格說明的要求。功能性測試包括兩個層次:類的規(guī)格說明和方法的規(guī)格說明。結(jié)構(gòu)性測試則是從程序出發(fā),對類中方法進行測試,需要考慮其中的代碼是否正確。測試分為兩層:第一層考慮類中各獨立方法的代碼,即方法要做單獨測試;第二層考慮方法之間的相互作
41、用,即方法需要進行綜合測試。例:擋風(fēng)玻璃雨刷(三個類合并為一個類)class windshieldWiper private wiperSpeed;leverPosition;dialPosition windshieldWiper(wiperSpeed,leverPosition,dialPosition) getWiperSpeed() setWiperSpeed() getLeverPosition() setLeverPosition() getDialPosition() setDialPosition() senseLeverUp() senseLeverDown() senseD
42、ialUp() senseDialDown()End class windshieldWiper斷電加電關(guān)間歇低速高速123046123060leverdownleverupleverdownleverdownleverupleverupdialDowndialDowndialUpdialUpInstate(Int)Instate(off)Instate(1)Instate(2)Instate(3)Instate(low)Instate(High)Instate(Int)Instate(low)Instate(1)Instate(2)windshieldWiper類的狀態(tài)圖senseLever
43、Up() Case leverPosition Of Case 1:Off leverPosition=Int Case dialPosition Of Case 1:1 wiperSpeed=4 Case 2:2 wiperSpeed=6 Case 3:3 wiperSpeed=12 EndCase dialPosition Case 2:Int leverPosition=Low wiperSpeed=30 Case 3:Low leverPosition=High wiperSpeed=60 Case 4:High (impossible;error condition) EndCase
44、 leverPosition windshieldWiper類的單元測試采用由下往上的測試;senseLeverUp/ senseLeverDown/DialUp/DialDown的測試測試windshieldWiper類的其他部分測試驅(qū)動器類的偽代碼:class testSenseLeverUp wiperSpeed leverPos dialPos testResult booleanmain() windshieldWiper testCase(0,Off,1) testCase.senseLeverUp() leverPos= testCase.getLeverPosition() i
45、f leverPos=Int Then testResult=Pass Else testResult=Fail EndifEnd mainclass testWindshieldWiper wiperSpeed leverPos dialPos testResult booleanmain() windshieldWiper testCase(0,Off,1) testCase.senseLeverUp() wiperSpeed = testCase.getWiperSpeed() if wiperSpeed=4 Then testResult=Pass Else testResult=Fa
46、il EndifEnd main基于類行為圖定義測試覆蓋指標(biāo):每個事件的覆蓋組件中每個狀態(tài)的覆蓋;組件中每個轉(zhuǎn)移的覆蓋;所有交互狀態(tài)覆蓋;客戶定義用例場景;測試用例前提windshieldWiper事件(方法)預(yù)期leverPos的輸出值123456windshieldWiper(0,Off,1)windshieldWiper(0,Int,1) windshieldWiper(0,Low,1)windshieldWiper(0,High,1)windshieldWiper(0,Low,1)windshieldWiper(0,Int,1)senseLeverUp()senseLeverUp()s
47、enseLeverUp()senseLeverDown()senseLeverDown()senseLeverDown()“間歇”“低速”“高速”“低速”“間歇”“關(guān)”控制桿組件每個狀態(tài)/轉(zhuǎn)移覆蓋層次的測試用例:場景覆蓋準(zhǔn)則與系統(tǒng)級測試幾乎相同,場景:UC1正常用法描述前提擋風(fēng)玻璃雨刷在“關(guān)”位置,“刻度盤”在位置1;用戶將控制桿推到“間歇”,然后將刻度盤從位置2轉(zhuǎn)到位置3;然后將控制桿推到“低速”;用戶將控制桿推到“間歇”,然后推到“關(guān)”擋風(fēng)玻璃雨刷在“關(guān)”位置,“刻度盤”在位置1,雨刷速度為0事件序列用戶行動系統(tǒng)應(yīng)答123456將控制桿推到“間歇”將刻度盤轉(zhuǎn)到2將刻度盤轉(zhuǎn)到3將控制桿推到“
48、低速”將控制桿推到“間歇”將控制桿推到“關(guān)”雨刷速度為4雨刷速度為6雨刷速度為12雨刷速度為30雨刷速度為12雨刷速度為0測試用例:class testScenario wiperSpeed leverPos dialPos step1OK boolean step2OK boolean step3OK boolean step4OK boolean step5OK boolean step6OK booleanmain() windshieldWiper testCase(0,Off,1) testCase.senseLeverUp() wiperSpeed= testCase.getWip
49、erSpeed() if wiperSpeed = 4 Then step1OK = Pass Else step1OK = Fail EndiftestCase.senseDialUp()wiperSpeed= testCase.getWiperSpeed()if wiperSpeed = 6 Then step2OK = Pass Else step2OK = FailEndiftestCase.senseDialUp()wiperSpeed= testCase.getWiperSpeed()if wiperSpeed = 12 Then step3OK = Pass Else step3
50、OK = FailEndiftestCase.senseLeverUp()wiperSpeed= testCase.getWiperSpeed()if wiperSpeed = 30 Then step4OK = Pass Else step4OK = FailEndif測試程序:testCase.senseLeverDown()wiperSpeed= testCase.getWiperSpeed()if wiperSpeed = 12 Then step5OK = Pass Else step2OK = FailEndiftestCase.senseLeverDown()wiperSpeed
51、= testCase.getWiperSpeed()if wiperSpeed = 0 Then step6OK = Pass Else step6OK = FailEndif6.5 面向?qū)ο蟮募蓽y試因為面向?qū)ο筌浖]有層次的控制結(jié)構(gòu),傳統(tǒng)的自頂向下和自底向上的集成策略是沒有意義的,類之間的相互依賴及其緊密,使其根本無法在編譯不完全的程序上對類進行測試。因此,面向?qū)ο蠹蓽y試通常需要在整個程序編譯完成后進行。此外,面向?qū)ο蟪绦蚓哂袆討B(tài)特性,程序的控制流往往無法確定,所以也只能對整個編譯后的程序做基于黑盒的集成測試。面向?qū)ο蟮募蓽y試能夠檢測出相對獨立的單元測試無法檢測出的那些類相互作用時才會
52、產(chǎn)生的錯誤。單元測試可以保證成員函數(shù)行為的正確性,集成測試則只關(guān)注于系統(tǒng)的結(jié)構(gòu)和內(nèi)部的相互作用。面向?qū)ο蟮募蓽y試(續(xù))面向?qū)ο蠹蓽y試可以分成兩步進行:先進行靜態(tài)測試,再進行動態(tài)測試。測試較為復(fù)雜。靜態(tài)測試主要針對程序結(jié)構(gòu)進行,檢測程序結(jié)構(gòu)是否符合設(shè)計要求。現(xiàn)在常用的一些測試軟件都能提供一種稱為 “可逆性工程”的功能,即通過源程序得到類關(guān)系圖和函數(shù)功能調(diào)用關(guān)系圖。將“可逆性工程”得到的結(jié)果與OOD的結(jié)果相比較,以檢測OOP是否達(dá)到了設(shè)計要求。動態(tài)測試則測試與每個動態(tài)語境有關(guān)的消息。設(shè)計測試用例時,通常需要上述的功能調(diào)用關(guān)系圖、類關(guān)系圖或?qū)嶓w關(guān)系圖為參考,確定不需要被重復(fù)測試的部分,從而優(yōu)化測
53、試用例,使得進行的測試能夠達(dá)到一定覆蓋標(biāo)準(zhǔn)。一、集成測試的UML支持以方法為單元的集成測試通常需要進行兩級集成:一是將成員函數(shù)集成到完整類中;二是將類與其它類集成。這里討論以類為單元的方法-更常見;以類為單元的測試完成后需要恢復(fù)被扁平化的類。UML協(xié)同圖和序列圖是集成測試的基礎(chǔ)。 UML在系統(tǒng)層描述類定義和類組成。UML協(xié)同圖顯示類間信息傳輸,支持成對集成和相鄰集成。例:o-oCalendar協(xié)同圖(類似單元調(diào)用圖)。testItDateYearMonthDay1:Create2:increment3:getYear1:Create2:increment3:printDate1:Create2
54、:increment3:setMonth4:getMonth1:Create2:increment3:setDay4:getDay1:isLeap1:getMonthSize圖18-1 o-oCalendar 的協(xié)同圖根據(jù)協(xié)同圖,可以得到一些要集成的類對:testIt和Date,為Year、Month和Day建立樁。以協(xié)同圖為基礎(chǔ)的面向?qū)ο蠹蓽y試的缺點是UML描述類行為的狀態(tài)圖很難合并,使較高層次的測試?yán)щy。類的相鄰集成會降低樁工作量,但缺陷隔離困難,測試用例失敗,則必須在更多的類中尋找缺陷。序列圖以時間先后表示類的操作即類的時間路徑。箭頭標(biāo)號表示類按時間順序發(fā)送的消息。例: o-oCale
55、ndar的printDate序列圖。testItDate:testdateDay:dMonth:mYear:y時間1:printDate()2:getMonth()3:getDay()4:getYear()圖18-2 printDate的序列圖測試偽代碼:testDriver m.setMonth(1) d.setDay(15) y.setYear(2002) Output(“expected value is 1/15/2002”) Output(“actual output is”) testdate.printDate()End testDriver面向?qū)ο筌浖腗M-路徑是由消息連接起
56、來的方法執(zhí)行序列。原子系統(tǒng)功能(ASF):從端口輸入事件開始到端口輸出事件結(jié)束的MM-路徑。ASF測試是集成測試和系統(tǒng)測試的交叉點,可在兩個層次上測試ASF。例: o-oCalendar偽代碼 消息圖(圖18-3) 二、面向?qū)ο筌浖腗M-路徑testitMainDateDate()Increment()printDate()DayDay()setCurrentPos()increment()setDay()getDay()MonthMonth()setCurrentPos()increment()setMonth()getMonth YearYear()setCurrentPos()incr
57、ement()getYear()isLeap()m1m2m3m6m5m4m7m11m8m9getMonthSize()m13m10m14m15m16m17m20m18m19m21圖18-3 o-oCalendar中的消息m12比協(xié)同圖更詳細(xì)。顯示了每個消息的源方法和目的方法,而不只是類。實例化(2002年1月15日)Date的部分MM-路徑偽代碼和路徑圖實例化(2002年4月30日)Date并計算第二天的部分MM-路徑偽代碼和路徑圖基于MM-路徑有向圖分析選擇o-oCalendar的集成測試用例最低限度需要覆蓋所有消息的MM-路徑集;13個基于決策表的功能測試用例構(gòu)成了透徹的集成測試用例集合。
58、可以尋找MM-路徑,確保所有消息被遍歷。測試用例MonthDayYear預(yù)期輸出Tes6/2001Test463020041/7/2004Test56312001不可能Test69116200417/1/2004Test1013120011/2/2001Test11141216200417/12/2004Tes1/2002Test16216200417/2/2004Tes2/2004Test1822820011/3/2001Test1922920041/3/2004Test202292001不可能Test212223
59、02004不可能13個基于決策表的功能測試用例testitMainDateDate()Increment()printDate()DayDay()setCurrentPos()increment()setDay()getDay()MonthMonth()setCurrentPos()increment()setMonth()getMonth YearYear()setCurrentPos()increment()getYear()isLeap()m1m6m5getMonthSize()m15m16m18m19m21圖18-4 實例化Date(2002年1月15日)的MM-路徑m4testitM
60、ainDateDate()Increment()printDate()DayDay()setCurrentPos()increment()setDay()getDay()MonthMonth()setCurrentPos()increment()setMonth()getMonth YearYear()setCurrentPos()increment()getYear()isLeap()m2m11m8getMonthSize()m7m17m20圖18-5 Date.increment (2002年4月30日)的MM-路徑6.6 面向?qū)ο蟮南到y(tǒng)測試 通過單元測試和集成測試,僅能保證軟件開發(fā)的功能
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 2024項目管理考試輔導(dǎo)材料試題及答案
- 廣告策劃中的危機公關(guān)處理考核試卷
- 財務(wù)數(shù)據(jù)解讀與應(yīng)用試題及答案
- 陜西排水帶施工方案
- 針對新形勢的注冊會計師考試變革探討試題及答案
- 2024項目管理專業(yè)知識考題試題及答案
- 2024年項目成功的關(guān)鍵因素與應(yīng)對方案試題及答案
- 打井前施工方案怎么寫
- 項目管理專業(yè)人士資格考試的備考經(jīng)驗試題及答案
- 電視機語音助手與智能交互技術(shù)考核試卷
- 婚育情況登記表
- INVOICE-商業(yè)發(fā)票樣本格式
- 圓周率1000000位 完整版
- DB33-1036-2021《公共建筑節(jié)能設(shè)計標(biāo)準(zhǔn)》
- 巖芯鑒定手冊
- 快速排序算法高校試講PPT
- 甘肅歷史與甘肅文化
- 工程勘察設(shè)計收費標(biāo)準(zhǔn)
- 高邊坡施工危險源辨識及分析
- 江蘇工業(yè)企業(yè)較大以上風(fēng)險目錄
- 監(jiān)理質(zhì)量評估報告(主體分部)
評論
0/150
提交評論