2010-06-18 125 views
25

具體來說,我有一種方法從列表中選取n個項目,其中一個百分比滿足一個條件,b%滿足第二個條件,依此類推。一個簡單的例子是選擇5個項目,其中50%具有給定屬性,值爲'真',50%'假'; 50%的時間該方法將返回2 true/3 false,另外50%,3 true/2 false。從統計學上講,這意味着超過100次運行,我應該得到約250真/ 250假,但由於隨機性,240/260是完全可能的。單元測試生成隨機輸出的代碼的最佳方法是什麼?

單元測試的最佳方式是什麼?我假設儘管300/200技術上是可能的,但如果發生這種情況,測試可能會失敗。這種情況是否有普遍接受的容忍度?如果是這樣,你如何確定這是什麼?

編輯:在我正在處理的代碼中,我沒有使用僞隨機數生成器的奢侈品,也沒有使用僞隨機數生成器或強制它隨時間推移而平衡的機制,因爲列出了所選列表在不同的機器上生成。我需要能夠證明,隨着時間的推移,符合每個標準的項目的平均數量將傾向於所需的百分比。

+0

在這個例子中,你想要至少/正好50%還是約50%?更具體地說,這個測試的隨機性是什麼? – Gishu 2010-06-18 09:41:04

+1

我懷疑你實際上沒有編寫單元測試。如果您正在測試運行在不同機器上的服務器,則實際上正在進行系統測試。我只能告訴你:如果你對這些服務器上運行的類進行了單元測試,那麼你不再需要進行太多(詳細的)系統測試。 – 2010-06-18 10:13:54

+0

不,重點是要確認算法在2/3 50%的時間內選擇2/3的其他50%(在這個簡單的例子中),無論它在哪裏使用。這不是一個製造這個系統的系統;在一臺機器上運行1000次被認爲是一個足夠的測試,以證明如果它在世界各地的100臺機器上運行10次,它將適當平均,因此我計劃對它進行單元測試。 – Flynn1179 2010-06-18 11:51:56

回答

22

隨機和統計不受單元測試的青睞。單元測試應該始終返回相同的結果。總是。主要不是。

你可以做的是試圖去除你正在測試的邏輯的隨機生成器。然後你可以模擬隨機發生器並返回預定義的值。


更多的想法:

你可以考慮改變實現,使其更容易測試。嘗試獲得儘可能少的隨機值。例如,您只能得到一個隨機值來確定與平均分佈的偏差。這將很容易測試。如果隨機值爲零,則應該得到您期望的平均分佈。如果該值爲例如1.0,那麼您會錯過某個定義因子的平均值,例如10%。您也可以實現一些高斯分佈等。我知道這不是這裏的主題,但如果您可以隨意實現它,那麼請考慮可測試性。

+1

+1的角度變化。 – 2010-06-18 09:40:05

+0

你不會認爲'值必須是 Flynn1179 2010-06-18 10:05:13

+0

有什麼不同的機器單元測試呢? – 2010-06-18 10:12:14

4

根據您的統計信息,確定範圍而不是特定的單個值作爲結果。

+2

只要你在測試中有任何隨機的話,它仍然可能是誤報的假陽性。 – 2010-06-18 09:35:45

2

您應該在「單一」單元測試中測試結果分佈,即在任何單獨運行中結果儘可能接近所需分佈。對於你的例子,2 true/3 false是OK,4 true/1 false是不好的結果。

你也可以編寫執行該方法的測試,例如100次,並檢查分佈的平均值「足夠接近」到所需的比率。這是一個臨界情況 - 運行較大的批處理可能需要很長時間,因此您可能需要單獨運行這些測試,而不是從「常規」單元測試中運行。同樣,正如Stefan Steinegger指出的那樣,如果您定義「足夠接近」更嚴格,或者如果您定義的閾值過於寬鬆,開始變得毫無意義,那麼此類測試會不時失敗。所以這是一個棘手的案例...

3

這取決於您對測試套件的使用情況。如果你每隔幾秒就運行一次,因爲你接受了測試驅動的開發和積極的重構,那麼它不會虛假地失敗是非常重要的,因爲這會導致嚴重的中斷並降低生產力,所以你應該選擇一個幾乎不可能實現的閾值達到一個行爲良好的實施。如果您每晚進行一次測試,並有時間調查失敗,則可能會更嚴格。

在任何情況下,您都不應該部署會導致頻繁未經調查的失敗的事情 - 這會破壞擁有測試套件的整個目的,並大大降低其對團隊的價值。

4

許多概率算法在例如科學計算使用pseudo-random number generators,而不是true隨機數發生器。即使它們不是真正的隨機數,精心挑選的僞隨機數生成器也可以很好地完成這項工作。一個 -random數發生器的

一個優點是,它們所產生的隨機數序列是完全可再現。由於該算法是確定性的,所以相同的種子將總是生成相同的序列。這通常是他們首先選擇的決定因素,因爲實驗需要可重複,結果可重現。

這個概念也適用於測試。組件可以設計成可以插入任何隨機數字源。爲了測試,您可以使用始終播種的發生器。結果將是可重複的,適合測試。

注意,如果實際上是需要一個真正隨機數,你可以仍然測試這種方式,只要組件功能的隨機數可插拔源。您可以將相同的序列(如果需要可能是真正的隨機序列)重新插入相同的元件進行測試。

1

我認爲如果我有同樣的問題,我可能會構建一個置信區間來檢測異常情況,如果您有一些關於average/stddev等的統計信息。所以在你的情況下,如果平均預期值是250,那麼使用正態分佈在平均值周圍創建一個95%的置信區間。如果結果超出此間隔,則測試失敗。

看到more

0

爲什麼不重新因素的隨機數生成代碼,讓單元測試框架和源代碼都使用它呢?你試圖測試你的算法,而不是隨機序列的權利?

4

在我看來,有你想在這裏測試至少三個不同的東西:

  1. 產生使用隨機源
  2. ,一個輸出的過程的正確性隨機源的分佈是你所期望的
  3. ,輸出的分佈是你期望

1應該是確定性的東西,你可以通過提供一個選擇的集合O單元測試f已知的「隨機」值和輸入,並檢查它是否產生已知的正確輸出。如果您構造代碼以使隨機源作爲參數傳遞而不是嵌入代碼中,這將是最簡單的。

2和3絕對不能測試。您可以測試某些選定的置信水平,但您必須準備好使這些測試在某些情況下失敗。可能你真正想要注意的是測試3比測試2失敗得多,因爲這會表明你的算法是錯誤的。

要應用的測試將取決於預期的分佈。對於2,你很可能期望隨機源是均勻分佈的。對此有各種測試,具體取決於您希望如何參與,請參閱Tests for pseudo-random number generators on this page

3的預期分配將很大程度上取決於您生產的產品。問題中的簡單50-50案例與testing for a fair coin完全相同,但顯然其他案例會更加複雜。如果你能確定分配應該是什麼,那麼反對它的chi-square test可能會有所幫助。

0

首先你必須知道你的隨機數生成過程應該產生什麼樣的分佈。在你的情況下,你生成的結果是0或1,概率爲-0.5。這描述了p = 0.5的binomial distribution

給定n的樣本量,您可以構建一個圍繞均值的置信區間。當n = 500時,你也可以對獲得的結果的可能性做出各種表述,例如240或更少的結果。

你可以只要p不是非常大或非常小的使用大於20的N個值正態分佈的假設。維基百科的帖子有更多。

相關問題