डाई को रोल करने के उपयोग के मामले को कवर करने के लिए अच्छी इकाई परीक्षण क्या हैं?


18

मैं इकाई परीक्षण के साथ पकड़ में आने की कोशिश कर रहा हूं।

मान लें कि हमारे पास एक डाई है जिसमें 6 के बराबर डिफ़ॉल्ट पक्ष हो सकते हैं (लेकिन 4, 5 पक्षीय आदि हो सकते हैं):

import random
class Die():
    def __init__(self, sides=6):
        self._sides = sides

    def roll(self):
        return random.randint(1, self._sides)

क्या निम्नलिखित मान्य / उपयोगी इकाई परीक्षण होंगे?

  • 6 पक्षीय मरने के लिए 1-6 की सीमा में रोल का परीक्षण करें
  • 6 पक्षीय मरने के लिए 0 के रोल का परीक्षण करें
  • 6 पक्षीय मरने के लिए 7 के रोल का परीक्षण करें
  • 3 तरफा मरने के लिए रेंज 1-3 में एक रोल का परीक्षण करें
  • एक 3 पक्षीय मरने के लिए 0 के रोल का परीक्षण करें
  • एक 3 पक्षीय मरने के लिए 4 के रोल का परीक्षण करें

मैं बस सोच रहा हूं कि ये समय की बर्बादी हैं क्योंकि यादृच्छिक मॉड्यूल काफी लंबे समय से आसपास है लेकिन फिर मुझे लगता है कि अगर यादृच्छिक मॉड्यूल अपडेट हो जाता है (कहते हैं कि मैं अपने पायथन संस्करण को अपडेट करता हूं) तो कम से कम मैं कवर हूं।

इसके अलावा, क्या मुझे इस मामले में 3 की तरह डाय रोल के अन्य रूपों का परीक्षण करने की भी आवश्यकता है, या क्या यह एक और आरंभिक डाई स्टेट को कवर करने के लिए अच्छा है?


1
माइनस 5-साइडेड मृत्‍यु या अशक्त मृत्‍यु के बारे में क्‍या?
जेएनएसजी

जवाबों:


22

आप सही हैं, आपके परीक्षणों को यह सत्यापित नहीं करना चाहिए कि randomमॉड्यूल अपना काम कर रहा है; एक यूनिटेस्ट को केवल कक्षा का ही परीक्षण करना चाहिए, न कि यह अन्य कोड के साथ कैसे इंटरैक्ट करता है (जिसे अलग से परीक्षण किया जाना चाहिए)।

यह पूरी तरह से संभव है कि आपका कोड random.randint()गलत उपयोग करता है; या आप random.randrange(1, self._sides)इसके बजाय फोन कर रहे हैं और आपकी मृत्यु कभी भी उच्चतम मूल्य नहीं फेंकती है, लेकिन यह एक अलग तरह का बग होगा, न कि आप जिसे एक सबसे अच्छे तरीके से पकड़ सकते हैं। उस स्थिति में, आपकी die इकाई डिज़ाइन के रूप में काम कर रही है, लेकिन डिज़ाइन स्वयं त्रुटिपूर्ण था।

इस स्थिति में, मैं फ़ंक्शन को बदलने के लिए मॉकिंग का उपयोग करूंगा randint(), और केवल यह सत्यापित करूंगा कि इसे सही तरीके से कहा गया है। पायथन 3.3 और अप इस प्रकार के परीक्षण को संभालने के लिए unittest.mockमॉड्यूल के साथ आता है , लेकिन आप सटीक समान कार्यक्षमता प्राप्त करने के लिए पुराने संस्करणों पर बाहरी mockपैकेज स्थापित कर सकते हैं

import unittest
try:
    from unittest.mock import patch
except ImportError:
    # < python 3.3
    from mock import patch


@patch('random.randint', return_value=3)
class TestDice(unittest.TestCase):
    def _make_one(self, *args, **kw):
        from die import Die
        return Die(*args, **kw)

    def test_standard_size(self, mocked_randint):
        die = self._make_one()
        result = die.roll()

        mocked_randint.assert_called_with(1, 6)
        self.assertEqual(result, 3)

    def test_custom_size(self, mocked_randint):
        die = self._make_one(sides=42)
        result = die.roll()

        mocked_randint.assert_called_with(1, 42)
        self.assertEqual(result, 3)


