精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

ZOMBIES:在軟件開發中定義邊界和接口(三)

開發
喪尸是沒有邊界感的,需要為你的軟件設定限制和期望。

喪尸沒有邊界感。它們踩倒柵欄,推倒圍墻,進入不屬于它們的地盤。在前面的文章中,我已經解釋了為什么把所有編程問題當作一群喪尸一次性處理是錯誤的。

ZOMBIES 代表首字母縮寫:

  • Z – 最簡場景(Zero)
  • O – 單個元素場景(One)
  • M – 多個元素場景(Many or more complex)
  • B – 邊界行為(Boundary behaviors)
  • I – 接口定義(Interface definition)
  • E – 處理特殊行為(Exercise exceptional behavior)
  • S – 簡單場景用簡單的解決方案(Simple scenarios, simple solutions)

在本系列的前面兩篇文章中,我演示了 ZOMBIES 方法的前三部分:最簡場景、單元素場景和多元素場景。第一篇文章 實現了最簡場景,它提供了代碼中的最簡可行路徑。第二篇文章中針對單元素場景和多元素場景 運行測試。在這篇文章中,我將帶你了解邊界和接口。

回到單元素場景

要想處理邊界,你需要繞回來(迭代)。

首先思考下面的問題:電子商務的邊界是什么?我需要限制購物框的大小嗎?(事實上,我不認為這有任何意義。)

目前唯一合理的邊界條件是確保購物框里的商品數量不能為負數。將這個限制表示成可運行的期望:

[Fact]
public void Add1ItemRemoveItemRemoveAgainHas0Items() {
        var expectedNoOfItems = 0;
        var actualNoOfItems = -1;
        Assert.Equal(expectedNoOfItems, actualNoOfItems);
}

這就是說,如果你向購物框里添加一件商品,然后將這個商品移除兩次,shoppingAPI 的實例應該告訴你購物框里有零個商品。

當然這個可運行期望(微測試)不出意料地會失敗。想要這個微測試能夠通過,最小改動是什么呢?

[Fact]
public void Add1ItemRemoveItemRemoveAgainHas0Items() {
        var expectedNoOfItems = 0;
        Hashtable item = new Hashtable();
        shoppingAPI.AddItem(item);
        shoppingAPI.RemoveItem(item);
        var actualNoOfItems = shoppingAPI.RemoveItem(item);
        Assert.Equal(expectedNoOfItems, actualNoOfItems);
}

這個期望測試依賴于 RemoveItem(item) 功能。目前的 shippingAPI 還不具備該功能,你需要增加該功能。

回到 app 文件夾,打開 IShippingAPI.cs 文件,新增以下聲明:

int RemoveItem(Hashtable item);

到 ShippingAPI.cs 中實現該功能:

public int RemoveItem(Hashtable item) {
        basket.RemoveAt(basket.IndexOf(item));
        return basket.Count;
}

運行,然后你會得到如下錯誤:

Error

Error

系統在移除一個不在購物框的商品,這導致了系統崩潰。加一點點 防御式編程defensive programming:

public int RemoveItem(Hashtable item) {
        if(basket.IndexOf(item) >= 0) {
                basket.RemoveAt(basket.IndexOf(item));
        }
        return basket.Count;
}

在移除商品之前先檢查它是否在購物框中。(你可能試過用捕獲異常的方式來處理,但是我認為上面的處理方式更具可讀性。)

更多具體的期望

在講更多具體的期望之前,讓我們先探討一下什么是接口。在軟件工程中,接口表示一種規范,或者對能力的描述。從某種程度上來說,接口類似于菜譜。它羅列出了制作蛋糕的原材料,但它本身并不能吃。我們只是按照菜譜上的說明來烤蛋糕。

與此類似,我們首先通過說明這個服務能做什么的方式來定義我們的服務。這個描述說明就是所謂的接口。但是接口本身并不能向我們提供任何功能。它只是指導我們實現指定功能的藍圖而已。

到目前為止,我們已經實現了接口(只是某部分實現了,稍后還會增加新功能)和業務處理邊界(也就是購物框里的商品不能是負數)。你指導了 shoppingAPI 怎么向購物框添加商品,并通過 Add2ItemsBasketHas2Items 測試驗證了該功能的有效性。

