2012-11-09 42 views
8

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

मैंने सुना है कि math.random लिए बीज वर्तमान समय माध्यम से उत्पन्न कर रहे हैं, यह सही है? उन्हें वर्तमान समय मिलि-सेकेंड या कुछ तक नीचे उपयोग करना चाहिए, क्योंकि यदि आपको नहीं मिला तो आपको एक ही परिणाम मिलेगा।

बीज वास्तव में क्या है? क्या यह समय "10:45" या समय और दिनांक जैसे "10:45 11/8/12" या कुछ संयोजन है?

मैं बीज कैसे ढूंढ सकता हूं, इसलिए मैं आउटपुट की भविष्यवाणी कर सकता हूं?

मैं इस प्लग करने के लिए सक्षम होना चाहते हैं:

alert(Math.floor((Math.random()*10)+1)); 
मेरी यूआरएल बार में

है, और परिणाम की भविष्यवाणी करने में सक्षम हो। क्या यह संभव है?

+0

'Math.random()' का पूरा बिंदु यह है कि आप इसकी भविष्यवाणी नहीं कर सकते (कम से कम, बिना किसी कठिनाई के)। –

+1

क्या कोई इस के लिए एक निश्चित उत्तर देने के लिए यहां 'v8' के स्रोत को पढ़ रहा है? – TiansHUo

+0

@TiansHUo - मैंने राइनो के स्रोत कोड को पढ़ा और मैंने जो पढ़ा है उसके आधार पर प्रश्न का उत्तर दिया: http://stackoverflow.com/a/13303029/783743 –

उत्तर

14

मैं जो छद्म यादृच्छिक समारोह वे का उपयोग पता लगाने के लिए राइनो source code के माध्यम से देखा। स्पष्ट रूप से वे fall backMath.random फ़ंक्शन को Java standard library में परिभाषित किया गया है।

Math.random के लिए दस्तावेज़ का कहना है:

एक सकारात्मक संकेत है, 1.0 से भी कम समय से अधिक या 0.0 के बराबर और के साथ एक डबल मान देता है। लौटाए गए मानों को उस सीमा से (लगभग) समान वितरण के साथ छद्म रूप से चुना जाता है।

जब इस विधि पहले कहा जाता है, यह केवल एक नया कूट-यादृच्छिक संख्या जनरेटर बनाता है, बिल्कुल के रूप में अगर अभिव्यक्ति

new java.util.Random 

द्वारा इस नए कूट-यादृच्छिक संख्या जनरेटर सभी कॉल्स के लिए प्रयोग किया जाता है उसके बाद इस विधि के लिए और कहीं और नहीं उपयोग किया जाता है।

यह विधि एक से अधिक धागे द्वारा सही उपयोग की अनुमति देने के लिए ठीक से सिंक्रनाइज़ किया गया है। हालांकि, अगर कई धागे को छद्म यादृच्छिक संख्याओं को एक महान दर पर उत्पन्न करने की आवश्यकता होती है, तो यह प्रत्येक धागे के लिए विवाद को कम कर सकता है ताकि उसका स्वयं का छद्म यादृच्छिक संख्या जनरेटर हो।

तो मैं java.util.Random के लिए दस्तावेज़ की जाँच की और this (डिफ़ॉल्ट निर्माता के लिए) में पाया गया:

एक नई यादृच्छिक संख्या जनरेटर बनाता है। इसके बीज वर्तमान समय के आधार मान पर आरंभ नहीं हो जाता:

public Random() { this(System.currentTimeMillis()); } 

दो रैंडम ही मिलीसेकंड में बनाई गई वस्तुओं यादृच्छिक संख्या का उसी क्रम होगा।

तो अब हम यह सुनिश्चित करने के लिए जानते हैं कि बीज मिलीसेकंड में वर्तमान समय है। इसके अलावा, second constructor के लिए दस्तावेज़ का कहना है:

public Random(long seed) { setSeed(seed); } 