if __name__ == '__main__':
    unittest.main()

मॉकिंग के साथ, आपका परीक्षण अब बहुत सरल है; केवल 2 मामले हैं, वास्तव में। 6-पक्षीय मरने के लिए डिफ़ॉल्ट मामला और कस्टम पक्ष केस।

randint()वैश्विक नामस्थान में फ़ंक्शन को अस्थायी रूप से प्रतिस्थापित करने के अन्य तरीके हैं Die, लेकिन mockमॉड्यूल यह सबसे आसान बनाता है। यहाँ @mock.patchसज्जाकार परीक्षण के मामले में सभी परीक्षण विधियों पर लागू होता है ; प्रत्येक परीक्षण विधि को एक अतिरिक्त तर्क दिया जाता है, random.randint()मॉक किए गए फ़ंक्शन, इसलिए हम मॉक के खिलाफ यह देखने के लिए परीक्षण कर सकते हैं कि क्या यह वास्तव में सही रूप से कहा गया है। return_valueतर्क निर्दिष्ट क्या, नकली से दिया जाता है तो हम पुष्टि कर सकते हैं जब यह कहा जाता है die.roll()विधि वास्तव में हमारे लिए 'यादृच्छिक' परिणाम प्राप्त हुआ।

मैंने यहां एक और पायथन का सबसे अच्छा अभ्यास किया है: परीक्षण के हिस्से के रूप में परीक्षण के तहत कक्षा का आयात करें। _make_oneविधि आयात और इन्स्टेन्शियशन काम करता है एक परीक्षण के भीतर , परीक्षण ताकि मॉड्यूल अभी भी लोड होगा, भले ही आप एक सिंटैक्स त्रुटि या अन्य गलती है कि आयात करने के लिए मूल मॉड्यूल रोक देंगे बना दिया।

इस तरह, यदि आपने मॉड्यूल कोड में ही गलती की है, तो परीक्षण अभी भी चलाए जाएंगे; वे आपके कोड में त्रुटि के बारे में बताते हुए, बस विफल हो जाएंगे।

स्पष्ट होने के लिए, उपरोक्त परीक्षण चरम में सरल हैं। random.randint()उदाहरण के लिए, यहाँ लक्ष्य को सही तर्कों के साथ परीक्षण करना नहीं है । इसके बजाय, लक्ष्य यह परीक्षण करना है कि इकाई कुछ इनपुटों को देखते हुए सही परिणाम दे रही है, जहां उन इनपुटों में अन्य इकाइयों के परिणाम शामिल हैं जो परीक्षण के तहत नहीं हैंrandom.randint()अपने कोड में सिर्फ एक और इनपुट पर नियंत्रण पाने के लिए विधि का मज़ाक उड़ाकर ।

में असली दुनिया परीक्षण, अपनी यूनिट-अंडर-परीक्षण में वास्तविक कोड और अधिक जटिल होने जा रहा है; एपीआई में पारित इनपुट्स के साथ संबंध और कैसे अन्य इकाइयां हैं, तब भी दिलचस्प हो सकता है, और मॉकिंग आपको मध्यवर्ती परिणामों तक पहुंच देगा, साथ ही साथ आप उन कॉल के लिए रिटर्न मान भी सेट करेंगे।

उदाहरण के लिए, कोड में जो उपयोगकर्ताओं को तृतीय पक्ष OAuth2 सेवा (एक मल्टी-स्टेज इंटरैक्शन) के खिलाफ प्रमाणित करता है, आप यह परीक्षण करना चाहते हैं कि आपका कोड उस 3 पार्टी सेवा के लिए सही डेटा पास कर रहा है, और आपको विभिन्न त्रुटि प्रतिक्रियाओं का मजाक उड़ाता है। 3 पार्टी सेवा वापस आ जाएगी, जिससे आप बिना पूर्ण OAuth2 सर्वर का निर्माण किए विभिन्न परिदृश्यों का अनुकरण कर सकते हैं। यहां यह परीक्षण करना महत्वपूर्ण है कि पहली प्रतिक्रिया से जानकारी को सही तरीके से संभाला गया है और दूसरे चरण के कॉल पर पास किया गया है, इसलिए आप यह देखना चाहते हैं कि नकली सेवा को सही तरीके से कहा जा रहा है।


