AR-MHアルゴリズム
プログラム
#include <oxstd.h> #include <oxprob.h> #include <oxfloat.h> #include <oxdraw.h> #import<maximize> //Calculate variance of time series fTsvar(const x, const Bm){ decl n,sp; // Calculate Spectral density function using // Bandwidth=Bm at 2 points (0, pi) and Parzen Window n=rows(x);sp=periodogram(x,Bm,2,1)/n; return M_2PI*sp[0]; } fTsvar_batch(const x, const n){ // N=n*m decl i,m,N,y,xbar; N=rows(x);m=N/n;xbar=meanc(x);y=zeros(m,1); for(i=0;i<m;++i){y[i]=meanc(x[i*n:(i+1)*n-1]);} return n/(m-1)*sumsqrc(y-xbar); } // Calculate p-value for Convergence (Geweke's Method) // H0: Convergence, H1: No Convergence fGeweke(const x, const Bm){ decl n,n1,n2,sp1,sp2,var1,var2,x1,x2,x1bar,x2bar,z; n=rows(x);n1=floor(0.1*n);n2=floor(0.5*n); x1=x[:n1-1];x2=x[n-n2:]; x1bar=meanc(x1);x2bar=meanc(x2); var1=fTsvar(x1,Bm);var2=fTsvar(x2,Bm); z=(x1bar-x2bar)/sqrt(var1/n1+var2/n2); return 2*tailn(fabs(z)); } static decl x; fLk(const dA, const adFunc, const avScore, const amHess) { decl alpha,nobs;nobs=rows(x);alpha=dA; adFunc[0]=-nobs*loggamma(alpha)+(alpha-1)*sumc(log(x))-sumc(x)-log(alpha); if(avScore){avScore[0]=-nobs*polygamma(alpha,0)+sumc(log(x))-1/alpha;} if(amHess){amHess[0]=-nobs*polygamma(alpha,1)+1/alpha^2;} return 1; } // main(){ decl a,a_m,a_n,a_o,a_s,i,n,nobs; decl frac,h_n,h_o,l_m,l_n,l_o,l1_m,l2_m,mu,var; decl burn,ar_count,ar_accept,mh_accept,mh_count; decl Bm,file,n_acf; a=1;nobs=1000; // Generate Dataset X_1,...,X_n ~ Gamma(a,1) x=rangamma(nobs,1,a,1); // Find the mode of L(a). initial value: a a_m=a;MaxBFGS(fLk,&a_m,&l_m,0,0);println("mode=",a_m); fLk(a_m,&l_m,&l1_m,&l2_m);var=-1/l2_m;mu=a_m+l1_m*var; // n=10000;burn=0.1*n;a_s=zeros(n,1); ar_count=ar_accept=mh_count=mh_accept=0; for(i=-burn;i<n;++i){ a_o=a;fLk(a_o,&l_o,0,0); // AR Step if(fmod(i,100)==0){println(i~a);} h_o=l_m+(a_o-a_m)*l1_m+0.5*(a_o-a_m)^2*l2_m; do{ do{a_n=mu+rann(1,1)*sqrt(var);}while(a_n<=0); fLk(a_n,&l_n,0,0); h_n=l_m+(a_n-a_m)*l1_m+0.5*(a_n-a_m)^2*l2_m; ar_count+=1; } while(ranu(1,1)>=exp(l_n-h_n)); ar_accept+=1; // MH Step frac=exp(l_n+min(l_o|h_o)-l_o-min(l_n|h_n)); if(ranu(1,1) <= frac){a=a_n;mh_accept+=1;} mh_count+=1; if(i>=0){a_s[i]=a;} } println("AR acceptance=",ar_accept/ar_count); println("MH acceptance=",mh_accept/mh_count); Bm=0.1*n; //Bm=0; println( "%r",{"ALPHA"}, "%c",{"Mean","Stdev","95%L","95%U","Geweke"}, meanc(a_s)~varc(a_s)^0.5~quantilec(a_s,<0.025,0.975>)'~fGeweke(a_s,Bm),"\n"); // n_acf=500; //ACF DrawCorrelogram(0,a_s',{"ALPHA"},n_acf); DrawTitle(0,"Sample ACF"); //Path DrawTMatrix(1,a_s',{"ALPHA"},1,1,1); DrawTitle(1,"Sample Path"); //Posterior density DrawDensity(2,a_s',{"ALPHA"},1,1,0); DrawTitle(2,"Posterior Density"); SaveDrawWindow("ar-mh.ps"); CloseDrawWindow(); // file = fopen("a.txt","w");fprint(file,"a","%15.10f",a_s);fclose(file); }
結果
mode= 1.0090 -1000.0 1.0000 -900.00 1.0080 (途中略) 9600.0 1.0030 9700.0 1.0262 9800.0 1.0400 9900.0 0.98925 AR acceptance=0.99719 MH acceptance=0.995818 Mean Stdev 95%L 95%U Geweke ALPHA 1.0092 0.024840 0.96075 1.0586 0.090136