然而僅僅具備向購物框添加商品的功能還不足以使其成為一個網購應用程序。它還需要能夠計算購物框里的商品的總價。現在需要增加另一個期望。

按照慣例,從最直接明了的期望開始。當你向購物框里加入一件價值 ¥10 的商品時,你希望這個購物 API 能正確地計算出總價為 ¥10。

第五個測試(偽造版)如下:

[Fact]
public void Add1ItemPrice10GrandTotal10() {
        var expectedTotal = 10.00;
        var actualTotal = 0.00;
        Assert.Equal(expectedTotal, actualTotal);
}

還是一樣的老把戲,通過硬編碼一個錯誤的值讓 Add1ItemPrice10GrandTotal10 測試失敗。當然前三個測試成功通過,但第四個新增的測試失敗了:

A total of 1 test files matched the specified pattern.
[xUnit.net 00:00:00.57] tests.UnitTest1.Add1ItemPrice10GrandTotal10 [FAIL]
  X tests.UnitTest1.Add1ItemPrice10GrandTotal10 [4ms]
  Error Message:
   Assert.Equal() Failure
Expected: 10
Actual: 0

Test Run Failed.
Total tests: 4
     Passed: 3
         Failed: 1
 Total time: 1.0320 Seconds

將硬編碼值換成實際的處理代碼。首先,檢查接口是否具備計算訂單總價的功能。根本沒有這種東西。目前為止接口中只聲明了三個功能:

  1. int NoOfItems();
  2. int AddItem(Hashtable item);
  3. int RemoveItem(Hashtable item);

它們都不具備計算總價的能力。所以需要聲明一個新功能:

double CalculateGrandTotal();

這個新功能應該讓 shoppingAPI 具備計算總價的能力。這是通過遍歷購物框中的商品并把它們的價格累加起來實現的。

修改第五個測試:

[Fact]
public void Add1ItemPrice10GrandTotal10() {
        var expectedGrandTotal = 10.00;
        Hashtable item = new Hashtable();
        item.Add("00000001", 10.00);
        shoppingAPI.AddItem(item);
        var actualGrandTotal = shoppingAPI.CalculateGrandTotal();
        Assert.Equal(expectedGrandTotal, actualGrandTotal);
}

這個測試表明了這樣的期望:如果向購物框里加入一件價格 ¥10 的商品,然后調用 CalculateGrandTotal() 方法,它會返回商品總價 ¥10。這是一個完全合理的期望,它完全符合商品總價計算的邏輯。

那么怎么實現這個功能呢?就像以前一樣,先寫一個假的實現。回到 ShippingAPI 類中,實現在接口中聲明的 CalculateGrandTotal() 方法:

public double CalculateGrandTotal() {
                return 0.00;
}

現在先將返回值硬編碼為 0.00,只是為了檢驗這個測試能否正常運行,并確認它是能夠失敗的。事實上,它能夠運行,并且如預期一樣失敗。接下來的工作就是正確實現計算商品總價的處理邏輯:

public double CalculateGrandTotal() {
        double grandTotal = 0.00;
        foreach(var product in basket) {
                Hashtable item = product as Hashtable;
                foreach(var value in item.Values) {
                        grandTotal += Double.Parse(value.ToString());
                }
        }
        return grandTotal;
}

運行,五個測試全部通過!

從單元素場景到多元素場景

現在是時候進入下一輪迭代了。你已經通過處理最簡場景、單元素場景和邊界場景迭代地構建了系統,現在需要處理稍復雜的多元素場景了。

快捷提示:由于我們一直在針對單個元素場景、多元素場景和邊界行為這三點上對軟件進行迭代改進,一些讀者可能會認為我們同樣應該對接口進行改進。我們稍后就會發現,接口已經完全滿足需要了,目前沒有新增功能的必要。請記住,應該保持接口的簡潔。(盲目地)擴增接口不會帶來任何好處,只會引入噪音。我們要遵循 奧卡姆剃刀Occam's Razor 原則:如無必要,勿增實體。 現在我們已經基本完成了接口功能描述的工作,是時候改進實現了。

