我有以下算法
步骤1.生成u1和u2〜U(0,1)
第2步。定义v1 = 2u1-1,v2 = 2u2-1和s = v1 ^ 2 + v2 ^ 2
第3步。如果s> 1,请返回第1步。
步骤4。如果s <= 1,则x = v1(-2logs / s)^(1/2)和y = v2(-2logs / s)^(1/2)
这是我在R中实现此算法的方法:
PolarMethod1<-function(N)
{
x<-numeric(N)
y<-numeric(N)
z<-numeric(N)
i<-1
while(i<=N)
{u1<-runif(1)
u2<-runif(1)
v1<-(2*u1)-1
v2<-(2*u2)-1
s<-(v1^2)+(v2^2)
if(s<=1)
{
x[i]<-((-2*log(s)/s)^(1/2))*v1
y[i]<-((-2*log(s)/s)^(1/2))*v2
z[i]<-(x[i]+y[i])/sqrt(2) #standarization
i<-i+1
}
else
i<-i-1
}
return(z)
}
z<-PolarMethod1(10000)
hist(z,freq=F,nclass=10,ylab="Density",col="purple",xlab=" z values")
curve(dnorm(x),from=-3,to=3,add=TRUE)
幸运的是,该代码未标记任何错误,并且与N=1000
配合得很好,但是当我更改为N=10000
时,而不是对曲线显示进行更好的处理:
显示N = 1000的对比度:
那是为什么?
我的代码有问题吗?当N
增加时,应该调整得更好。
注意:我在代码中添加了z
,以在输出中包括两个变量。
答案 0 :(得分:2)
在绘制直方图时,您需要10个bin,但这只是一个建议。您实际上有8个,因为要覆盖从-4到4的范围,就不会将其划分为10个bin,最终得到漂亮的整数,而8个bin的边界非常好。
如果您想要更多箱,则不要指定nclass
。默认给了我20个垃圾箱。或指定breaks = "Scott"
,它使用不同的规则来选择垃圾箱。我看到大约80个垃圾箱使用了此选项。
答案 1 :(得分:2)
为什么运行1000和100000之间会有差异?
运行1000次仿真时,z值通常从-3.2到3.2。但是,如果将行程增加到100k,您将获得更多的极值,z将从-4变为4。
直方图将z结果分为10个bin。 z的较大范围将导致较宽的分档,并且较宽的分档通常会更差地调整概率密度。
您的纸箱宽度(用于1000次运行)大约为0.5,但对于100k,则为1。