मैं एक समान वितरण (जैसा कि सबसे यादृच्छिक संख्या जनरेटर का उत्पादन करता हूं, जैसे 0.0 और 1.0 के बीच) को सामान्य वितरण में कैसे बदल सकता हूं? क्या होगा यदि मुझे मेरे चयन का एक मतलब और मानक विचलन चाहिए?
मैं एक समान वितरण (जैसा कि सबसे यादृच्छिक संख्या जनरेटर का उत्पादन करता हूं, जैसे 0.0 और 1.0 के बीच) को सामान्य वितरण में कैसे बदल सकता हूं? क्या होगा यदि मुझे मेरे चयन का एक मतलब और मानक विचलन चाहिए?
जवाबों:
Ziggurat एल्गोरिथ्म इस के लिए बहुत कुशल हालांकि है, बॉक्स-मुलर को बदलने लागू करना आसान खरोंच से (और पागल धीमी गति से नहीं है)।
बहुत सारे तरीके हैं:
किसी भी फ़ंक्शन के वितरण को दूसरे में बदलना, आपके इच्छित फ़ंक्शन के व्युत्क्रम का उपयोग करना शामिल है।
दूसरे शब्दों में, यदि आप किसी विशिष्ट प्रायिकता फ़ंक्शन p (x) का लक्ष्य रखते हैं, तो आप इस पर एकीकरण करके वितरण प्राप्त करते हैं -> d (x) = इंटीग्रल (p (x)) और इसके व्युत्क्रम का उपयोग करें: Inv (d (x)) । अब यादृच्छिक संभाव्यता फ़ंक्शन (जिसमें एक समान वितरण है) का उपयोग करें और फ़ंक्शन आमंत्रण (d (x)) के माध्यम से परिणाम मान डालें। आपके द्वारा चुने गए फ़ंक्शन के अनुसार आपको वितरण के साथ यादृच्छिक मान प्राप्त होने चाहिए।
यह जेनेरिक गणित दृष्टिकोण है - इसका उपयोग करके अब आप किसी भी संभावना या वितरण फ़ंक्शन को चुन सकते हैं, जब तक कि इसका उलटा या अच्छा उलटा सन्निकटन हो।
आशा है कि इस मदद और वितरण का उपयोग करने के बारे में छोटी टिप्पणी के लिए धन्यवाद और संभावना ही नहीं।
यहां बॉक्स-मुलर परिवर्तन के ध्रुवीय रूप का उपयोग करके एक जावास्क्रिप्ट कार्यान्वयन है।
/*
* Returns member of set with a given mean and standard deviation
* mean: mean
* standard deviation: std_dev
*/
function createMemberInNormalDistribution(mean,std_dev){
return mean + (gaussRandom()*std_dev);
}
/*
* Returns random number in normal distribution centering on 0.
* ~95% of numbers returned should fall between -2 and 2
* ie within two standard deviations
*/
function gaussRandom() {
var u = 2*Math.random()-1;
var v = 2*Math.random()-1;
var r = u*u + v*v;
/*if outside interval [0,1] start over*/
if(r == 0 || r >= 1) return gaussRandom();
var c = Math.sqrt(-2*Math.log(r)/r);
return u*c;
/* todo: optimize this algorithm by caching (v*c)
* and returning next time gaussRandom() is called.
* left out for simplicity */
}
अपने लाभ के लिए केंद्रीय सीमा प्रमेय विकिपीडिया प्रविष्टि मैथवर्ल्ड प्रविष्टि का उपयोग करें।
समान रूप से वितरित संख्याओं के n उत्पन्न करें, उन्हें योग करें, n * 0.5 घटाएं और आपके पास लगभग सामान्य वितरण का उत्पादन 0 के बराबर होता है और समान रूप से भिन्न होता है (1/12) * (1/sqrt(N))
( उस अंतिम एक के लिए समान वितरण पर विकिपीडिया देखें )
n = 10 आपको कुछ अच्छा आधा उपवास देता है। यदि आप टायलर समाधान के लिए आधे से अधिक सभ्य चाहते हैं (जैसा कि सामान्य वितरण पर विकिपीडिया प्रविष्टि में उल्लेख किया गया है )
मैं बॉक्स-मुलर का उपयोग करूंगा। इसके बारे में दो बातें:
जहाँ R1, R2 यादृच्छिक समरूप संख्याएँ हैं:
1, sqrt (-2 * लॉग (R1)) * cos (2 * p * * R2) के एसडी के साथ सामान्य वितरण
यह सटीक है ... उन सभी धीमी छोरों को करने की कोई आवश्यकता नहीं है!
यह अविश्वसनीय लगता है कि मैं आठ साल के बाद इसमें कुछ जोड़ सकता हूं, लेकिन जावा के मामले में मैं पाठकों को रैंडम.नेक्स्टगॉसियन () विधि की ओर संकेत करना चाहूंगा , जो आपके लिए औसत 0.0 और मानक भक्ति 1.0 के साथ गौसियन वितरण उत्पन्न करता है।
एक साधारण जोड़ और / या गुणा आपकी आवश्यकताओं के औसत और मानक विचलन को बदल देगा।
मानक अजगर पुस्तकालय मॉड्यूल यादृच्छिक आप क्या चाहते हैं:
normalvariate (mu, sigma)
सामान्य वितरण। म्यू मतलब है, और सिग्मा मानक विचलन है।
एल्गोरिथ्म के लिए, पायथन लाइब्रेरी में random.py के फ़ंक्शन पर एक नज़र डालें।
डोनाल्ड नथ की पुस्तक द आर्ट ऑफ़ कंप्यूटर प्रोग्रामिंग की धारा 3.4.1 से यह एल्गोरिथम पी ( सामान्य विचलन के लिए ध्रुवीय विधि ) का मेरा जावास्क्रिप्ट कार्यान्वयन है :
function normal_random(mean,stddev)
{
var V1
var V2
var S
do{
var U1 = Math.random() // return uniform distributed in [0,1[
var U2 = Math.random()
V1 = 2*U1-1
V2 = 2*U2-1
S = V1*V1+V2*V2
}while(S >= 1)
if(S===0) return 0
return mean+stddev*(V1*Math.sqrt(-2*Math.log(S)/S))
}
मुझे लगता है कि तुम EXCEL में यह कोशिश करनी चाहिए: =norminv(rand();0;1)
:। यह यादृच्छिक संख्याओं का उत्पादन करेगा जो सामान्य रूप से शून्य माध्य और एकजुट संस्करण के साथ वितरित किया जाना चाहिए। "0" किसी भी मूल्य के साथ आपूर्ति की जा सकती है, ताकि संख्या वांछित साधन की हो, और "1" को बदलकर, आपको अपने इनपुट के वर्ग के बराबर विचरण मिलेगा।
उदाहरण के लिए: =norminv(rand();50;3)
MEAN = 50 VARIANCE = 9 के साथ सामान्य रूप से वितरित संख्याओं के लिए उपज होगी।
Q मैं एक समान वितरण (जैसे सबसे यादृच्छिक संख्या जनरेटर का उत्पादन, जैसे 0.0 और 1.0 के बीच) को सामान्य वितरण में कैसे बदल सकता हूं?
सॉफ्टवेयर कार्यान्वयन के लिए मुझे युगल यादृच्छिक जनरेटर नाम पता हैं जो आपको [0,1] में एक छद्म वर्दी यादृच्छिक अनुक्रम देते हैं (मेरसेन ट्विस्टर, लीनियर कग्रेट जेनरेटर)। चलो इसे यू (एक्स) कहते हैं
यह गणितीय क्षेत्र है, जिसे संभाव्यता सिद्धांत कहा जाता है। पहली बात: यदि आप अभिन्न वितरण F के साथ rv मॉडल करना चाहते हैं तो आप F ^ -1 (U (x)) का मूल्यांकन करने का प्रयास कर सकते हैं। Pr.theory में यह साबित हुआ कि ऐसे rv का अभिन्न वितरण F होगा।
चरण 2 किसी भी गिनती के तरीकों के उपयोग के बिना आरवी ~ एफ उत्पन्न करने के लिए प्रशंसनीय हो सकता है जब एफ -1 को समस्याओं के बिना विश्लेषणात्मक रूप से प्राप्त किया जा सकता है। (उदा। विस्तार)
सामान्य वितरण को मॉडल करने के लिए आप y1 * cos (y2) को कैसक्यूलेट कर सकते हैं, जहां y1 ~ [0,2pi] में समान है। और y2 रेले वितरण है।
प्रश्न: क्या होगा अगर मुझे मेरे चयन का एक मतलब और मानक विचलन चाहिए?
आप सिग्मा * N (0,1) + m की गणना कर सकते हैं।
यह दिखाया जा सकता है कि इस तरह की शिफ्टिंग और स्केलिंग से N (m, sigma) को बढ़ावा मिलता है
यह बॉक्स-मुलर परिवर्तन के ध्रुवीय रूप का उपयोग करके एक मैटलैब कार्यान्वयन है :
समारोह randn_box_muller.m
:
function [values] = randn_box_muller(n, mean, std_dev)
if nargin == 1
mean = 0;
std_dev = 1;
end
r = gaussRandomN(n);
values = r.*std_dev - mean;
end
function [values] = gaussRandomN(n)
[u, v, r] = gaussRandomNValid(n);
c = sqrt(-2*log(r)./r);
values = u.*c;
end
function [u, v, r] = gaussRandomNValid(n)
r = zeros(n, 1);
u = zeros(n, 1);
v = zeros(n, 1);
filter = r==0 | r>=1;
% if outside interval [0,1] start over
while n ~= 0
u(filter) = 2*rand(n, 1)-1;
v(filter) = 2*rand(n, 1)-1;
r(filter) = u(filter).*u(filter) + v(filter).*v(filter);
filter = r==0 | r>=1;
n = size(r(filter),1);
end
end
और histfit(randn_box_muller(10000000),100);
यह परिणाम है:
जाहिर है कि यह वास्तव में अक्षम है, जिसमें निर्मित मलबे की तुलना में रैंडन है ।
मेरे पास निम्नलिखित कोड हैं जो शायद मदद कर सकते हैं:
set.seed(123)
n <- 1000
u <- runif(n) #creates U
x <- -log(u)
y <- runif(n, max=u*sqrt((2*exp(1))/pi)) #create Y
z <- ifelse (y < dnorm(x)/2, -x, NA)
z <- ifelse ((y > dnorm(x)/2) & (y < dnorm(x)), x, z)
z <- z[!is.na(z)]
कार्यान्वित फ़ंक्शन रेनॉर्म () का उपयोग करना भी आसान है क्योंकि यह सामान्य वितरण के लिए यादृच्छिक संख्या जनरेटर लिखने की तुलना में तेज़ है। निम्न कोड को साबित के रूप में देखें
n <- length(z)
t0 <- Sys.time()
z <- rnorm(n)
t1 <- Sys.time()
t1-t0
function distRandom(){
do{
x=random(DISTRIBUTION_DOMAIN);
}while(random(DISTRIBUTION_RANGE)>=distributionFunction(x));
return x;
}