1
आपको 2 से अधिक परीक्षण मामले मिल गए हैं ... परिणाम डिफ़ॉल्ट मान के लिए जाँच करते हैं: निचला (1), ऊपरी (6), नीचे कम (0), ऊपरी (7) से परे और उपयोगकर्ता के लिए निर्दिष्ट संख्या जैसे max_int के परिणाम आदि इनपुट भी मान्य नहीं है, जिसे किसी बिंदु पर जांचने की आवश्यकता हो सकती है ...
जेम्स स्नेल

2
नहीं, उन के लिए परीक्षण हैं randint(), न कि कोड में Die.roll()
मार्टिज़न पीटर्स

वास्तव में यह सुनिश्चित करने का एक तरीका है कि न केवल रैंडिंट को सही तरीके से कहा जाता है, बल्कि इसका परिणाम भी सही तरीके से उपयोग किया जाता है: sentinel.dieउदाहरण के लिए इसे वापस करने के लिए नकली (प्रहरी वस्तु unittest.mockभी) से है और फिर सत्यापित करें कि यह वही है जो आपके रोल विधि से वापस आ गया था। यह वास्तव में परीक्षण की गई विधि को लागू करने का केवल एक तरीका है।
अर्गेर

@aragaer: निश्चित रूप से, यदि आप यह सत्यापित करना चाहते हैं कि मान अपरिवर्तित है, sentinel.dieतो यह सुनिश्चित करने का एक शानदार तरीका होगा।
मार्टिजन पीटरर्स

मुझे समझ नहीं आता कि आप यह क्यों सुनिश्चित करना चाहेंगे कि mocked_randint को कुछ मान कहा जाता है। मैं समझता हूं कि पूर्वानुमानित मूल्यों को वापस करने के लिए रैंडम का मजाक उड़ाना चाहता है, लेकिन क्या यह चिंता सिर्फ यह नहीं है कि यह अनुमानित मूल्यों को लौटाता है और न कि किन मूल्यों के साथ इसे कहा जाता है? यह मुझे लगता है कि बुलाया मूल्यों की जाँच अनावश्यक रूप से परीक्षण को क्रियान्वयन के बारीक विवरण से बांध रही है। इसके अलावा, हम इस बात की परवाह क्यों करते हैं कि मरना रंडिन का सही मूल्य देता है? क्या हम वास्तव में केवल इस बात की परवाह नहीं करते हैं कि यह मूल्य> १ और अधिकतम के बराबर से कम हो?
bdrx

16

मार्टिज़न का जवाब है कि आप यह कैसे करेंगे यदि आप वास्तव में एक परीक्षण चलाना चाहते हैं जो दर्शाता है कि आप random.randint कह रहे हैं। हालांकि, "यह सवाल का जवाब नहीं देता है" के जोखिम पर, मुझे लगता है कि यह बिल्कुल भी परीक्षण नहीं किया जाना चाहिए। मॉकिंग रैंडिंट अब ब्लैक बॉक्स परीक्षण नहीं है - आप विशेष रूप से दिखा रहे हैं कि कार्यान्वयन में कुछ चीजें चल रही हैं । ब्लैक बॉक्स परीक्षण यह एक विकल्प भी नहीं है - कोई भी परीक्षण नहीं है जिसे आप निष्पादित कर सकते हैं जो यह साबित करेगा कि परिणाम कभी भी 1 से कम या 6 से अधिक नहीं होगा ।

क्या आप मजाक कर सकते हैं randint? हाँ तुम कर सकते हो। लेकिन आप क्या साबित कर रहे हैं? कि आप इसे तर्क 1 और पक्षों के साथ कहते हैं। क्या करता है कि मतलब? आप एक वर्ग में वापस आ गए हैं - दिन के अंत में आप को साबित करना होगा - औपचारिक रूप से या अनौपचारिक रूप से - कि कॉलिंग random.randint(1, sides)सही ढंग से एक पासा रोल लागू करता है।

