我試圖用拒絕方法在Fortran中的均勻分佈值中創建正態分佈。它實際上或多或少地運作良好,但我並不完全符合我想要的結果。用拒絕方法創建正態分佈產生錯誤的前因子
我生成與該段的代碼
function generator result(c)
implicit none
integer, dimension(2) :: clock
double precision :: c,d
call System_clock(count=clock(1))
call random_seed(put=clock)
!initialize matrix with random values
call random_number(c)
end function
subroutine Rejection(aa,bb,NumOfPoints)
implicit none
double precision :: xx, yy, cc
integer :: ii, jj, kk
integer, intent(in) :: NumOfPoints
double precision, intent(in) :: aa, bb
cc=1
xx=generator()
allocate(rejectionArray(NumOfPoints))
do ii=1, NumOfPoints
call random_number(xx)
xx=aa+(bb-aa)*xx
call random_number(yy)
do while(cc*yy>1/sqrt(pi)*exp(-xx**2))
call random_number(xx)
xx=aa+xx*(bb-aa)
call random_number(yy)
end do
rejectionArray(ii)=xx
end do
end subroutine
正態分佈由於我使用作爲函數1/PI * EXP(-x^2),I認爲正態分佈,我獲得也應該給予前因子1/pi ^(1/2)的分佈,但它不是。如果我創建了一個直方圖並用正態分佈擬合這個直方圖,我可以得到約0.11的前因子。
這怎麼可能?我究竟做錯了什麼?
編輯:這是我如何創建直方圖
implicit none
double precision :: aa, bb
integer :: NumOfPoints, ii, kk, NumOfBoxes, counter, CounterTotal,counterTotal2
logical :: exists
character(len=15) :: frmat
double precision :: Intermediate
%read NumOfPoints (Total amount of random numbers), NumOfBoxes
%(TotalAmountofBins)
open(unit=39, action='read', status='old', name='samples.txt')
read(39,*) NumOfPoints, aa, bb, NumOfBoxes
close(39)
% number of Counts will be stored temporarily in 'counter'
counter=0
open(unit=39, action='write', status='replace', name='distRejection.txt')
Call Rejection(aa,bb,NumOfPoints)
do ii=1, NumOfBoxes
counter=0
%calculate the middle of the bin
Intermediate=aa+(2*ii-1)*((bb-aa)/NumOfBoxes)/2
%go through all the random numbers and check if they are within
% one of the bins. If they are in one bin -->increase Counter
% by one
do kk=1, size(rejectionArray,1)
if(abs(RejectionArray(kk)-intermediate).le.((bb-aa)/NumOfBoxes/2)) then
counter=counter+1
end if
end do
%save Points + relative number of Counts in file
write(39,100)intermediate,dble(counter)/dble(NumOfPoints)
100 format (f10.3,T20,f10.3,/)
end do
close(39)
前因子現在是0.056的是1/SQRT(PI)* 1月10日。這是我想要的prefactor的1/10。問題是如果我放大我整合函數的區域,這個前因子不會變得更好。這意味着如果使用此代碼創建-5000到+ 5000的分佈,那麼即使該函數的-5000到5000的積分導致我使用的分佈爲0.2,我仍然可以獲得相同的前因子。 (我把隨機分佈的值放到matlab中,並用這些值計算-5000到5000的數值積分,得到0.2,這意味着這裏積分的前因子應該是1/pi * 1/5。 ,我很困惑的事實是積分從-5000到+50000的高斯僅爲0.2,根據數學這個積分約爲1.所以有些事情是錯的)
問題不在於我沒有獲得高斯分佈。我獲得的分佈是一個或多或少完美的高斯分佈。問題是當我用gnuplot分配分佈時,擬合參數是錯誤的。我應該獲得作爲前因子1/pi或多或少0.56,但我得到0.11而不是 – anonymous
由於您問:我自己創建直方圖。我寫了一個函數,將所有數據點計算在一些分箱內,然後用gnuplot對其進行繪圖。 – anonymous
由於幾個原因,結果不能是完美的高斯分佈。 (i)使用有限數量的計數將導致分佈中的「噪聲」。 (ii)有限範圍意味着分佈不是在無窮大,+無窮大但是aa,bb上歸一化的。如果您已經考慮到這一點,完整的Fortran和gnuplot代碼可以幫助調查問題。 –