通過上一輪的迭代,系統已經能夠處理購物框里有超過一件商品的情況了。現在我么來讓系統具備購物框里有超過一件商品時計算總價的能力。首先寫可執行期望:

[Fact]
public void Add2ItemsGrandTotal30() {
        var expectedGrandTotal = 30.00;
        var actualGrandTotal = 0.00;
        Assert.Equal(expectedGrandTotal, actualGrandTotal);
}

硬編碼所有值,盡量讓期望測試失敗。

測試確實失敗了,現在得想辦法讓它通過。向購物框添加兩件商品,然后調用 CalculateGrandTotal() 方法:

[Fact]
public void Add2ItemsGrandTotal30() {
	      var expectedGrandTotal = 30.00;
        Hashtable item = new Hashtable();
        item.Add("00000001", 10.00);
        shoppingAPI.AddItem(item);
        Hashtable item2 = new Hashtable();
        item2.Add("00000002", 20.00);
        shoppingAPI.AddItem(item2);
        var actualGrandTotal = shoppingAPI.CalculateGrandTotal();
        Assert.Equal(expectedGrandTotal, actualGrandTotal);
}

測試通過。現在共有六個可以通過的微測試,系統回到了穩態。

設定期望

作為一個認真負責的工程師,你希望確保當用戶向購物框添加一些商品然后又移除一些商品后系統仍然能夠計算出正確出總價。下面是這個新的期望:

[Fact]
public void Add2ItemsRemoveFirstItemGrandTotal200() {
        var expectedGrandTotal = 200.00;
        var actualGrandTotal = 0.00;
        Assert.Equal(expectedGrandTotal, actualGrandTotal);
}

這個期望表示將兩件商品加入到購物框,然后移除第一件后期望的總價是 ¥200。硬編碼行為失敗了。現在設計更具體的正面測試樣例,然后運行代碼:

[Fact]
public void Add2ItemsRemoveFirstItemGrandTotal200() {
        var expectedGrandTotal = 200.00;
        Hashtable item = new Hashtable();
        item.Add("00000001", 100.00);
        shoppingAPI.AddItem(item);
        Hashtable item2 = new Hashtable();
        item2.Add("00000002", 200.00);
        shoppingAPI.AddItem(item2);
        shoppingAPI.RemoveItem(item);
        var actualGrandTotal = shoppingAPI.CalculateGrandTotal();
        Assert.Equal(expectedGrandTotal, actualGrandTotal);
}

在這個正面測試樣例中,先向購物框加入第一件商品(編號為 00000001,價格為 ¥100),再加入第二件商品(編號為 00000002,價格為 ¥200)。然后將第一件商品移除,計算總價,比較計算值與期望值是否相等。

運行期望測試,系統正確地計算出了總價,滿足這個期望測試。現在有七個能順利通過的測試了。系統運行良好,無異常!

Test Run Successful.
Total tests: 7
     Passed: 7
 Total time: 0.9544 Seconds

敬請期待

現在你已經學習了 ZOMBIES 方法中的 ZOMBI 部分,下一篇文章將介紹處理特殊行為。到那個時候,你可以試試自己的測試!

責任編輯:龐桂玉 來源: Linux中國
相關推薦

2023-05-16 17:34:49

ZOMBIES軟件開發

2023-05-30 18:26:49

ZOMBIES軟件開發

2023-05-13 17:38:03

ZOMBIES軟件開發

2010-03-24 14:37:29

Python編程語言

2024-04-02 06:03:00

GenAI軟件開發人工智能

2023-08-01 15:24:18

DevOps自動化軟件開發

2024-05-20 12:47:03

AI軟件開發

2009-06-12 11:35:28

模式框架軟件設計

2023-06-08 16:47:09

軟件開發工具

2023-02-09 16:48:12

軟件開發測試結對測試

2024-07-23 08:06:19

緩存技術策略

2024-03-14 06:51:22

GenAI人工智能

2021-12-14 09:00:00

IT開發運營

2020-03-31 10:08:15

零信任安全軟件

2023-06-09 19:01:03

軟件開發

2011-07-04 17:09:54

2011-08-11 09:56:50

模式

2020-10-16 10:21:23

大數據開發軟件開發技術

2014-03-21 09:30:26

軟件開發碼農