मैं सभी इकाई परीक्षण के लिए हूँ। वे शानदार पवित्रता जाँच रहे हैं और बग की उपस्थिति को उजागर करते हैं। हालांकि, वे कभी भी अपनी अनुपस्थिति को साबित नहीं कर सकते हैं, और ऐसी चीजें हैं जिन्हें परीक्षण के माध्यम से पूरा नहीं किया जा सकता है (जैसे कि एक विशेष फ़ंक्शन कभी अपवाद नहीं फेंकता है या हमेशा समाप्त होता है।) इस विशेष मामले में, मुझे लगता है कि आप बहुत कम खड़े हैं। प्राप्त करें। नियतात्मक होने वाले व्यवहार के लिए, यूनिट परीक्षण समझ में आता है क्योंकि आप वास्तव में जानते हैं कि आप जिस उत्तर की उम्मीद कर रहे हैं वह क्या होगा।


यूनिट परीक्षण वास्तव में ब्लैक बॉक्स परीक्षण नहीं हैं। इंटीग्रेशन टेस्ट क्या हैं, यह देखने के लिए कि विभिन्न भाग डिज़ाइन के अनुसार बातचीत करते हैं। यह राय का विषय है, निश्चित रूप से (अधिकांश परीक्षण दर्शन है), देखें क्या "यूनिट परीक्षण" सफेद बॉक्स या ब्लैक बॉक्स परीक्षण के अंतर्गत आता है? और कुछ (स्टैक ओवरफ्लो) दृष्टिकोण के लिए ब्लैक बॉक्स यूनिट परीक्षण
मार्टिज़न पीटर 13

@MartijnPieters मैं असहमत हूं कि "यही एकीकरण परीक्षण हैं"। एकीकरण परीक्षण यह जांचने के लिए हैं कि सिस्टम के सभी घटक सही तरीके से बातचीत करते हैं। वे यह जांचने का स्थान नहीं हैं कि एक दिया गया घटक किसी दिए गए इनपुट के लिए सही आउटपुट देता है। ब्लैक बॉक्स बनाम व्हाइट बॉक्स यूनिट परीक्षण के रूप में, सफेद बॉक्स यूनिट परीक्षण अंततः कार्यान्वयन परिवर्तनों के साथ टूट जाएगा, और कार्यान्वयन में आपके द्वारा की गई कोई भी धारणा संभवतः परीक्षण में आगे बढ़ेगी। अगर यह गलत काम है, तो इसके random.randintसाथ मान्य 1, sidesहोना बेकार है।
डोवल

हाँ, यह एक सफेद बॉक्स इकाई परीक्षण की एक सीमा है। हालाँकि, परीक्षण का कोई मतलब नहीं है कि random.randint()रेंज [1, पक्षों] (समावेशी) में मूल्यों को सही ढंग से लौटाएगा, यह सुनिश्चित करने के लिए कि यह randomसही ढंग से काम करता है कि यूनिट काम करती है।
मार्टिनेज पीटरर्स