विधि अगले द्वारा प्रयुक्त कूट-यादृच्छिक संख्या की स्थिति धारण करने के लिए:

एक भी लंबे समय से बीज का उपयोग करने के लिए एक नया यादृच्छिक संख्या जनरेटर बनाता है जनरेटर।

documentationsetSeed विधि के लिए कहते हैं:

एक भी लंबे समय से बीज का उपयोग कर इस यादृच्छिक संख्या जनरेटर के बीज सेट करता है। सेटसिड का सामान्य अनुबंध यह है कि यह इस यादृच्छिक संख्या जेनरेटर ऑब्जेक्ट की स्थिति को बदल देता है ताकि वास्तव में उसी स्थिति में हो जैसे कि यह बीज के रूप में तर्क बीज के साथ बनाया गया हो। इस प्रकार विधि setSeed वर्ग रैंडम द्वारा कार्यान्वित किया जाता:

synchronized public void setSeed(long seed) { 
    this.seed = (seed^0x5DEECE66DL) & ((1L << 48) - 1); 
    haveNextNextGaussian = false; 
} 

वर्ग रैंडम द्वारा setSeed के कार्यान्वयन को देखते हुए बीज का केवल 48 बिट का उपयोग होता है। आम तौर पर, हालांकि, एक ओवरराइडिंग विधि बीज तर्क के रूप में लंबे तर्क के सभी 64 बिट्स का उपयोग कर सकती है।नोट: हालांकि बीज मूल्य एक परमाणु है, लेकिन इस विधि को अभी भी NextNextGaussian के सही अर्थशास्त्र सुनिश्चित करने के लिए सिंक्रनाइज़ किया जाना चाहिए।

actual method यादृच्छिक संख्या उत्पन्न करने के लिए इस्तेमाल किया nextDouble है:

रिटर्न अगले कूट-यादृच्छिक, समान रूप से इस यादृच्छिक संख्या जनरेटर के अनुक्रम से 0.0 और 1.0 के बीच डबल मूल्य वितरित किए।

nextDouble समारोह के कार्यान्वयन इस प्रकार है:

public double nextDouble() { 
    return (((long)next(26) << 27) + next(27)) 
     /(double)(1L << 53); 
} 

जाहिर है यह dependsnext समारोह पर:

अगले कूट-यादृच्छिक संख्या उत्पन्न करता है। Subclass इसे ओवरराइड करना चाहिए, क्योंकि यह अन्य सभी तरीकों से प्रयोग किया जाता है।

synchronized protected int next(int bits) { 
    seed = (seed * 0x5DEECE66DL + 0xBL) & ((1L << 48) - 1); 
    return (int)(seed >>> (48 - bits)); 
} 

छद्म यादृच्छिक समारोह के लिए आप देख रहे हैं कि:

next समारोह के कार्यान्वयन इस प्रकार है। यह दस्तावेज में कहा है के रूप में: Seminumerical एल्गोरिदम, खंड 3.2:

यह एक रैखिक congruential कूट-यादृच्छिक संख्या जनरेटर, के रूप में DH लेह्मर द्वारा परिभाषित और कंप्यूटर प्रोग्रामिंग, खंड 2 कला में डोनाल्ड ई नुथ द्वारा वर्णित है। 1।

नोट हालांकि यह केवल राइनो द्वारा उपयोग किया जाने वाला यादृच्छिक संख्या जनरेटर है। स्पाइडरमॉकी और वी 8 जैसे अन्य कार्यान्वयनों में अपना स्वयं का छद्म-यादृच्छिक संख्या जेनरेटर हो सकता है।

+0

+1, अद्भुत जवाब, इसलिए इसका मतलब है कि कम से कम मैं समय की सटीकता के आधार पर संभावित समय की एक श्रृंखला का आकलन कर सकता हूं, और कम से कम मुझे संभावित यादृच्छिक संख्याओं की एक सूची मिल सकती है (जो सुरक्षा कारणों से निश्चित रूप से असुरक्षित है)। लेकिन मूल प्रश्न के लिए, शायद नहीं, जब तक कि आप वास्तव में मिलीसेकंड सही नहीं प्राप्त कर सकते। – TiansHUo