2017-03-17 08:15:17

敏捷軟件開發軟件開發
點贊
收藏

51CTO技術棧公眾號

日韩在线观看www| 中文字幕亚洲精品在线| 日韩免费大片| 亚洲一区二区三区四区的| 久久久久成人精品免费播放动漫| 无码人妻aⅴ一区二区三区69岛| 91禁在线看| 国产喂奶挤奶一区二区三区| 91九色单男在线观看| 九九热免费在线| av动漫精品一区二区| 色综合中文综合网| 奇米777四色影视在线看| 精品国产无码一区二区| 亚洲欧美日韩精品一区二区| 久久久国产影院| 久久精品影视大全| brazzers在线观看| 最新国产成人在线观看| 91在线看www| 无码免费一区二区三区| 欧美日韩激情| 亚洲国语精品自产拍在线观看| 久久久久久久久久久视频| 日韩欧美亚洲系列| 国产福利一区二区| 国产精选久久久久久| 黄色片免费观看视频| 女主播福利一区| 在线播放精品一区二区三区| 在线观看国产网站| 国产精品诱惑| 色哟哟一区二区| 精品无码国模私拍视频| 激情小视频在线观看| thepron国产精品| 亚洲综合精品一区二区| 中文字幕在线观看免费视频| 这里只有精品在线| 日韩中文有码在线视频| 欧美做受高潮6| 尤物tv在线精品| 欧美人妇做爰xxxⅹ性高电影 | 日本a√在线观看| 麻豆免费在线| 中文字幕在线观看一区| 天天久久人人| av影片在线看| 99久久国产综合精品色伊| 成人欧美视频在线| 亚洲欧美另类视频| 成人三级伦理片| 国产伦精品一区| 后入内射欧美99二区视频| 国产aⅴ综合色| 国产高清在线不卡| 久久久成人免费视频| 免费看的黄色欧美网站| 欧美最顶级丰满的aⅴ艳星| 2014亚洲天堂| 我不卡伦不卡影院| 欧美成人精品在线播放| 免费人成视频在线| 婷婷综合亚洲| 欧美精品一区在线播放| 久久精品www人人爽人人| 亚洲天堂激情| 欧美在线视频网| 波多野结衣视频观看| 蜜臀av性久久久久蜜臀av麻豆| 97色在线视频| 无码人妻一区二区三区线| 日韩黄色在线观看| 成人国产精品免费视频| 伊人久久中文字幕| 久草热8精品视频在线观看| 91精品视频在线| a片在线免费观看| 亚洲一级在线| 国产精品入口免费视| 一区二区 亚洲| 成人一道本在线| 欧美亚洲一级二级| 九七电影韩国女主播在线观看| 国产精品无遮挡| www.99riav| 免费看男女www网站入口在线 | 精品在线一区二区| 成人午夜电影在线播放| www.色婷婷.com| 91性感美女视频| 国语精品中文字幕| 岛国最新视频免费在线观看| 亚洲欧洲av一区二区三区久久| 亚洲 日韩 国产第一区| 中文在线免费| 色婷婷激情综合| 麻豆av免费在线| 97色婷婷成人综合在线观看| 亚洲国产中文字幕在线观看| 999精品久久久| 99国产一区| 成人看片人aa| 国产尤物视频在线| 亚洲最色的网站| 中文字幕无码精品亚洲资源网久久| 日日夜夜天天综合入口| 欧日韩精品视频| 亚洲综合色在线观看| www国产精品| 波霸ol色综合久久| 99久久99久久精品国产| 久久国产高清| 国产98在线|日韩| 午夜伦理在线| 日本韩国欧美一区| 国产高清成人久久| 啪啪亚洲精品| 国语自产在线不卡| 99这里有精品视频| 国产精品嫩草99a| 四虎永久在线精品无码视频| 久久天天久久| 亚洲色图第一页| 天天做天天爱夜夜爽| 高清日韩电视剧大全免费| 一本一本a久久| 欧美四级在线| 欧美一区二区三级| jizzjizzjizz国产| 免费看欧美美女黄的网站| 久久精品日韩精品| 1024视频在线| 欧美体内she精视频| 亚洲AV无码片久久精品| 国产日韩专区| 国模一区二区三区私拍视频| 激情网站在线| 日韩欧美在线综合网| 女尊高h男高潮呻吟| 亚洲视频碰碰| 国产成人看片| 成人影音在线| 欧美日韩美女一区二区| 蜜桃色一区二区三区| 国产精品嫩草影院在线看| 久久精品国产精品| 成人午夜视频精品一区| 免费国产亚洲视频| 亚洲巨乳在线观看| 精品乱码一区二区三区四区| 最好看的2019年中文视频| 久久婷婷国产麻豆91| 国产 欧美在线| 福利视频一区二区三区四区| 伦理一区二区| 国产成人短视频| 亚洲免费成人网| 亚洲小说欧美激情另类| 又黄又爽的网站| 亚洲女同在线| 亚洲成色最大综合在线| 久久av影院| 久久夜色精品国产欧美乱| 欧美日韩综合一区二区三区| 久久精品欧美一区二区三区麻豆| www.av毛片| 国产精一区二区| 亚洲性无码av在线| 中文字幕乱码一区二区| 91美女视频网站| 热久久精品免费视频| 99热国内精品| 国产区二精品视| 巨茎人妖videos另类| 日韩在线欧美在线| 中文在线免费观看| 亚洲欧洲中文日韩久久av乱码| 男人搞女人网站| 在线国产一区| 九九九九精品| 国产精品99| 九九久久精品一区| 欧美美女色图| 欧美一区二区福利在线| 亚洲日本韩国在线| 国产精品传媒视频| 三上悠亚在线一区| 亚洲高清二区| 亚洲一区二区三区午夜| 国产伦精品一区二区三区在线播放| 欧美疯狂性受xxxxx另类| 头脑特工队2免费完整版在线观看| 97精品人妻一区二区三区香蕉| 激情欧美丁香| 日本一区二区三区视频在线观看| 久久毛片亚洲| 九九九久久国产免费| jizz在线观看视频| 欧美精品一区二区三区蜜桃视频| 日韩精品一卡二卡| 国产日韩av一区| 亚洲77777| 国产精品女主播一区二区三区| 精品欧美一区二区三区久久久 | 国产黄色高清视频| 欧美日韩性视频在线| 成年人二级毛片| 久久久久国产精品人| 美女日批在线观看| 七七婷婷婷婷精品国产| 美女日批免费视频| 国产成人三级| 福利视频一区二区三区| 日韩成人免费av| 国产成人拍精品视频午夜网站| 岛国最新视频免费在线观看| 制服丝袜中文字幕一区| 中文字幕免费观看| 国产精品网曝门| 51调教丨国产调教视频| 成人免费毛片a| 久久久久亚洲av无码麻豆| 麻豆精品在线播放| 成人在线免费播放视频| 在线 亚洲欧美在线综合一区| 欧美精品亚洲| 欧美大片网址| 国内精品视频免费| 中文字幕区一区二区三| 成人免费看吃奶视频网站| 日韩毛片一区| 国产精品精品久久久| 国产精品久久麻豆| 日韩资源在线观看| 波多野结衣一区二区| 国产亚洲激情在线| 男男电影完整版在线观看| 日韩成人av一区| 深夜福利在线视频| 日韩精品视频免费| 性感美女福利视频| 国产午夜精品久久久 | 国产精品天天干| 99re66热这里只有精品3直播 | 欧美xxxx做受欧美护士| 欧美在线视频免费播放| 依依综合在线| 欧美高清一级大片| 国产盗摄精品一区二区酒店| 中文字幕精品视频| 天堂中文а√在线| 久久伊人精品天天| 高清国产福利在线观看| 国产亚洲成av人片在线观看桃| 免费国产精品视频| 亚洲国产精品成人av| 日韩电影网址| 亚洲性线免费观看视频成熟| 天天干视频在线| 日韩精品视频免费专区在线播放| 亚洲精品久久久久久久久久| 欧美视频一区在线| 国产日韩免费视频| 亚洲成人免费网站| 美女欧美视频在线观看免费| 一区二区三区日韩在线| 岛国中文字幕在线| 欧美精品videossex性护士| 亚洲精华液一区二区三区| 国产精品成人播放| 国产美女亚洲精品7777| 岛国一区二区三区高清视频| 偷拍亚洲精品| 亚洲一区二区三区精品在线观看| 国产亚洲精品美女久久久久久久久久| 3d动漫啪啪精品一区二区免费| 精品女同一区二区三区在线观看| 国产成人在线视频| 亚洲人成777| 久久66热这里只有精品| 成人一区不卡| 日韩在线视频在线| 久久久精品性| 亚洲天堂小视频| 91麻豆6部合集magnet| 大地资源高清在线视频观看| 亚洲一区二区三区免费视频| 无码视频一区二区三区| 色婷婷亚洲综合| 成 人 免费 黄 色| 日韩女优电影在线观看| 日韩av视屏| 色在人av网站天堂精品| 国产另类xxxxhd高清| 999国内精品视频在线| 亚洲精品观看| 动漫精品视频| 欧美影院三区| 国产 日韩 欧美在线| 久久av老司机精品网站导航| 少妇户外露出[11p]| 亚洲女人的天堂| 一级特黄免费视频| 精品国产乱码久久久久久浪潮 | 成人午夜激情视频| 国产毛片欧美毛片久久久| 国产精品网站在线| 久久久精品免费看| 日韩欧美一级在线播放| 手机看片1024日韩| 久久国产精品久久精品| 欧美福利在线播放| 久久99精品久久久久久久久久 | 国产亚洲综合久久| 51精品视频| 亚洲最大成人免费视频| 日韩美女一区二区三区在线观看| 成人在线观看www| 免费久久99精品国产| 亚洲精品乱码久久久久久9色| av在线这里只有精品| 国产精品久久久久久久精| 欧美日韩一区视频| 免费在线稳定资源站| 97香蕉超级碰碰久久免费软件| 婷婷六月国产精品久久不卡| 成人激情综合网| jlzzjlzz亚洲女人| 久久婷婷国产精品| 91小视频在线观看| 日产精品久久久久| 欧美日韩一区二区三区四区| 国模精品一区二区| 青青久久av北条麻妃黑人| 欧美人与动xxxxz0oz| 亚洲 欧洲 日韩| 九九视频精品免费| 国产精品精品软件男同| 亚洲第一在线综合网站| 国产精品第6页| 亚洲一区二区久久久| h1515四虎成人| 亚洲精品日韩成人| 免费久久99精品国产| av在线免费播放网址| 欧美日韩1234| 91麻豆免费在线视频| 国产99久久精品一区二区 夜夜躁日日躁 | 中文字幕人妻无码系列第三区| 国产午夜亚洲精品不卡| 久草国产在线观看| 精品污污网站免费看| 午夜18视频在线观看| 欧美在线视频一二三| 国产一区二区精品久| 欧美日韩亚洲自拍| 中文字幕制服丝袜一区二区三区| 人人爽人人爽人人片av| 亚洲网站在线看| 免费视频观看成人| 日韩视频在线免费播放| 国产成人免费视频网站高清观看视频| 黄大色黄女片18免费| 福利视频导航一区| 九色视频在线播放| 国产精品永久免费在线| 亚洲乱码电影| 免费黄色三级网站| 日本道在线观看一区二区| 欧美成人三区| 国产精品欧美在线| 影音先锋成人在线电影| 一级特级黄色片| 欧美日韩免费高清一区色橹橹| 国产小视频在线| 成人字幕网zmw| 亚洲美洲欧洲综合国产一区| 受虐m奴xxx在线观看| 欧美精品日韩综合在线| 国产丝袜在线播放| 欧美日韩亚洲在线| 国产美女在线精品| 午夜精品久久久久久久久久久久久蜜桃| 欧美一区二区三区白人| 成年人黄视频在线观看| 国产在线日韩在线| 影音先锋在线一区| 手机免费观看av| 亚洲电影免费观看高清完整版在线| 污视频网站在线免费| 欧美动漫一区二区| 国内精品久久久久影院一蜜桃| 一区二区国产精品精华液| 日韩av在线精品| 一区二区三区日本视频| 日韩欧美精品在线观看视频| 国产三级精品在线| 亚洲精品中文字幕成人片| 国产精品白丝jk喷水视频一区|