और जैसा कि आप स्वयं कहते हैं, इकाई परीक्षण यह गारंटी नहीं दे सकता कि आपका कोड बग मुक्त है; यदि आपका कोड गलत तरीके से अन्य इकाइयों का उपयोग कर रहा है (कहो, तो आप ऐसा random.randint()व्यवहार करने की अपेक्षा करते हैं random.randrange()और इस तरह से कॉल करते हैं random.randint(1, sides + 1), तो आप वैसे भी डूब जाते हैं।
Martijn Pieters

2
@MartijnPieters मैं आपसे वहाँ सहमत हूँ, लेकिन ऐसा नहीं है जिस पर मुझे आपत्ति है। मैं परीक्षण करने पर आपत्ति कर रहा हूं कि random.randint को तर्कों (1, पक्षों) के साथ बुलाया जा रहा है । आपने कार्यान्वयन में मान लिया है कि यह सही काम है, और अब आप परीक्षण में उस धारणा को दोहरा रहे हैं। क्या यह धारणा गलत होनी चाहिए, परीक्षा पास हो चुकी है लेकिन आपका कार्यान्वयन अभी भी गलत है। यह एक आधा-गधा सबूत है जो लिखने और बनाए रखने के लिए एक पूर्ण दर्द-इन-गधा है।
डोवल

6

यादृच्छिक बीज को ठीक करें। 1, 2, 5 और 12-पक्षीय पासा के लिए, पुष्टि करें कि कुछ हजार रोल 1 और N सहित परिणाम देते हैं, और 0 या N + 1. को शामिल नहीं करते हैं। यदि फ्रीक चांस लगता है तो आपको यादृच्छिक परिणाम का एक सेट मिलता है जो नहीं अपेक्षित सीमा को कवर करें, एक अलग बीज पर स्विच करें।

मॉकिंग टूल शांत होते हैं, लेकिन सिर्फ इसलिए कि वे आपको एक काम करने की अनुमति देते हैं इसका मतलब यह नहीं है कि चीज़ को किया जाना चाहिए। YAGNI सुविधाओं के रूप में जुड़नार का परीक्षण करने के लिए लागू होता है।

यदि आप आसानी से बेमेल निर्भरता के साथ परीक्षण कर सकते हैं, तो आपको हमेशा बहुत अधिक चाहिए; इस तरह से आपके परीक्षण दोष की गिनती को कम करने पर केंद्रित होंगे, न कि केवल परीक्षण की संख्या को बढ़ाने के लिए। भ्रामक कवरेज के आंकड़े पैदा करने वाले अतिरिक्त जोखिम, जो बदले में वास्तविक परीक्षण को कुछ बाद के चरण में स्थगित करने का कारण बन सकते हैं, आपके पास शायद कभी भी गोल होने का समय नहीं है ...


3

Dieयदि आप इसके बारे में सोचते हैं तो क्या है ? - आसपास रैपर से ज्यादा नहीं random। यह random.randintआपके अनुप्रयोग की अपनी शब्दावली के संदर्भ में इसे संक्षिप्त और संक्षिप्त करता है Die.Roll:।

मुझे बीच Die- बीच में अमूर्तता की एक और परत डालने के लिए प्रासंगिक नहीं लगता है और randomक्योंकि आपके एप्लिकेशन और प्लेटफ़ॉर्म के बीच Dieअप्रत्यक्षता की यह परत पहले से ही मौजूद है।

यदि आप डिब्बाबंद पासा परिणाम चाहते हैं , तो केवल नकली Die, नकली न करेंrandom

सामान्य तौर पर, मैं अपने रैपर ऑब्जेक्ट्स का परीक्षण नहीं करता हूं जो बाहरी प्रणालियों के साथ संवाद करते हैं, मैं उनके लिए एकीकरण परीक्षण लिखता हूं। आप उन लोगों के लिए कुछ लिख सकते हैं, Dieलेकिन जैसा कि आपने बताया, अंतर्निहित वस्तु की यादृच्छिक प्रकृति के कारण, वे सार्थक नहीं होंगे। इसके अलावा, यहाँ कोई कॉन्फ़िगरेशन या नेटवर्क संचार शामिल नहीं है इसलिए प्लेटफ़ॉर्म कॉल को छोड़कर परीक्षण करने के लिए बहुत अधिक नहीं है।

=> यह देखते हुए कि Dieकोड की केवल कुछ तुच्छ लाइनें हैं और randomखुद की तुलना में कोई तर्क नहीं जोड़ता है, मैं इसे उस विशिष्ट उदाहरण में परीक्षण करना छोड़ दूंगा।


2

यादृच्छिक संख्या जनरेटर को सीडिंग करना और अपेक्षित परिणामों की पुष्टि करना, जहां तक ​​मैं देख सकता हूं, एक वैध परीक्षण नहीं है। यह अनुमान लगाता है कि आपके पासा आंतरिक रूप से कैसे काम करते हैं, जो शरारती-शरारती है। अजगर के डेवलपर्स यादृच्छिक संख्या जनरेटर को बदल सकते हैं, या मर सकते हैं (नोट: "पासा" बहुवचन है, "मरना" विलक्षण है। जब तक आपकी कक्षा एक कॉल में एकाधिक डाई रोल लागू नहीं करती है, तब तक इसे संभवतः "डाई" कहा जाना चाहिए)। एक अलग यादृच्छिक संख्या जनरेटर का उपयोग करें।

इसी तरह, रैंडम फंक्शन का मजाक उड़ाना यह मानता है कि क्लास इंप्लीमेंटेशन बिल्कुल उम्मीद के मुताबिक काम करता है। ऐसा क्यों नहीं हो सकता है? कोई व्यक्ति डिफ़ॉल्ट अजगर यादृच्छिक संख्या जनरेटर का नियंत्रण ले सकता है, और इससे बचने के लिए, आपके मरने का एक भविष्य का संस्करण अधिक यादृच्छिक डेटा में मिश्रण करने के लिए कई यादृच्छिक संख्या, या बड़े यादृच्छिक संख्या ला सकता है। फ्रीबीएसडी ऑपरेटिंग सिस्टम के निर्माताओं द्वारा इसी तरह की योजना का उपयोग किया गया था, जब उन्हें संदेह था कि एनएसए सीपीयू में निर्मित हार्डवेयर यादृच्छिक संख्या जनरेटर के साथ छेड़छाड़ कर रहा है।

अगर यह मैं होता, तो मैं कहता, 6000 रोल करता, उन्हें टो करता, और यह सुनिश्चित करता कि 1-6 से प्रत्येक नंबर 500 और 1500 बार के बीच रोल किया जाता। मैं यह भी जाँच करूंगा कि उस सीमा के बाहर की कोई संख्या वापस नहीं हुई है। मैं यह भी जाँच सकता हूँ कि, आवृत्ति के क्रम में [१.६.६] का आदेश देने पर ६००० रोल के दूसरे सेट के लिए, परिणाम अलग है (यह संख्या !२० रन से एक बार विफल हो जाएगी, यदि संख्या यादृच्छिक हैं!)। यदि आप पूरी तरह से बनना चाहते हैं, तो आपको एक 1 के बाद संख्याओं की आवृत्ति मिल सकती है, 2 का अनुसरण करते हुए, आदि; लेकिन सुनिश्चित करें कि आपका नमूना आकार काफी बड़ा है, और आपके पास पर्याप्त विचरण है। मनुष्य यादृच्छिक संख्याओं की अपेक्षा करता है कि वे वास्तव में कम पैटर्न रखते हैं।

एक 12 पक्षीय के लिए दोहराएं, और 2 तरफा मरना (6 सबसे अधिक उपयोग किया जाता है, इसलिए इस कोड को लिखने वाले किसी भी व्यक्ति के लिए सबसे अधिक अपेक्षित है)।

अंत में, मैं यह देखने के लिए परीक्षण करूंगा कि 1-पक्षीय मृत्यु, 0-पक्षीय मृत्यु, -1-पक्षीय मृत्यु, 2.3-पक्षीय मृत्यु, [1,2,3,4,5,6] पक्षीय मृत्यु, और क्या होता है a "ब्लाह" -sided मर गया। बेशक, इन सभी को विफल होना चाहिए; क्या वे एक उपयोगी तरीके से विफल होते हैं? ये संभवत: सृजन पर असफल होना चाहिए, लुढ़कने पर नहीं।

या, शायद, आप भी इनको अलग तरह से संभालना चाहते हैं - शायद [१,२,३,४,५,६] के साथ मरना स्वीकार्य होना चाहिए - और शायद "ब्ला" भी; यह 4 चेहरों वाला डाई हो सकता है, और प्रत्येक चेहरे पर एक अक्षर होगा। खेल "बोगल" मन में घूमता है, जैसा कि एक जादू आठ गेंद करता है।

और अंत में, आप इस पर विचार करना चाह सकते हैं: http://lh6.ggpht.com/-fAGXwbJbYRM/UJA_31ACOLI/AAAAAAAAAPAPg/2FxOWzo96KE//1616-h/random%25255B3%25255D.jpg


2

ज्वार के खिलाफ तैरने के जोखिम पर, मैंने इस सटीक समस्या को कई साल पहले हल किया था, जिसमें अब तक उल्लेख नहीं किया गया है।

मेरी रणनीति बस RNG का मज़ाक उड़ाने के लिए थी जो पूरे अंतरिक्ष में फैले मूल्यों की एक पूर्वानुमानित धारा पैदा करती है। यदि (कहें) पक्ष = ६ और आरएनजी ० से ५ के क्रम में मान उत्पन्न करता है तो मैं यह अनुमान लगा सकता हूं कि मेरी कक्षा को कैसे व्यवहार करना चाहिए और उसके अनुसार इकाई परीक्षण करना चाहिए।

तर्क यह है कि यह इस वर्ग में अकेले तर्क का परीक्षण करता है, इस धारणा पर कि RNG अंततः उन मूल्यों में से प्रत्येक का उत्पादन करेगा और खुद RNG का परीक्षण किए बिना।

यह सरल, नियतात्मक, प्रतिलिपि प्रस्तुत करने योग्य है और यह बग को पकड़ता है। मैं फिर से उसी रणनीति का उपयोग करूंगा।


प्रश्न यह नहीं बताता है कि परीक्षण क्या होना चाहिए, बस एक आरएनजी की उपस्थिति को देखते हुए, परीक्षण के लिए कौन से डेटा का उपयोग किया जा सकता है। मेरा सुझाव महज RNG का मजाक उड़ाकर परीक्षण करना है। परीक्षण के लायक होने का प्रश्न प्रश्न में प्रदान की गई जानकारी पर निर्भर करता है।


कहते हैं कि आप RNG का अनुमान लगाने योग्य हैं। अच्छा तो आप क्या परीक्षण करते हैं? प्रश्न पूछता है "क्या निम्नलिखित मान्य / उपयोगी इकाई परीक्षण होंगे?" 0-5 पर लौटने के लिए इसका मजाक उड़ाना परीक्षण नहीं है, बल्कि परीक्षण सेटअप है। आप "इकाई परीक्षण तदनुसार" कैसे करेंगे? मैं यह समझने में विफल रहा हूं कि यह "कीड़े कैसे पकड़ता है"। मुझे यह समझने में कठिन समय हो रहा है कि मुझे 'यूनिट' टेस्ट की क्या आवश्यकता है।
bdrx

@bdrx: यह कुछ समय पहले था: मैं इसे अब अलग तरीके से उत्तर दूंगा। लेकिन संपादित देखें।
david.pfx

1

आपके प्रश्न में आपके द्वारा सुझाए गए परीक्षण कार्यान्वयन के रूप में एक मॉड्यूलर अंकगणितीय काउंटर का पता नहीं लगाते हैं। और वे संभावना वितरण से संबंधित कोड की तरह सामान्य कार्यान्वयन त्रुटियों का पता नहीं लगाते हैं return 1 + (random.randint(1,maxint) % sides)। या जनरेटर के लिए एक परिवर्तन जिसके परिणामस्वरूप 2-आयामी पैटर्न होते हैं।

यदि आप वास्तव में यह सत्यापित करना चाहते हैं कि आप समान रूप से वितरित यादृच्छिक-दिखने वाली संख्याएँ उत्पन्न कर रहे हैं, तो आपको बहुत व्यापक गुणों की जाँच करनी होगी। उस पर यथोचित अच्छा काम करने के लिए आप अपने उत्पन्न नंबरों पर http://www.phy.duke.edu/~rgb/General/dieharder.php चला सकते हैं । या एक समान जटिल यूनिट-टेस्ट सूट लिखें।

यह इकाई-परीक्षण या टीडीडी की गलती नहीं है, यादृच्छिकता सिर्फ सत्यापित करने के लिए एक बहुत ही कठिन संपत्ति होती है। और उदाहरण के लिए एक लोकप्रिय विषय।


-1

एक डाई-रोल का सबसे आसान परीक्षण बस इसे कई सौ-हजार बार दोहराना है, और यह पुष्टि करें कि प्रत्येक संभावित परिणाम लगभग (1 / पक्षों की संख्या) बार मारा गया था। 6-पक्षीय मृत्यु के मामले में, आपको प्रत्येक संभावित मूल्य को लगभग 16.6% हिट देखना चाहिए। यदि कोई प्रतिशत से अधिक बंद है, तो आपको एक समस्या है।

इसे इस तरह से करने से बचा जाता है कि आप परीक्षण को बदले बिना, एक यादृच्छिक संख्या को आसानी से उत्पन्न करने के अंतर्निहित मैकेनिक को फिर से तैयार कर सकते हैं और सबसे महत्वपूर्ण बात।


1
यह परीक्षण एक पूरी तरह से गैर-यादृच्छिक कार्यान्वयन के लिए पारित होगा जो बस एक पूर्वनिर्धारित क्रम में एक-एक करके पक्षों से गुजरता है
gnat

1
यदि एक कोडर बुरी आस्था में कुछ लागू करने पर आमादा है (मरने पर एक यादृच्छिक एजेंट का उपयोग नहीं कर रहा है), और बस 'लाल बत्ती को हरा बनाने के लिए कुछ खोजने की कोशिश कर रहा है' तो आपको यूनिट परीक्षण की तुलना में वास्तव में हल हो सकती है।
क्रिस्टोफरब्रॉन
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.