+0

@Aadit आप सही हैं कि यह कार्यान्वयन पर निर्भर करता है, यदि आप जावास्क्रिप्ट का उपयोग करके वेबपैप लिख रहे हैं, तो विभिन्न वेब ब्राउज़र अलग-अलग छद्म यादृच्छिक संख्या जेनरेटर का उपयोग करते हैं। विशिष्ट अनुप्रयोगों के लिए यह विनाश का कारण बन सकता है। सभी वांछित "यादृच्छिक" गुणों - मजबूत धारावाहिक सहसंबंध होने पर रैखिक संयोग विधि कुख्यात रूप से खराब हैं। Http://stackoverflow.com/questions/19507469/math-random-and-web-programming-in-javascript देखें। महान जवाब बीटीडब्ल्यू। – MHH

0

बीज एक संख्यात्मक मान है, इसलिए मेरा अनुमान है कि अगर आप Date.now() (या new Date().getTime() पुराने ब्राउज़र के लिए) कहते हैं तो यह आपको मिलेगा।

हालांकि, मैं नहीं यकीन है कि जब कि बीज लिया जाता है कर रहा हूँ, या बीज पूरे ब्राउज़र प्रक्रिया के लिए आम वर्तमान पृष्ठ के लिए अलग या जाता है। यादृच्छिक संख्याओं की भविष्यवाणी करना बहुत मुश्किल या असंभव माना जाता है, यह उनका पूरा बिंदु यादृच्छिक है।

6

यह संभावना है कि मिलीसेकंड गिनती से बीज के लिए और भी कुछ है, क्योंकि आप उसी मिलिसेकंड में कई बार Math.random() को कॉल कर सकते हैं और यह हर बार एक अलग मूल्य लौटाएगा।

for (var i = 0; i < 3; i++) { 
    console.log(Math.random(), (new Date()).getTime()); 
}; 

मेरे उत्पादन:

0.0617244818713516 1352433709108 
0.8024995378218591 1352433709108 
0.2409922298975289 1352433709108 

अगर मैं लागू कर रहे थे मैं एक millisecond गणना के आधार पर प्रारंभिक बीज बना सकता है, और उसके बाद 1 हर बार यह कहा जाता है जोड़ने के लिए, ताकि आप नहीं मिलेगा वही बीज मूल्य दो बार।

Math.random = function() { return .5; }; 

अब Math.random() हमेशा .5 वापस आ जाएगी:

यहाँ Math.random() से उत्पादन की भविष्यवाणी की एक 100% सही तरीका है।

+0

@ 43.52.4 डी। पता लगाने का एक तरीका है। इसे शुरू करना, दस वर्षों में हमारे पास जवाब होगा, यानी, यदि यह संभव है या नहीं ... क्या आप असली हैं ?! – gdoron

+0

क्रोम के Math.random() के पीछे कोड यहां है: http://code.google.com/p/v8/source/browse/trunk/src/v8.cc#170 ऐसा लगता है कि यह मूल रूप से आपके सिस्टम का उपयोग करने जा रहा है यादृच्छिक संख्या जेनरेटर, तो यह अंततः आपके ओएस के आरएनजी पर कितना अच्छा है। – evan

0

नहीं, आप बीज अनुमान नहीं लगा सकते, लेकिन आप preemtively सही रूप में जानवर बल के लिए एक मैच के क्रम में पर्याप्त संख्या उत्पन्न कर सकते हैं।

किसी भी तरह, आरएनजी के http://en.wikipedia.org/wiki/Random_number_generation पर विकी पेज पढ़ने से शुरू करें, पीआरएनजी के व्यावहारिक कार्यान्वयन पर नजर डालें।