mirror of
https://bitbucket.org/cosmicvoids/vide_public.git
synced 2025-07-04 15:21:11 +00:00
Merge branch 'master' of https://bitbucket.org/cosmicvoids/vide_public
This commit is contained in:
commit
1ec0d26b20
29 changed files with 2187 additions and 5963 deletions
|
@ -1,161 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <time.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
void output_matter_power_spectrum()
|
|
||||||
{
|
|
||||||
int k;
|
|
||||||
double dlogk,xk,plin,pnl;
|
|
||||||
FILE *fp;
|
|
||||||
char aa[100];
|
|
||||||
|
|
||||||
fprintf(stderr,"\n\nCALCULATING MATTER POWER SPECTRA.\n");
|
|
||||||
fprintf(stderr, "---------------------------------\n\n");
|
|
||||||
|
|
||||||
sprintf(aa,"%s.matter_pk",Task.root_filename);
|
|
||||||
fp = fopen(aa,"w");
|
|
||||||
|
|
||||||
for(k=-300;k<=100;++k)
|
|
||||||
{
|
|
||||||
xk=pow(10.0,k/100.0);
|
|
||||||
plin = linear_power_spectrum(xk)/(xk*xk*xk)*TWOPI*PI;
|
|
||||||
pnl = nonlinear_power_spectrum(xk)/(xk*xk*xk)*TWOPI*PI;
|
|
||||||
fprintf(fp,"%e %e %e\n",xk,plin,pnl);
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
void output_matter_correlation_function()
|
|
||||||
{
|
|
||||||
int k,nr=50;
|
|
||||||
double dlogr,r,xlin,xnl,rmin = 0.05,rmax = 80.0;
|
|
||||||
FILE *fp;
|
|
||||||
char aa[100];
|
|
||||||
|
|
||||||
fprintf(stderr,"\n\nCALCULATING MATTER CORRELATION FUNCTIONIONS.\n");
|
|
||||||
fprintf(stderr, "--------------------------------------------\n\n");
|
|
||||||
|
|
||||||
sprintf(aa,"%s.matter_xi",Task.root_filename);
|
|
||||||
fp = fopen(aa,"w");
|
|
||||||
|
|
||||||
dlogr = (log(rmax) - log(rmin))/(nr-1);
|
|
||||||
|
|
||||||
for(k=0;k<nr;++k)
|
|
||||||
{
|
|
||||||
r = exp(k*dlogr)*rmin;
|
|
||||||
xlin = xi_linear_interp(r);
|
|
||||||
xnl = xi_interp(r);
|
|
||||||
fprintf(fp,"%e %e %e\n",r,xlin,xnl);
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
}
|
|
||||||
|
|
||||||
void output_halo_correlation_function(double mass)
|
|
||||||
{
|
|
||||||
int k,nr=50;
|
|
||||||
double dlogr,r,xlin,xnl,rmin = 0.15,rmax = 40.0;
|
|
||||||
FILE *fp;
|
|
||||||
char aa[100];
|
|
||||||
|
|
||||||
fprintf(stderr,"\n\nCALCULATING HALO CORRELATION FUNCTIONION (M=%.2e)\n",mass);
|
|
||||||
fprintf(stderr, "-------------------------------------------------\n\n");
|
|
||||||
|
|
||||||
sprintf(aa,"%s.halo_xi",Task.root_filename);
|
|
||||||
fp = fopen(aa,"w");
|
|
||||||
|
|
||||||
rmin = pow(3*mass/(4*DELTA_HALO*PI*RHO_CRIT*OMEGA_M),THIRD);
|
|
||||||
|
|
||||||
dlogr = (log(rmax) - log(rmin))/(nr-1);
|
|
||||||
|
|
||||||
for(k=0;k<nr;++k)
|
|
||||||
{
|
|
||||||
r = exp(k*dlogr)*rmin;
|
|
||||||
xlin = bias_interp(mass,r);
|
|
||||||
xnl = xi_interp(r);
|
|
||||||
fprintf(fp,"%e %e\n",r,xnl*xlin*xlin);
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
}
|
|
||||||
|
|
||||||
void output_matter_variance()
|
|
||||||
{
|
|
||||||
int k,nr=50;
|
|
||||||
double dlogr,r,slin,snl,mass,rmin = 0.05,rmax = 80.0,pnorm,pnorm_nl;
|
|
||||||
FILE *fp;
|
|
||||||
char aa[100];
|
|
||||||
|
|
||||||
fprintf(stderr,"\n\nCALCULATING MATTER VARIANCE.\n");
|
|
||||||
fprintf(stderr, "----------------------------\n\n");
|
|
||||||
|
|
||||||
sprintf(aa,"%s.sigma_r",Task.root_filename);
|
|
||||||
fp = fopen(aa,"w");
|
|
||||||
|
|
||||||
dlogr = (log(rmax) - log(rmin))/(nr-1);
|
|
||||||
pnorm = SIGMA_8/sigmac(8.0);
|
|
||||||
pnorm_nl = pnorm*sigmac(80.0)/nonlinear_sigmac(80.0);
|
|
||||||
|
|
||||||
for(k=0;k<nr;++k)
|
|
||||||
{
|
|
||||||
r = exp(k*dlogr)*rmin;
|
|
||||||
mass = 4./3.*PI*r*r*r*RHO_CRIT*OMEGA_M;
|
|
||||||
slin = sigmac(r)*pnorm;
|
|
||||||
snl = nonlinear_sigmac(r)*pnorm_nl;
|
|
||||||
fprintf(fp,"%e %e %e %e\n",r,slin,snl,mass);
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
void output_halo_concentrations()
|
|
||||||
{
|
|
||||||
int k,nr=100;
|
|
||||||
double x,dlogm,m,mvir,cdelta,mmin=1e8,mmax=1e16,delta_vir;
|
|
||||||
FILE *fp;
|
|
||||||
char aa[100];
|
|
||||||
|
|
||||||
fprintf(stderr,"\n\nCALCULATING HALO CONCENTRATIONS.\n");
|
|
||||||
fprintf(stderr, "--------------------------------\n\n");
|
|
||||||
|
|
||||||
sprintf(aa,"%s.cvir",Task.root_filename);
|
|
||||||
fp = fopen(aa,"w");
|
|
||||||
|
|
||||||
dlogm = (log(mmax) - log(mmin))/(nr-1);
|
|
||||||
x=OMEGA_M-1;
|
|
||||||
delta_vir=(18*PI*PI+82*x-39*x*x)/(1+x);
|
|
||||||
|
|
||||||
for(k=0;k<nr;++k)
|
|
||||||
{
|
|
||||||
m = exp(k*dlogm)*mmin;
|
|
||||||
cdelta = halo_concentration(m);
|
|
||||||
fprintf(fp,"%e %e\n",m,cdelta);
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
void output_halo_mass_function()
|
|
||||||
{
|
|
||||||
int k,nr=100;
|
|
||||||
double x,dlogm,m,mvir,cdelta,mmin=1e8,mmax=1e16,delta_vir;
|
|
||||||
FILE *fp;
|
|
||||||
char aa[100];
|
|
||||||
|
|
||||||
fprintf(stderr,"\n\nCALCULATING HALO MASS FUNCTION.\n");
|
|
||||||
fprintf(stderr, "-------------------------------\n\n");
|
|
||||||
|
|
||||||
sprintf(aa,"%s.massfunc",Task.root_filename);
|
|
||||||
fp = fopen(aa,"w");
|
|
||||||
|
|
||||||
dlogm = (log(mmax) - log(mmin))/(nr-1);
|
|
||||||
|
|
||||||
for(k=0;k<nr;++k)
|
|
||||||
{
|
|
||||||
m = exp(k*dlogm)*mmin;
|
|
||||||
x = dndM_interp(m);
|
|
||||||
fprintf(fp,"%e %e\n",m,x);
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
}
|
|
|
@ -1,73 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* This calculates the linear growthfactor at redshift z.
|
|
||||||
* Currently, the default is a flat LCDM universe, but can easily
|
|
||||||
* be changed.
|
|
||||||
*/
|
|
||||||
double x03_g1,
|
|
||||||
xi3_g1;
|
|
||||||
double func_D0(double);
|
|
||||||
double func_Di(double);
|
|
||||||
|
|
||||||
double growthfactor(double z)
|
|
||||||
{
|
|
||||||
int i;
|
|
||||||
double zp1,x03,xi3,bi,b0,yy,sqx,sqx1,dbdx,x0,xi,lambda_i,htemp,omega_L,omega_i,hubble_i,
|
|
||||||
astart,fac,redshift;
|
|
||||||
|
|
||||||
redshift=z;
|
|
||||||
astart=1.0/(z+1);
|
|
||||||
zp1=redshift+1;
|
|
||||||
omega_L=1-OMEGA_M;
|
|
||||||
|
|
||||||
hubble_i = sqrt(OMEGA_M/(astart*astart*astart) +
|
|
||||||
(1.0-OMEGA_M-omega_L)/(astart*astart) +omega_L);
|
|
||||||
|
|
||||||
if(omega_L>0)
|
|
||||||
{
|
|
||||||
lambda_i=omega_L/(omega_L+(1.0-OMEGA_M-omega_L)*zp1*zp1+OMEGA_M*pow(zp1,3.0));
|
|
||||||
omega_i=OMEGA_M*pow(zp1,3.0)*lambda_i/omega_L;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
lambda_i=0;
|
|
||||||
omega_i=OMEGA_M*zp1/(1.0+OMEGA_M*redshift);
|
|
||||||
}
|
|
||||||
|
|
||||||
fac=astart;
|
|
||||||
|
|
||||||
if((OMEGA_M < 0.99) && (omega_L > 0.001))
|
|
||||||
{
|
|
||||||
x03_g1=x03=1.0/OMEGA_M-1.0;
|
|
||||||
xi3_g1=xi3=1.0/omega_i-1.0;
|
|
||||||
b0 = qromo(func_D0,0.0,1.0,midpnt);
|
|
||||||
bi = qromo(func_Di,0.0,1.0,midpnt);
|
|
||||||
b0=b0*sqrt(x03+1.0);
|
|
||||||
bi=bi*sqrt(xi3+1.0)*astart;
|
|
||||||
fac=bi/b0;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
if((OMEGA_M < 0.99) && (omega_L == 0))
|
|
||||||
{
|
|
||||||
x0=1.0/OMEGA_M-1.0;
|
|
||||||
xi=x0*astart;
|
|
||||||
b0 = 1.+3./x0+3.*sqrt(1+x0)*log(sqrt(1.+x0)-sqrt(x0))/pow(x0,1.5);
|
|
||||||
bi = 1.+3./xi+3.*sqrt(1+xi)*log(sqrt(1.+xi)-sqrt(xi))/pow(xi,1.5);
|
|
||||||
fac = bi/b0;
|
|
||||||
}
|
|
||||||
return(fac);
|
|
||||||
}
|
|
||||||
|
|
||||||
double func_Di(double y)
|
|
||||||
{
|
|
||||||
return(pow(1.0+xi3_g1*pow(y,1.2),-1.5));
|
|
||||||
}
|
|
||||||
|
|
||||||
double func_D0(double y)
|
|
||||||
{
|
|
||||||
return(pow(1.0+x03_g1*pow(y,1.2),-1.5));
|
|
||||||
}
|
|
|
@ -1,300 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
|
|
||||||
/* This is the bias factor for halos. Mass (in h^{-1} M_sol) is the input.
|
|
||||||
* This is not the scale-dependent bias factor, which can be calculated later.
|
|
||||||
*
|
|
||||||
* There are many variants of the bias in this function.
|
|
||||||
* The one it is set up to use is from the Tinker etal (in prep, currently)
|
|
||||||
* bias paper calibrated from the SO halo catalogs from the Tinker et al mass functino
|
|
||||||
* paper. The parameters of the bias functions are calibrated such that they will
|
|
||||||
* work with any chosen halo overdensity.
|
|
||||||
*
|
|
||||||
* Other variants:
|
|
||||||
*
|
|
||||||
* The parameterization of b(M) is taken from Sheth Mo & Tormen (2001 MNRAS 232 1)
|
|
||||||
* but the actual parameters have been replaced by the values of Appendix A in
|
|
||||||
* Tinker, Weinberg, Zheng, & Zehavi. 2005 Apj (M/L paper)
|
|
||||||
*
|
|
||||||
* See also Seljak & Warren (2004).
|
|
||||||
* See also Sheth & Tormen (1999)
|
|
||||||
* See also Mo & White (1996)
|
|
||||||
*/
|
|
||||||
|
|
||||||
double bias_from_file(double m, double r);
|
|
||||||
|
|
||||||
double bias(double mass)
|
|
||||||
{
|
|
||||||
double rm,sig,k,neff,b,logk,khi,klo,phi,plo,nu,psp,x;
|
|
||||||
static int flag=0;
|
|
||||||
static double pnorm, prev_delta=-1;
|
|
||||||
|
|
||||||
// variables for the SO(DELTA) bias functions
|
|
||||||
static double bias_A, bias_a, bias_B, bias_b;
|
|
||||||
|
|
||||||
/* Original SMT parameters */
|
|
||||||
double a=0.707,bb=0.5,c=0.6;
|
|
||||||
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
rm=pow(3.0*mass/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
sig=pnorm*sigmac(rm);
|
|
||||||
|
|
||||||
/* Tinker et al parameters */
|
|
||||||
a=0.707;
|
|
||||||
bb=0.35;
|
|
||||||
c=0.8;
|
|
||||||
|
|
||||||
/* Fitting to Mike Warren's simulations. */
|
|
||||||
bb=0.28;
|
|
||||||
|
|
||||||
/* Use the globel parameters. */
|
|
||||||
a=BIAS_A; bb=BIAS_B; c=BIAS_C;
|
|
||||||
|
|
||||||
/* First normalize the power spectrum
|
|
||||||
*/
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
rm=pow(3.0*mass/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
sig=pnorm*sigmac(rm);
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/* This is from Tinker etal in prep for SO halos
|
|
||||||
*/
|
|
||||||
if(DELTA_HALO != prev_delta)
|
|
||||||
{
|
|
||||||
bias_A = pow(fabs(log10(DELTA_HALO)-2.69),2)*0.16 + 0.785;
|
|
||||||
bias_a = (log10(DELTA_HALO) - 2.28)*0.45;
|
|
||||||
bias_B = 0.4*(log10(DELTA_HALO)-2.3)+0.7*log10(DELTA_HALO)*exp(-pow(4/log10(DELTA_HALO),4.0))+1.23;
|
|
||||||
bias_b = 2.4;
|
|
||||||
fprintf(stderr,"BIAS PARAMS: %f %f %f %f\n",bias_A, bias_a, bias_B, bias_b);
|
|
||||||
prev_delta = DELTA_HALO;
|
|
||||||
}
|
|
||||||
|
|
||||||
a = pow(sig,-bias_a);
|
|
||||||
b = 1 - bias_A*a/(a+1) + bias_B*pow(sig,-bias_b);
|
|
||||||
|
|
||||||
return(b);
|
|
||||||
|
|
||||||
/* This is the Seljak & Warren (2004) bias.
|
|
||||||
* There's an alpha_s in the correction term, which here I set to zero. (RUNNING.)
|
|
||||||
* See App. A of Tinker et al (M/L) for a comparison of this bias with above bias.
|
|
||||||
*/
|
|
||||||
x=mass/MSTAR;
|
|
||||||
b=(0.53+0.39*pow(x,0.45)+0.13/(40*x+1) + 5.0e-4*pow(x,1.5));
|
|
||||||
b=b+log10(x)*(0.4*(OMEGA_M-0.3+SPECTRAL_INDX-1)+0.3*(SIGMA_8-0.9+HUBBLE-0.7)+0.8*0.0);
|
|
||||||
return(b);
|
|
||||||
|
|
||||||
/* This is the Sheth Mo Tormen bias.
|
|
||||||
* (possible that parameter values have been changed to better fit simulations,
|
|
||||||
* ie from Tinker etal 2005 ML paper).
|
|
||||||
*/
|
|
||||||
nu=DELTA_CRIT/sig;
|
|
||||||
b=1+1.0/(sqrt(a)*DELTA_CRIT)*(sqrt(a)*a*nu*nu + sqrt(a)*bb*pow(a*nu*nu,1-c) -
|
|
||||||
(pow(a*nu*nu,c)/(pow(a*nu*nu,c)+bb*(1-c)*(1-c/2.))));
|
|
||||||
return(b);
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/* This is Sheth & Tormen
|
|
||||||
*/
|
|
||||||
nu = DELTA_CRIT/sig;
|
|
||||||
nu = nu*nu;
|
|
||||||
return(1 + (0.707*nu - 1)/DELTA_CRIT + 2*0.3/DELTA_CRIT/(1+pow(0.707*nu,0.3)));
|
|
||||||
|
|
||||||
/* This is the old Mo & White (1996) formula
|
|
||||||
*/
|
|
||||||
return(1+DELTA_CRIT/sig/sig-1/DELTA_CRIT);
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Just like the halo mass function, we'll set this up such that
|
|
||||||
* you just need to interpolate.
|
|
||||||
*
|
|
||||||
* Now this has been changed to calculate the spatial-scale dependence
|
|
||||||
* of the bias factor. If you don't want the scale dep. b, then just
|
|
||||||
* input r<0.
|
|
||||||
*
|
|
||||||
* If the global flag LINEAR_PSP==0, uses the scale dependence calculated for
|
|
||||||
* for halo bias relative to the non-linear matter \xi_m(r):
|
|
||||||
*
|
|
||||||
* f^2(r) = (1.0+xi*1.17)^1.49/(1.0+xi*0.69)^2.09 --> b(r) = b0*f(r)
|
|
||||||
*
|
|
||||||
* For LINEAR_PSP==1, use scale dependence determined for the linear P(k):
|
|
||||||
*
|
|
||||||
* f(r) = 1 + exp[-(r/A)^0.7] --> where A is a parameter that we're gonna have to
|
|
||||||
* determine in more detail, but now A \approx 1
|
|
||||||
*/
|
|
||||||
double bias_interp(double m, double r)
|
|
||||||
{
|
|
||||||
static int flag=0,prev_cosmo=0;
|
|
||||||
static double *x,*y,*y2, pnorm;
|
|
||||||
int i,n=100;
|
|
||||||
double dm,max=16.3,min=9,a,b,m1,m2,dm1,xi,power,rm,sig,b1,b2,mass,rvir,a1;
|
|
||||||
|
|
||||||
if(!flag || RESET_COSMOLOGY!=prev_cosmo)
|
|
||||||
{
|
|
||||||
if(!ThisTask && OUTPUT)
|
|
||||||
fprintf(stdout,"RESET: resetting bias for %f %f\n",OMEGA_M,SIGMA_8);
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
dm=(double)(max-min)/n;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x[i]=pow(10.0,min+i*dm);
|
|
||||||
y[i]=log(bias(x[i]));
|
|
||||||
x[i] = log(x[i]);
|
|
||||||
//printf("BIAS %f %f\n",x[i]/2.302, y[i]/2.302);
|
|
||||||
continue;
|
|
||||||
|
|
||||||
// no longer need to do this part, since we're taking into account
|
|
||||||
// halo overdensity in the bias formula.
|
|
||||||
if(DELTA_HALO!=200)
|
|
||||||
{
|
|
||||||
x[i]=log(halo_mass_conversion2(x[i],halo_c200(x[i]),200.0,DELTA_HALO));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
x[i]=log(x[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
m=log(m);
|
|
||||||
splint(x,y,y2,n,m,&a);
|
|
||||||
a = exp(a);
|
|
||||||
|
|
||||||
// if we're using systematic errors in an MCMC, adjust parameter a1 (amplitude)
|
|
||||||
if(USE_ERRORS)
|
|
||||||
a *= M2N.bias_amp;
|
|
||||||
|
|
||||||
// if no scale-dependence required, return the large-scale value
|
|
||||||
if(r<0) return a;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
* SCALE DEPENDENT BIAS!!!
|
|
||||||
*----------------------------------------------------------------------
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* first, calculate the standard Zheng-like, mass-independent scale bias
|
|
||||||
* based on the non-linear correlation function
|
|
||||||
* (re-calibrated using the SO catalogs)
|
|
||||||
*/
|
|
||||||
xi = xi_interp(r);
|
|
||||||
b = pow(1.0+xi*0.92,2.08)*pow(1.0+xi*0.74,-2.37);
|
|
||||||
if(b<0.6)b=0.6;
|
|
||||||
|
|
||||||
/* Now the mass-dependent term.
|
|
||||||
* Where the mass-dependence comes in the form of the large-scale bias itself
|
|
||||||
*/
|
|
||||||
/*
|
|
||||||
sig = sigmac_radius_interp(r);
|
|
||||||
if(a<0)
|
|
||||||
b *= pow(1 + 0.028*pow(a,1.53)*pow(sig,1.57),2.59)/
|
|
||||||
pow(1 + 0.253*pow(a,1.24)*pow(sig,1.71),0.397);
|
|
||||||
*/
|
|
||||||
|
|
||||||
// if we're using systematic errors in an MCMC, adjust parameter a1 (amplitude)
|
|
||||||
if(USE_ERRORS) {
|
|
||||||
b = (b-1)*M2N.scalebias_amp + 1;
|
|
||||||
if(b<0)b=0;
|
|
||||||
}
|
|
||||||
return b*a;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* This is the integrand which qromo or qtrap would call
|
|
||||||
* to calculate the large-scale galaxy bias.
|
|
||||||
* The integral is a number-weighted average of the halo
|
|
||||||
* bias function, integrated over the halo mass function.
|
|
||||||
*/
|
|
||||||
double func_galaxy_bias(double m)
|
|
||||||
{
|
|
||||||
m=exp(m);
|
|
||||||
return(dndM_interp(m)*N_avg(m)*bias_interp(m,-1.)*m);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* This is to get the bias from a series of files.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
double bias_from_file(double m, double r)
|
|
||||||
{
|
|
||||||
FILE *fp;
|
|
||||||
static int nfiles=10, *n, flag =1;
|
|
||||||
static double *mass, **rad, **bias;
|
|
||||||
float x1,x2,x3;
|
|
||||||
char fname[1000];
|
|
||||||
int i,j,i1,i2;
|
|
||||||
double b;
|
|
||||||
|
|
||||||
if(flag)
|
|
||||||
{
|
|
||||||
n = ivector(0,nfiles-1);
|
|
||||||
mass = dvector(0,nfiles-1);
|
|
||||||
rad = dmatrix(0,nfiles-1,1,30);
|
|
||||||
bias = dmatrix(0,nfiles-1,1,30);
|
|
||||||
|
|
||||||
fp = openfile("/home/tinker/cosmo/SDSS/zspace_analysis/SO_calibration/halofiles/sigma.dat");
|
|
||||||
|
|
||||||
for(i=0;i<nfiles;++i)
|
|
||||||
fscanf(fp,"%lf %f",&mass[i],&x1);
|
|
||||||
for(i=0;i<nfiles;++i)
|
|
||||||
mass[i] = log(mass[i]);
|
|
||||||
fclose(fp);
|
|
||||||
|
|
||||||
for(i=0;i<nfiles;++i)
|
|
||||||
{
|
|
||||||
sprintf(fname,"/home/tinker/cosmo/SDSS/zspace_analysis/SO_calibration/halofiles/bias_nl.200.m%d",i);
|
|
||||||
fp = openfile(fname);
|
|
||||||
n[i] = filesize(fp);
|
|
||||||
for(j=1;j<=n[i];++j)
|
|
||||||
{
|
|
||||||
fscanf(fp,"%lf %lf %f %f %f",&rad[i][j],&bias[i][j],&x1,&x2,&x3);
|
|
||||||
rad[i][j] = log(rad[i][j]);
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
}
|
|
||||||
flag = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
r = log(r);
|
|
||||||
if(m>mass[nfiles-1])return -1;
|
|
||||||
|
|
||||||
for(i=1;i<nfiles;++i)
|
|
||||||
if(mass[i]>=m)break;
|
|
||||||
i2 = i;
|
|
||||||
i1 = i-1;
|
|
||||||
|
|
||||||
|
|
||||||
for(j=2;j<=n[i1];++j)
|
|
||||||
if(rad[i1][j]>r)break;
|
|
||||||
x1 = (bias[i1][j] - bias[i1][j-1])/(rad[i1][j] - rad[i1][j-1])*(r-rad[i1][j-1]) + bias[i1][j-1];
|
|
||||||
|
|
||||||
for(j=2;j<=n[i2];++j)
|
|
||||||
if(rad[i2][j]>r)break;
|
|
||||||
x2 = (bias[i2][j] - bias[i2][j-1])/(rad[i2][j] - rad[i2][j-1])*(r-rad[i2][j-1]) + bias[i2][j-1];
|
|
||||||
|
|
||||||
b = (x2 - x1)/(mass[i2] - mass[i1])*(m - mass[i1]) + x1;
|
|
||||||
|
|
||||||
// if(r>log(4))
|
|
||||||
// printf("%e %e %f %f %f %f %f\n",m,r,b,x2,x1,mass[i2],mass[i1]);
|
|
||||||
return b;
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,178 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
|
|
||||||
/* This is the bias factor for halos. Mass (in h^{-1} M_sol) is the input.
|
|
||||||
* This is not the scale-dependent bias factor, which can be calculated later.
|
|
||||||
*
|
|
||||||
* The parameterization of b(M) is taken from Sheth Mo & Tormen (2001 MNRAS 232 1)
|
|
||||||
* but the actual parameters have been replaced by the values of Appendix A in
|
|
||||||
* Tinker, Weinberg, Zheng, & Zehavi. 2005 Apj (submitted)
|
|
||||||
*/
|
|
||||||
|
|
||||||
double bias(double mass)
|
|
||||||
{
|
|
||||||
static int prev_cosmo=-1;
|
|
||||||
static long IDUM=-3333;
|
|
||||||
double rm,sig,k,neff,b,logk,khi,klo,phi,plo,nu,psp,x,fac,fac1,fac2;
|
|
||||||
static int flag=0,na=4;
|
|
||||||
static double pnorm,*xa,*ya,*za;
|
|
||||||
int i;
|
|
||||||
|
|
||||||
/* Original SMT parameters */
|
|
||||||
double a=0.707,bb=0.5,c=0.6;
|
|
||||||
|
|
||||||
/* Tinker et al parameters */
|
|
||||||
a=0.707;
|
|
||||||
bb=0.35;
|
|
||||||
c=0.8;
|
|
||||||
|
|
||||||
/* Fitting to Mike Warren's simulations. */
|
|
||||||
bb=0.28;
|
|
||||||
|
|
||||||
/* Use the globel parameters. */
|
|
||||||
a=BIAS_A; bb=BIAS_B; c=BIAS_C;
|
|
||||||
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
xa=dvector(1,na);
|
|
||||||
ya=dvector(1,na);
|
|
||||||
za=dvector(1,na);
|
|
||||||
flag=1;
|
|
||||||
xa[1] = log(1/2.51);
|
|
||||||
xa[2] = log(1/1.49);
|
|
||||||
xa[3] = log(1/0.905);
|
|
||||||
xa[4] = log(1/0.501);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(prev_cosmo != RESET_COSMOLOGY)
|
|
||||||
{
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
for(i=1;i<=4;++i)
|
|
||||||
ya[i] = gasdev(&IDUM);
|
|
||||||
spline(xa,ya,na,1.0E+30,1.0E+30,za);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* First normalize the power spectrum
|
|
||||||
*/
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
rm=pow(3.0*mass/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
sig=pnorm*sigmac(rm);
|
|
||||||
|
|
||||||
nu=DELTA_CRIT/sig;
|
|
||||||
b=1+1.0/(sqrt(a)*DELTA_CRIT)*(sqrt(a)*a*nu*nu + sqrt(a)*bb*pow(a*nu*nu,1-c) -
|
|
||||||
(pow(a*nu*nu,c)/(pow(a*nu*nu,c)+bb*(1-c)*(1-c/2.))));
|
|
||||||
|
|
||||||
splint(xa,ya,za,na,log(1/sig),&fac1);
|
|
||||||
fac2 = 0.0158*pow(sig,-2.7) + 0.00251*pow(sig,2.2);
|
|
||||||
fac = 1 + fac1*fac2;
|
|
||||||
if(fac<0.01)fac=0.01;
|
|
||||||
b*=fac;
|
|
||||||
|
|
||||||
return(b);
|
|
||||||
|
|
||||||
|
|
||||||
/* This is the Seljak & Warren (2004) bias.
|
|
||||||
* There's an alpha_s in the correction term, which here I set to zero. (RUNNING.)
|
|
||||||
* See App. A of Tinker et al for a comparison of this bias with above bias.
|
|
||||||
*/
|
|
||||||
x=mass/MSTAR;
|
|
||||||
b=(0.53+0.39*pow(x,0.45)+0.13/(40*x+1) + 5.0e-4*pow(x,1.5));
|
|
||||||
b=b+log10(x)*(0.4*(OMEGA_M-0.3+SPECTRAL_INDX-1)+0.3*(SIGMA_8-0.9+HUBBLE-0.7)+0.8*0.0);
|
|
||||||
return(b);
|
|
||||||
|
|
||||||
/* This is the old Mo & White (1996) formula
|
|
||||||
*/
|
|
||||||
return(1+DELTA_CRIT/sig/sig-1/DELTA_CRIT);
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Just like the halo mass function, we'll set this up such that
|
|
||||||
* you just need to interpolate.
|
|
||||||
*
|
|
||||||
* Now this has been changed to calculate the spatial-scale dependence
|
|
||||||
* of the bias factor. If you don't want the scale dep. b, then just
|
|
||||||
* input r<0.
|
|
||||||
*
|
|
||||||
* If the global flag LINEAR_PSP==0, uses the scale dependence calculated for
|
|
||||||
* for halo bias relative to the non-linear matter \xi_m(r):
|
|
||||||
*
|
|
||||||
* f^2(r) = (1.0+xi*1.17)^1.49/(1.0+xi*0.69)^2.09 --> b(r) = b0*f(r)
|
|
||||||
*
|
|
||||||
* For LINEAR_PSP==1, use scale dependence determined for the linear P(k):
|
|
||||||
*
|
|
||||||
* f(r) = 1 + exp[-(r/A)^0.7] --> where A is a parameter that we're gonna have to
|
|
||||||
* determine in more detail, but now A \approx 1
|
|
||||||
*/
|
|
||||||
double bias_interp(double m, double r)
|
|
||||||
{
|
|
||||||
static int flag=0,prev_cosmo=0;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int i,n=100;
|
|
||||||
double dm,max=16.3,min=9,a,b,m1,m2,dm1,xi;
|
|
||||||
|
|
||||||
if(!flag || RESET_COSMOLOGY!=prev_cosmo)
|
|
||||||
{
|
|
||||||
if(!ThisTask && OUTPUT)
|
|
||||||
fprintf(stdout,"RESET: resetting bias for %f %f\n",OMEGA_M,SIGMA_8);
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
dm=(double)(max-min)/n;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x[i]=pow(10.0,min+i*dm);
|
|
||||||
y[i]=log(bias(x[i]));
|
|
||||||
if(DELTA_HALO!=200)
|
|
||||||
{
|
|
||||||
m1 = halo_mass_conversion2(x[i]*1.001,halo_c200(x[i]*1.001),DELTA_HALO,200.0);
|
|
||||||
m2 = halo_mass_conversion2(x[i]*0.999,halo_c200(x[i]*0.999),DELTA_HALO,200.0);
|
|
||||||
dm1 = (x[i]*1.001 - x[i]*0.999)/(m1-m2);
|
|
||||||
y[i] = y[i] + log(dm1);
|
|
||||||
x[i]=log(halo_mass_conversion2(x[i],halo_c200(x[i]),DELTA_HALO,200.0));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
x[i]=log(x[i]);
|
|
||||||
}
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
m=log(m);
|
|
||||||
splint(x,y,y2,n,m,&a);
|
|
||||||
if(r<0 || r>10)return(exp(a));
|
|
||||||
|
|
||||||
if(LINEAR_PSP)
|
|
||||||
{
|
|
||||||
b=exp(-pow(r,0.7)) + 1;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
xi=xi_interp(r);
|
|
||||||
b=pow(1.0+xi*1.17,1.49*0.5)*pow(1.0+xi*0.69,-2.09*0.5);
|
|
||||||
}
|
|
||||||
a=exp(a)*b;
|
|
||||||
return(a);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* This is the integrand which qromo or qtrap would call
|
|
||||||
* to calculate the large-scale galaxy bias.
|
|
||||||
* The integral is a number-weighted average of the halo
|
|
||||||
* bias function, integrated over the halo mass function.
|
|
||||||
*/
|
|
||||||
double func_galaxy_bias(double m)
|
|
||||||
{
|
|
||||||
return(dndM_interp(m)*N_avg(m)*bias_interp(m,-1.));
|
|
||||||
}
|
|
|
@ -1,155 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
double collapse_redshift(double z);
|
|
||||||
double cvir_pnorm_g1,
|
|
||||||
cvir_sigma_g1;
|
|
||||||
|
|
||||||
/* This calculates and tabulates the halo concentrations
|
|
||||||
* as a function of halo mass. Uses the "Bullock model",
|
|
||||||
* described in a little more detail below.
|
|
||||||
*/
|
|
||||||
|
|
||||||
double halo_concentration(double m)
|
|
||||||
{
|
|
||||||
static int flag=1,n,prev_cosmo=0;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int i;
|
|
||||||
float x1,x2,cfac;
|
|
||||||
double a,dm,x3,x4;
|
|
||||||
FILE *fp;
|
|
||||||
char fname[1000];
|
|
||||||
|
|
||||||
if(flag || RESET_COSMOLOGY!=prev_cosmo)
|
|
||||||
{
|
|
||||||
MSTAR = mstar();
|
|
||||||
if(OUTPUT)
|
|
||||||
fprintf(stdout,"Calc cvir with DELTA_HALO= %f\n",DELTA_HALO);
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
n=50;
|
|
||||||
if(flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
cvir_pnorm_g1=SIGMA_8/sigmac(8.0);
|
|
||||||
|
|
||||||
flag=0;
|
|
||||||
|
|
||||||
dm=(log(HOD.M_max)-log(1.0E8))/(n-1);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x[i]=exp((i-1)*dm+log(1.0E8));
|
|
||||||
y[i]=cvir_model(x[i]);
|
|
||||||
x[i]=log(halo_mass_conversion(x[i],&y[i],DELTA_HALO));
|
|
||||||
y[i]=log(y[i]);
|
|
||||||
//y[i] = log(10);
|
|
||||||
}
|
|
||||||
spline(x,y,n,1.0E+30,1.0E+30,y2);
|
|
||||||
}
|
|
||||||
cfac = 0.13*log10(m/1.0e12) + 0.125;
|
|
||||||
cfac = 1;
|
|
||||||
if(m>80*MSTAR) m=80*MSTAR;
|
|
||||||
m=log(m);
|
|
||||||
splint(x,y,y2,n,m,&a);
|
|
||||||
return(exp(a)*cfac);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* This is the cvir model, which should reproduce the results
|
|
||||||
* of cvir3.f, which can be obtained off James Bullock's web site.
|
|
||||||
*
|
|
||||||
* Basic idea; For a halo of mass M, find the collapse redshift
|
|
||||||
* of that halo be finding the redshift at which rms mass variance
|
|
||||||
* sigma(Mf) = DELTA_CRIT (using linear growth factor), where Mf is some
|
|
||||||
* fraction of the redshift zero halo mass.
|
|
||||||
*
|
|
||||||
* cvir = k*(1+z_coll(M*f))
|
|
||||||
*
|
|
||||||
* Model params:
|
|
||||||
* - k = 3.12 - fitting parameter (taken from cvir3.f)
|
|
||||||
* - f = 0.001 - fraction of halo mass that collapsed at z_coll
|
|
||||||
*/
|
|
||||||
|
|
||||||
double cvir_model(double mass)
|
|
||||||
{
|
|
||||||
double cvir,z_coll,zbrent(),rad;
|
|
||||||
double k=3.12;
|
|
||||||
double f=0.001;
|
|
||||||
|
|
||||||
rad=pow(3.0*f*mass/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
cvir_sigma_g1=cvir_pnorm_g1*sigmac(rad);
|
|
||||||
|
|
||||||
if(collapse_redshift(0.0)<0)return(k);
|
|
||||||
z_coll=zbrent(collapse_redshift,0.0,200.0,1.0E-3);
|
|
||||||
cvir=k*(1+z_coll);
|
|
||||||
return(cvir);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This is the input function to find where sig(M)*D(z)-DELTA_CRIT = 0
|
|
||||||
* which is the redshift at which a halo of mass M collapsed.
|
|
||||||
*/
|
|
||||||
double collapse_redshift(double z)
|
|
||||||
{
|
|
||||||
double D;
|
|
||||||
D=growthfactor(z);
|
|
||||||
return(cvir_sigma_g1*D-DELTA_CRIT);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Some quantities are specific to an overdensity of 200 (i.e., the Jenkins mass
|
|
||||||
* function and the halo bias relation of Tinker et al. )
|
|
||||||
* Specfically, these are actually for FOF 0.2 halos, for which 200 is the
|
|
||||||
* current best approximation. (Although Warren et al quotes 250, which is the most recent
|
|
||||||
* value.)
|
|
||||||
*
|
|
||||||
* Therefore, the halo concentrations for Delta=200 halos need to be easily
|
|
||||||
* accessible for halo mass conversion of these quantities. The values are
|
|
||||||
* tabulates here, as opposed to the above routine which tabulates the
|
|
||||||
* concentrations for a user-specified overdensity.
|
|
||||||
*/
|
|
||||||
|
|
||||||
double halo_c200(double m)
|
|
||||||
{
|
|
||||||
static int flag=1,n,prev_cosmo=0;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int i;
|
|
||||||
float x1,x2;
|
|
||||||
double a,dm,x3,x4;
|
|
||||||
FILE *fp;
|
|
||||||
char fname[1000];
|
|
||||||
|
|
||||||
if(flag || RESET_COSMOLOGY!=prev_cosmo)
|
|
||||||
{
|
|
||||||
if(OUTPUT)
|
|
||||||
fprintf(stdout,"Calc cvir with DELTA_HALO= %f\n",200.0);
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
n=50;
|
|
||||||
if(flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
cvir_pnorm_g1=SIGMA_8/sigmac(8.0);
|
|
||||||
|
|
||||||
flag=0;
|
|
||||||
|
|
||||||
dm=(log(HOD.M_max)-log(1.0E8))/(n-1);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x[i]=exp((i-1)*dm+log(1.0E8));
|
|
||||||
y[i]=cvir_model(x[i]);
|
|
||||||
x[i]=log(halo_mass_conversion(x[i],&y[i],200.0));
|
|
||||||
y[i]=log(y[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
m=log(m);
|
|
||||||
splint(x,y,y2,n,m,&a);
|
|
||||||
return(exp(a));
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,86 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
|
|
||||||
/* This is a routine which takes a virial mass (as defined by the virial
|
|
||||||
* overdensity relation (see fitting formula of Bryan & Normax)
|
|
||||||
* and converts if to a mass of some given overdensity. This is all
|
|
||||||
* taken from the appendix of Hu & Kravtsov. 2003ApJ...584..702H
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Constants from conversion formula in Hu & Kravtsov (2003)
|
|
||||||
*/
|
|
||||||
#define a1 0.5116
|
|
||||||
#define a2 -0.4283
|
|
||||||
#define a3 -3.13E-3
|
|
||||||
#define a4 -3.52E-5
|
|
||||||
|
|
||||||
double HK_func(double x);
|
|
||||||
|
|
||||||
double halo_mass_conversion(double mvir, double *cvir1, double delta_halo)
|
|
||||||
{
|
|
||||||
double x,y,z,vx,vy,vz,x1,x2,x3,x4,omega_m,delta=180,mstar,delta_vir,delta_fof,p,f,
|
|
||||||
mp,v,mass,lambda,error,tol=1.0E-3,cprev,m_delta,delta_fac,cvir,rdelta,rvir;
|
|
||||||
|
|
||||||
cvir=*cvir1;
|
|
||||||
omega_m=OMEGA_M;
|
|
||||||
lambda=1-OMEGA_M;
|
|
||||||
mstar=MSTAR;
|
|
||||||
delta=delta_halo;
|
|
||||||
|
|
||||||
x=omega_m-1;
|
|
||||||
delta_vir=(18*PI*PI+82*x-39*x*x)/(1+x);
|
|
||||||
|
|
||||||
/* Now convert from virial mass to m_delta.
|
|
||||||
*/
|
|
||||||
f=delta/delta_vir*HK_func(1.0/cvir);
|
|
||||||
p=a2+a3*log(f)+a4*log(f)*log(f);
|
|
||||||
x1=1.0/sqrt(a1*pow(f,2*p)+0.5625)+2*f;
|
|
||||||
m_delta=mvir*(delta/delta_vir*pow(1.0/(x1*cvir),3.0));
|
|
||||||
|
|
||||||
/* Now convert the cvir to c_delta.
|
|
||||||
*/
|
|
||||||
rvir=pow(3*mvir/(4*delta_vir*PI*RHO_CRIT*OMEGA_M),1.0/3.0);
|
|
||||||
rdelta=pow(3*m_delta/(4*delta*PI*RHO_CRIT*OMEGA_M),1.0/3.0);
|
|
||||||
*cvir1=cvir*rdelta/rvir;
|
|
||||||
|
|
||||||
return(m_delta);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This is a slight modification to the above routine-- instead of converting from
|
|
||||||
* the virial mass, it converts from a specified Delta to the other Delta.
|
|
||||||
* (so here the "_vir" quantities are any arbitrary input overdensity.)
|
|
||||||
*/
|
|
||||||
|
|
||||||
double halo_mass_conversion2(double mvir, double cvir1, double delta_vir, double delta_halo)
|
|
||||||
{
|
|
||||||
double x,y,z,vx,vy,vz,x1,x2,x3,x4,omega_m,delta=180,mstar,delta_fof,p,f,
|
|
||||||
mp,v,mass,lambda,error,tol=1.0E-3,cprev,m_delta,delta_fac,cvir,rdelta,rvir;
|
|
||||||
|
|
||||||
cvir=cvir1;
|
|
||||||
omega_m=OMEGA_M;
|
|
||||||
lambda=1-OMEGA_M;
|
|
||||||
mstar=MSTAR;
|
|
||||||
delta=delta_halo;
|
|
||||||
|
|
||||||
/* Now convert from virial mass to m_delta.
|
|
||||||
*/
|
|
||||||
f=delta/delta_vir*HK_func(1.0/cvir);
|
|
||||||
p=a2+a3*log(f)+a4*log(f)*log(f);
|
|
||||||
x1=1.0/sqrt(a1*pow(f,2*p)+0.5625)+2*f;
|
|
||||||
m_delta=mvir*(delta/delta_vir*pow(1.0/(x1*cvir),3.0));
|
|
||||||
|
|
||||||
/* Now convert the cvir to c_delta.
|
|
||||||
*/
|
|
||||||
rvir=pow(3*mvir/(4*delta_vir*PI*RHO_CRIT*OMEGA_M),1.0/3.0);
|
|
||||||
rdelta=pow(3*m_delta/(4*delta*PI*RHO_CRIT*OMEGA_M),1.0/3.0);
|
|
||||||
|
|
||||||
return(m_delta);
|
|
||||||
}
|
|
||||||
|
|
||||||
double HK_func(double x)
|
|
||||||
{
|
|
||||||
return(x*x*x*(log(1+1.0/x)-1.0/(1+x)));
|
|
||||||
}
|
|
|
@ -1,338 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* This is a calculation of the differential halo mass function of
|
|
||||||
* Jenkins et al 2001 (MNRAS 321, 372).
|
|
||||||
*
|
|
||||||
* Also included is the mass function from my own analysis, which is
|
|
||||||
* a variant of the Sheth-Tormen mass function (leaving all 3 parameters
|
|
||||||
* as free parameters), with a 2-parameter high-mass cutoff of the form
|
|
||||||
* suggested by Reed et al.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
void initialize_mass_function(double *a1, double *a2, double *a3, double *a4);
|
|
||||||
|
|
||||||
double halo_mass_function(double mass)
|
|
||||||
{
|
|
||||||
double sig,logm,a,slo,shi,rm,rlo,rhi,mlo,mhi,dsdM,n,nuprime,nufnu,p,A;
|
|
||||||
static int flag=0,SO180=0,SO324=0,WARREN=0,ST=0,JENKINS=0;
|
|
||||||
static double pnorm, prev_delta;
|
|
||||||
double btemp = -1;
|
|
||||||
|
|
||||||
static double
|
|
||||||
a1 = 0.325277,
|
|
||||||
a2 = 0.492785,
|
|
||||||
a3 = 0.310289,
|
|
||||||
a4 = 1.317104,
|
|
||||||
a5 = 2.425681;
|
|
||||||
|
|
||||||
/* Jenkins et al. SO 180 best-fit
|
|
||||||
*/
|
|
||||||
if(SO180)
|
|
||||||
{
|
|
||||||
JENKINS_A = 0.301;
|
|
||||||
JENKINS_B = 0.64;
|
|
||||||
JENKINS_C = 3.82;
|
|
||||||
}
|
|
||||||
if(SO324)
|
|
||||||
{
|
|
||||||
JENKINS_A = 0.316;
|
|
||||||
JENKINS_B = 0.67;
|
|
||||||
JENKINS_C = 3.82;
|
|
||||||
}
|
|
||||||
if(JENKINS) //their .2 fof function
|
|
||||||
{
|
|
||||||
JENKINS_A = 0.315;
|
|
||||||
JENKINS_B = 0.61;
|
|
||||||
JENKINS_C = 3.8;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* First normalize the power spectrum
|
|
||||||
*/
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
rm=pow(3.0*mass/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
sig=pnorm*sigmac(rm);
|
|
||||||
logm=log10(mass);
|
|
||||||
|
|
||||||
mlo=0.99*mass;
|
|
||||||
mhi=1.01*mass;
|
|
||||||
rlo=pow(3.0*mlo/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
rhi=pow(3.0*mhi/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
|
|
||||||
slo=pnorm*sigmac(rlo);
|
|
||||||
shi=pnorm*sigmac(rhi);
|
|
||||||
dsdM=(shi-slo)/(mhi-mlo);
|
|
||||||
|
|
||||||
if(SO324)goto JENKINS_FUNCTION;
|
|
||||||
if(SO180)goto JENKINS_FUNCTION;
|
|
||||||
if(WARREN)goto WARREN_FUNCTION;
|
|
||||||
if(ST)goto ST_FUNCTION;
|
|
||||||
if(JENKINS)goto JENKINS_FUNCTION;
|
|
||||||
|
|
||||||
/* Tinker et al. (in prep) for SO 200
|
|
||||||
*/
|
|
||||||
if(DELTA_HALO != prev_delta)
|
|
||||||
{
|
|
||||||
initialize_mass_function(&a1,&a2,&a3,&a4);
|
|
||||||
prev_delta = DELTA_HALO;
|
|
||||||
|
|
||||||
// if we're using systematic errors in an MCMC, adjust parameter a1 (amplitude)
|
|
||||||
if(USE_ERRORS)
|
|
||||||
a1 *= M2N.mf_amp;
|
|
||||||
|
|
||||||
fprintf(stderr,"MF PARAMS for DELTA=%f %f %f %f %f\n",DELTA_HALO,a1,a2,a3,a4);
|
|
||||||
}
|
|
||||||
|
|
||||||
n = -a1*(pow(sig/a3,-a2)+1)*exp(-a4/sig/sig)*OMEGA_M*RHO_CRIT/mass/sig*dsdM;
|
|
||||||
return(n);
|
|
||||||
|
|
||||||
/* Jenkins et al. FOF .2 best-fit (unless SO180==1)
|
|
||||||
*/
|
|
||||||
JENKINS_FUNCTION:
|
|
||||||
a=-JENKINS_A*OMEGA_M*RHO_CRIT/mass/sig;
|
|
||||||
n=a*dsdM*exp(-pow(fabs(JENKINS_B-log(sig)),JENKINS_C));
|
|
||||||
return(n);
|
|
||||||
|
|
||||||
/* Warren et al. (calibrated only on concordance cosmology, FOF.2)
|
|
||||||
*/
|
|
||||||
WARREN_FUNCTION:
|
|
||||||
n = -0.7234*(pow(sig,-1.625)+0.2538)*exp(-1.198/sig/sig)*OMEGA_M*RHO_CRIT/mass/sig*dsdM;
|
|
||||||
return(n);
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/* Need to find the derivative dlog(sig)/dlog(M)
|
|
||||||
*/
|
|
||||||
mlo=0.99*logm;
|
|
||||||
mhi=1.01*logm;
|
|
||||||
rlo=pow(3.0*pow(10.0,mlo)/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
rhi=pow(3.0*pow(10.0,mhi)/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
slo=log10(pnorm*sigmac(rlo));
|
|
||||||
shi=log10(pnorm*sigmac(rhi));
|
|
||||||
dsdM=(shi-slo)/(mhi-mlo);
|
|
||||||
|
|
||||||
ST_FUNCTION:
|
|
||||||
|
|
||||||
/* This is a bunch of Sheth-Tormen stuff.
|
|
||||||
* NB! because I'm skipping the above derivative (dlogs/dlogM), i'm using the lower
|
|
||||||
*/
|
|
||||||
nuprime=0.841*DELTA_CRIT/sig;
|
|
||||||
nufnu=0.644*(1+1.0/pow(nuprime,0.6))*(sqrt(nuprime*nuprime/2/PI))*exp(-nuprime*nuprime/2);
|
|
||||||
//n=RHO_CRIT*OMEGA_M/mass*mass*nufnu*fabs(dsdM);
|
|
||||||
n=RHO_CRIT*OMEGA_M/mass*nufnu*fabs(dsdM)/sig;
|
|
||||||
return(n);
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* It may be a bit costly to run the above function every time you need
|
|
||||||
* dn/dM, so here we put the values into an array and then interpolate.
|
|
||||||
*
|
|
||||||
* The currentrange of masses calculated is 10^9 to 10^16.7. The tabulation is
|
|
||||||
* done in log(M), so the spline interpolation will perform a power-law fit
|
|
||||||
* to masses outside this range.
|
|
||||||
*/
|
|
||||||
double dndM_interp(double m)
|
|
||||||
{
|
|
||||||
static int flag=0,prev_cosmo=0;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int i,n=2000;
|
|
||||||
double dm,max=16.7,min=8,a,m1,m2,dm1;
|
|
||||||
|
|
||||||
if(!flag || RESET_COSMOLOGY!=prev_cosmo)
|
|
||||||
{
|
|
||||||
if(!ThisTask && OUTPUT)
|
|
||||||
fprintf(stdout,"RESET: resetting mass function for %f %f\n",OMEGA_M,SIGMA_8);
|
|
||||||
fflush(stdout);
|
|
||||||
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
dm=(double)(max-min)/n;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x[i]=pow(10.0,min+i*dm);
|
|
||||||
y[i]=log(halo_mass_function(x[i]));
|
|
||||||
x[i]=log(x[i]);
|
|
||||||
continue;
|
|
||||||
|
|
||||||
/*
|
|
||||||
m1 = halo_mass_conversion2(x[i]*1.001,halo_concentration(x[i]*1.001),DELTA_HALO,200);
|
|
||||||
m2 = halo_mass_conversion2(x[i]*0.999,halo_concentration(x[i]*0.999),DELTA_HALO,200.0);
|
|
||||||
dm1 = (x[i]*1.001 - x[i]*0.999)/(m1-m2);
|
|
||||||
y[i] = y[i] + log(dm1);
|
|
||||||
x[i]=log(halo_mass_conversion2(x[i],halo_concentration(x[i]),DELTA_HALO,200.0));
|
|
||||||
printf("%e %e %e %e\n",exp(x[i]),exp(y[i]),0.1*exp(y[i]),0.1);
|
|
||||||
continue;
|
|
||||||
*/
|
|
||||||
if(DELTA_HALO!=200)
|
|
||||||
{
|
|
||||||
m1 = halo_mass_conversion2(x[i]*1.001,halo_c200(x[i]*1.001),200.0,DELTA_HALO);
|
|
||||||
m2 = halo_mass_conversion2(x[i]*0.999,halo_c200(x[i]*0.999),200.0,DELTA_HALO);
|
|
||||||
dm1 = (x[i]*1.001 - x[i]*0.999)/(m1-m2);
|
|
||||||
y[i] = y[i] + log(dm1);
|
|
||||||
x[i]=log(halo_mass_conversion2(x[i],halo_c200(x[i]),200.0,DELTA_HALO));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
x[i]=log(x[i]);
|
|
||||||
|
|
||||||
}
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
}
|
|
||||||
//exit(0);
|
|
||||||
m=log(m);
|
|
||||||
splint(x,y,y2,n,m,&a);
|
|
||||||
return(exp(a));
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* Reads mass function in from a file and spline interpolates.
|
|
||||||
*/
|
|
||||||
double nbody_massfunction(double m)
|
|
||||||
{
|
|
||||||
static int flag=0,n;
|
|
||||||
static double *x,*y,*y2,log10_2,normhi,normlo;
|
|
||||||
float x1,x2,x3;
|
|
||||||
int i;
|
|
||||||
double a,dx;
|
|
||||||
char aa[1000];
|
|
||||||
FILE *fp;
|
|
||||||
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
log10_2=log10(2.0);
|
|
||||||
flag++;
|
|
||||||
if(!(fp=fopen(Files.MassFuncFile,"r")))
|
|
||||||
endrun("ERROR opening MassFuncFile");
|
|
||||||
i=0;
|
|
||||||
n = filesize(fp);
|
|
||||||
fprintf(stderr,"Read %d lines from [%s]\n",n,Files.MassFuncFile);
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
fscanf(fp,"%f %f",&x1,&x2);
|
|
||||||
x[i]=log(x1);
|
|
||||||
y[i]=log(x2);
|
|
||||||
fgets(aa,1000,fp);
|
|
||||||
}
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
fclose(fp);
|
|
||||||
fprintf(stderr,"Minimum halo mass in N-body dndM= %e\n",exp(x[1]));
|
|
||||||
|
|
||||||
normhi = exp(y[n])/halo_mass_function(exp(x[n]));
|
|
||||||
normlo = exp(y[1])/halo_mass_function(exp(x[1]));
|
|
||||||
}
|
|
||||||
|
|
||||||
m=log(m);
|
|
||||||
// if(m>x[n])return(0);
|
|
||||||
/*if(m<x[1])return(0);*/
|
|
||||||
|
|
||||||
if(m>x[n])
|
|
||||||
return(halo_mass_function(exp(m))*normhi);
|
|
||||||
if(m<x[1])
|
|
||||||
return(halo_mass_function(exp(m))*normlo);
|
|
||||||
splint(x,y,y2,n,m,&a);
|
|
||||||
/*if(m<x[1])printf("LESS %e %e %e\n",pow(10.0,m),pow(10.0,a),pow(10.0,y[1]));*/
|
|
||||||
return(exp(a));
|
|
||||||
}
|
|
||||||
|
|
||||||
void initialize_mass_function(double *a1, double *a2, double *a3, double *a4)
|
|
||||||
{
|
|
||||||
int n = 9, i;
|
|
||||||
double *x, *y, *z, at, ztemp;
|
|
||||||
|
|
||||||
x = dvector(1,n);
|
|
||||||
y = dvector(1,n);
|
|
||||||
z = dvector(1,n);
|
|
||||||
|
|
||||||
// initialize the overdensities
|
|
||||||
for(i=1;i<=9;i+=2)
|
|
||||||
x[i] = log(200*pow(2.0,(i-1.0)/2.0));
|
|
||||||
for(i=2;i<=9;i+=2)
|
|
||||||
x[i] = log(300*pow(2.0,(i-2.0)/2.0));
|
|
||||||
|
|
||||||
//first parameter
|
|
||||||
y[1] = 1.858659e-01 ;
|
|
||||||
y[2] = 1.995973e-01 ;
|
|
||||||
y[3] = 2.115659e-01 ;
|
|
||||||
y[4] = 2.184113e-01 ;
|
|
||||||
y[5] = 2.480968e-01 ;
|
|
||||||
y[6] = 2.546053e-01 ;
|
|
||||||
y[7] = 2.600000e-01 ;
|
|
||||||
y[8] = 2.600000e-01 ;
|
|
||||||
y[9] = 2.600000e-01 ;
|
|
||||||
|
|
||||||
spline(x,y,n,1.0E+30,1.0E+30,z);
|
|
||||||
splint(x,y,z,n,log(DELTA_HALO),a1);
|
|
||||||
if(DELTA_HALO>=1600) *a1 = 0.26;
|
|
||||||
|
|
||||||
//second parameter
|
|
||||||
y[1] = 1.466904e+00 ;
|
|
||||||
y[2] = 1.521782e+00 ;
|
|
||||||
y[3] = 1.559186e+00 ;
|
|
||||||
y[4] = 1.614585e+00 ;
|
|
||||||
y[5] = 1.869936e+00 ;
|
|
||||||
y[6] = 2.128056e+00 ;
|
|
||||||
y[7] = 2.301275e+00 ;
|
|
||||||
y[8] = 2.529241e+00 ;
|
|
||||||
y[9] = 2.661983e+00 ;
|
|
||||||
|
|
||||||
spline(x,y,n,1.0E+30,1.0E+30,z);
|
|
||||||
splint(x,y,z,n,log(DELTA_HALO),a2);
|
|
||||||
|
|
||||||
//third parameter
|
|
||||||
y[1] = 2.571104e+00 ;
|
|
||||||
y[2] = 2.254217e+00 ;
|
|
||||||
y[3] = 2.048674e+00 ;
|
|
||||||
y[4] = 1.869559e+00 ;
|
|
||||||
y[5] = 1.588649e+00 ;
|
|
||||||
y[6] = 1.507134e+00 ;
|
|
||||||
y[7] = 1.464374e+00 ;
|
|
||||||
y[8] = 1.436827e+00 ;
|
|
||||||
y[9] = 1.405210e+00 ;
|
|
||||||
|
|
||||||
spline(x,y,n,1.0E+30,1.0E+30,z);
|
|
||||||
splint(x,y,z,n,log(DELTA_HALO),a3);
|
|
||||||
|
|
||||||
|
|
||||||
//fourth parameter
|
|
||||||
y[1] = 1.193958e+00;
|
|
||||||
y[2] = 1.270316e+00;
|
|
||||||
y[3] = 1.335191e+00;
|
|
||||||
y[4] = 1.446266e+00;
|
|
||||||
y[5] = 1.581345e+00;
|
|
||||||
y[6] = 1.795050e+00;
|
|
||||||
y[7] = 1.965613e+00;
|
|
||||||
y[8] = 2.237466e+00;
|
|
||||||
y[9] = 2.439729e+00;
|
|
||||||
|
|
||||||
spline(x,y,n,1.0E+30,1.0E+30,z);
|
|
||||||
splint(x,y,z,n,log(DELTA_HALO),a4);
|
|
||||||
|
|
||||||
// now adjust for redshift
|
|
||||||
if(!(REDSHIFT>0))return;
|
|
||||||
|
|
||||||
ztemp = REDSHIFT;
|
|
||||||
if(REDSHIFT>3) ztemp = 3.0;
|
|
||||||
*a1 *= pow(1+ztemp,-0.14);
|
|
||||||
*a2 *= pow(1+ztemp,-0.14);
|
|
||||||
at = -pow(0.75/log10(DELTA_HALO/75),1.2);
|
|
||||||
at = pow(10.0,at);
|
|
||||||
*a3 *= pow(1+ztemp,-at);
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,146 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* This is a calculation of the differential halo mass function of
|
|
||||||
* Jenkins et al 2001 (MNRAS 321, 372).
|
|
||||||
*
|
|
||||||
* Also included is the mass function from my own analysis, which is
|
|
||||||
* a variant of the Sheth-Tormen mass function (leaving all 3 parameters
|
|
||||||
* as free parameters, with a 2-parameter high-mass cutoff of the form
|
|
||||||
* suggested by Reed et al.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
double halo_mass_function(double mass)
|
|
||||||
{
|
|
||||||
double sig,logm,a,slo,shi,rm,rlo,rhi,mlo,mhi,dsdM,n,nuprime,nufnu,p,A;
|
|
||||||
static int flag=0, prev_cosmo=-1,na=4;
|
|
||||||
static double pnorm,*xa,*ya,*za;
|
|
||||||
|
|
||||||
double fac1,fac2,fac;
|
|
||||||
static long IDUM=-555;
|
|
||||||
int i;
|
|
||||||
static double
|
|
||||||
a1 = 0.325277,
|
|
||||||
a2 = 0.492785,
|
|
||||||
a3 = 0.310289,
|
|
||||||
a4 = 1.317104,
|
|
||||||
a5 = 2.425681;
|
|
||||||
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
xa=dvector(1,na);
|
|
||||||
ya=dvector(1,na);
|
|
||||||
za=dvector(1,na);
|
|
||||||
flag=1;
|
|
||||||
xa[1] = log(1/2.51);
|
|
||||||
xa[2] = log(1/1.49);
|
|
||||||
xa[3] = log(1/0.905);
|
|
||||||
xa[4] = log(1/0.501);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(prev_cosmo != RESET_COSMOLOGY)
|
|
||||||
{
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
for(i=1;i<=4;++i)
|
|
||||||
ya[i] = gasdev(&IDUM);
|
|
||||||
spline(xa,ya,na,1.0E+30,1.0E+30,za);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* First normalize the power spectrum
|
|
||||||
*/
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
|
|
||||||
rm=pow(3.0*mass/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
sig=pnorm*sigmac(rm);
|
|
||||||
logm=log10(mass);
|
|
||||||
|
|
||||||
mlo=0.99*mass;
|
|
||||||
mhi=1.01*mass;
|
|
||||||
rlo=pow(3.0*mlo/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
rhi=pow(3.0*mhi/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
slo=pnorm*sigmac(rlo);
|
|
||||||
shi=pnorm*sigmac(rhi);
|
|
||||||
dsdM=(shi-slo)/(mhi-mlo);
|
|
||||||
|
|
||||||
if(BEST_FIT)
|
|
||||||
{
|
|
||||||
n = a1*sqrt(2*a2/PI)*(1+pow(sig*sig/(a2*DELTA_CRIT*DELTA_CRIT),a3))
|
|
||||||
*DELTA_CRIT/sig*exp(-a2*DELTA_CRIT*DELTA_CRIT/(2*sig*sig))
|
|
||||||
*exp(-a4/sig/pow(fabs(cosh(2*sig)),a5));
|
|
||||||
|
|
||||||
splint(xa,ya,za,na,log(1/sig),&fac1);
|
|
||||||
fac2 = 0.00562*pow(sig,-2.9) + 0.00158*pow(sig,2.2);
|
|
||||||
fac = 1 + fac1*fac2;
|
|
||||||
if(fac<0.01)fac=0.01;
|
|
||||||
n = n*fac;
|
|
||||||
/* printf("%e %e %e %e\n",sig,n,n/fac,fac); */
|
|
||||||
n = -n*OMEGA_M*RHO_CRIT/mass/sig*dsdM;
|
|
||||||
return(n);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Jenkins et al.
|
|
||||||
*/
|
|
||||||
a=-JENKINS_A*OMEGA_M*RHO_CRIT/mass/sig;
|
|
||||||
n=a*dsdM*exp(-pow(fabs(JENKINS_B-log(sig)),JENKINS_C));
|
|
||||||
return(n);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* It may be a bit costly to run the above function every time you need
|
|
||||||
* dn/dM, so here we put the values into an array and then interpolate.
|
|
||||||
*/
|
|
||||||
double dndM_interp(double m)
|
|
||||||
{
|
|
||||||
static int flag=0,prev_cosmo=0;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int i,n=1000;
|
|
||||||
double dm,max=16.7,min=9,a,m1,m2,dm1;
|
|
||||||
|
|
||||||
if(!flag || RESET_COSMOLOGY!=prev_cosmo)
|
|
||||||
{
|
|
||||||
if(!ThisTask && OUTPUT)
|
|
||||||
fprintf(stdout,"RESET: resetting mass function for %f %f\n",OMEGA_M,SIGMA_8);
|
|
||||||
fflush(stdout);
|
|
||||||
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
dm=(double)(max-min)/n;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x[i]=pow(10.0,min+i*dm);
|
|
||||||
y[i]=log(halo_mass_function(x[i]));
|
|
||||||
if(DELTA_HALO!=200)
|
|
||||||
{
|
|
||||||
m1 = halo_mass_conversion2(x[i]*1.001,halo_c200(x[i]*1.001),DELTA_HALO,200.0);
|
|
||||||
m2 = halo_mass_conversion2(x[i]*0.999,halo_c200(x[i]*0.999),DELTA_HALO,200.0);
|
|
||||||
dm1 = (x[i]*1.001 - x[i]*0.999)/(m1-m2);
|
|
||||||
y[i] = y[i] + log10(dm1);
|
|
||||||
x[i]=log10(halo_mass_conversion2(x[i],halo_c200(x[i]),DELTA_HALO,200.0));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
x[i]=log(x[i]);
|
|
||||||
}
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
}
|
|
||||||
|
|
||||||
m=log(m);
|
|
||||||
splint(x,y,y2,n,m,&a);
|
|
||||||
return(exp(a));
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,95 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <string.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <time.h>
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
double *mu_x,*mu_y,*mu_z;
|
|
||||||
int mu_n;
|
|
||||||
|
|
||||||
/* Equation (10) of vdB et al, assuming alpha = 1 (standard NFW)
|
|
||||||
*/
|
|
||||||
double func_jeans1(double x)
|
|
||||||
{
|
|
||||||
return(x/(1+x)/(1+x));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Equation (11) of vdB et al.
|
|
||||||
*/
|
|
||||||
double func_jeans2(double x)
|
|
||||||
{
|
|
||||||
double y;
|
|
||||||
splint(mu_x,mu_y,mu_z,mu_n,x,&y);
|
|
||||||
return(y/(x*x*x*(1+x)*(1+x)));
|
|
||||||
}
|
|
||||||
double jeans_dispersion(double mass, double rx, double v[])
|
|
||||||
{
|
|
||||||
int i,j,k,n,nc,nr;
|
|
||||||
double rmin,rmax,dlogr;
|
|
||||||
static double cmin,cmax,dlogc;
|
|
||||||
double rvir,rs,s1,sig,mu1,vcirc,cvir;
|
|
||||||
|
|
||||||
static long IDUM2 = -4555;
|
|
||||||
|
|
||||||
static double fac=-1;
|
|
||||||
static int prev_cosmo=-1;
|
|
||||||
|
|
||||||
if(fac<0)
|
|
||||||
{
|
|
||||||
mu_n = nc = 1000;
|
|
||||||
cmin = 0.1;
|
|
||||||
cmax = 100.0;
|
|
||||||
dlogc = (log(cmax) - log(cmin))/(nc-1);
|
|
||||||
|
|
||||||
mu_x = dvector(1,nc);
|
|
||||||
mu_y = dvector(1,nc);
|
|
||||||
mu_z = dvector(1,nc);
|
|
||||||
|
|
||||||
for(i=1;i<=nc;++i)
|
|
||||||
{
|
|
||||||
mu_x[i] = exp((i-1)*dlogc)*cmin;
|
|
||||||
mu_y[i] = qromo(func_jeans1,0,mu_x[i],midpnt);
|
|
||||||
}
|
|
||||||
spline(mu_x,mu_y,nc,1.0E+30,1.0E+30,mu_z);
|
|
||||||
fac=sqrt(4.499E-48)*3.09E19;
|
|
||||||
}
|
|
||||||
|
|
||||||
cvir = halo_concentration(mass);
|
|
||||||
rvir = pow(3*mass/(4*PI*DELTA_HALO*OMEGA_M*RHO_CRIT),THIRD);
|
|
||||||
rs = rvir/cvir;
|
|
||||||
rx = rx/rs;
|
|
||||||
vcirc = fac*fac*mass/rvir;
|
|
||||||
splint(mu_x,mu_y,mu_z,mu_n,cvir,&mu1);
|
|
||||||
|
|
||||||
s1 = qromo(func_jeans2,rx,cmax,midpnt);
|
|
||||||
sig = sqrt(cvir*vcirc/mu1*rx*(1+rx)*(1+rx)*s1);
|
|
||||||
|
|
||||||
if(isnan(sig))
|
|
||||||
sig = sqrt(vcirc/2);
|
|
||||||
|
|
||||||
for(i=0;i<3;++i)
|
|
||||||
v[i]=gasdev(&IDUM2)*sig*VBIAS;
|
|
||||||
|
|
||||||
return sig;
|
|
||||||
|
|
||||||
nr = 100;
|
|
||||||
rmin = rvir*0.01;
|
|
||||||
rmax = rvir*0.99;
|
|
||||||
dlogr = (log(rmax) - log(rmin))/(nr-1);
|
|
||||||
rs = rvir/cvir;
|
|
||||||
|
|
||||||
vcirc = fac*fac*mass/rvir;
|
|
||||||
splint(mu_x,mu_y,mu_z,mu_n,cvir,&mu1);
|
|
||||||
|
|
||||||
for(i=0;i<nr;++i)
|
|
||||||
{
|
|
||||||
rx = exp(i*dlogr)*rmin/rs;
|
|
||||||
s1 = qromo(func_jeans2,rx,cmax,midpnt);
|
|
||||||
sig = cvir/mu1*rx*(1+rx)*(1+rx)*s1*2;
|
|
||||||
printf("%f %f\n",rx*rs/rvir,sqrt(sig));
|
|
||||||
}
|
|
||||||
exit(0);
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,432 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* Local variables for the coordinate in redshift space.
|
|
||||||
*/
|
|
||||||
double rs_g8,rp_g8;
|
|
||||||
|
|
||||||
/* Internal functions.
|
|
||||||
*/
|
|
||||||
double func_kaiser(double z);
|
|
||||||
double xi_bar(double r);
|
|
||||||
double f_xibar(double r);
|
|
||||||
double xi_prime(double r, double mu);
|
|
||||||
double xi_t(double r);
|
|
||||||
double Lpoly(double x, int i);
|
|
||||||
double f_xi2bar(double r);
|
|
||||||
double xi_harmonic(double r, int i);
|
|
||||||
double scale_dependent_dispersion(double r);
|
|
||||||
double scale_dependent_skewness(double r);
|
|
||||||
|
|
||||||
void initial_dispersion_model_values(double *a, double **pp, double *yy);
|
|
||||||
void dispersion_model_input(void);
|
|
||||||
double chi2_dispersion_model(double *a);
|
|
||||||
|
|
||||||
/* Internal variables.
|
|
||||||
*/
|
|
||||||
struct DISPERION_MODEL_STRUCT {
|
|
||||||
int n;
|
|
||||||
double **rs,**rp;
|
|
||||||
double **x,**e;
|
|
||||||
} XX;
|
|
||||||
|
|
||||||
double *rr_g8, *aa_g8;
|
|
||||||
int nparams_g8, niter_g8=0;
|
|
||||||
|
|
||||||
void fit_dispersion_model()
|
|
||||||
{
|
|
||||||
int n,niter,i,j;
|
|
||||||
double *a,**pp,*yy,FTOL=1.0E-3,chi2min,s1,dlogm,m;
|
|
||||||
FILE *fp;
|
|
||||||
char aa[1000];
|
|
||||||
|
|
||||||
fprintf(stderr,"\n\nCHI2 MINIMIZATION OF xi(SIGMA,PI) WITH DISPERSION MODEL.\n");
|
|
||||||
fprintf(stderr, "--------------------------------------------------------\n\n");
|
|
||||||
|
|
||||||
if(POWELL)
|
|
||||||
FTOL=1.0E-4;
|
|
||||||
else
|
|
||||||
FTOL=1.0E-4;
|
|
||||||
|
|
||||||
nparams_g8 = n = 8;
|
|
||||||
|
|
||||||
dispersion_model_input();
|
|
||||||
|
|
||||||
wp.ncf=n;
|
|
||||||
a=dvector(1,n);
|
|
||||||
rr_g8 = dvector(1,n);
|
|
||||||
aa_g8 = dvector(1,n);
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
rr_g8[i] = (log(10)-log(0.1))/(n-1.)*(i-1) + log(0.1);
|
|
||||||
|
|
||||||
BETA = 0.5;
|
|
||||||
|
|
||||||
if(POWELL)
|
|
||||||
pp=dmatrix(1,n,1,n);
|
|
||||||
else
|
|
||||||
pp=dmatrix(1,n+1,1,n);
|
|
||||||
yy=dvector(1,n+1);
|
|
||||||
|
|
||||||
initial_dispersion_model_values(a,pp,yy);
|
|
||||||
|
|
||||||
if(POWELL)
|
|
||||||
{
|
|
||||||
if(OUTPUT)printf("dispersion_model> starting powell.\n");
|
|
||||||
powell(a,pp,n,FTOL,&niter,&chi2min,chi2_dispersion_model);
|
|
||||||
chi2min = chi2_dispersion_model(a);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if(OUTPUT)printf("dispersion_model> starting amoeba.\n");
|
|
||||||
amoeba(pp,yy,n,FTOL,chi2_dispersion_model,&niter);
|
|
||||||
for(i=1;i<=n;++i)a[i]=pp[1][i];
|
|
||||||
chi2min = chi2_dispersion_model(a);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void initial_dispersion_model_values(double *a, double **pp, double *yy)
|
|
||||||
{
|
|
||||||
static int flag=0;
|
|
||||||
int i,j;
|
|
||||||
double d[100];
|
|
||||||
|
|
||||||
|
|
||||||
if(!flag) {
|
|
||||||
for(i=1;i<=nparams_g8;++i)
|
|
||||||
a[i] = 500;
|
|
||||||
|
|
||||||
printf("INITIAL VALUES: ");
|
|
||||||
for(i=1;i<=wp.ncf;++i)printf("%e ",a[i]);
|
|
||||||
printf("\n");
|
|
||||||
}
|
|
||||||
flag++;
|
|
||||||
|
|
||||||
/* Make the starting stepsize 10% of the initial values.
|
|
||||||
*/
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
d[i]=a[i]*0.1/flag;
|
|
||||||
|
|
||||||
|
|
||||||
if(POWELL)
|
|
||||||
{
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
{
|
|
||||||
for(j=1;j<=wp.ncf;++j)
|
|
||||||
{
|
|
||||||
pp[i][j]=0;
|
|
||||||
if(i==j)pp[i][j]+=d[j];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
for(j=1;j<=wp.ncf;++j)
|
|
||||||
pp[1][j]=a[j];
|
|
||||||
yy[1]=chi2_dispersion_model(a);
|
|
||||||
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
{
|
|
||||||
a[i]+=d[i];
|
|
||||||
if(i>1)a[i-1]-=d[i-1];
|
|
||||||
yy[i+1]=chi2_dispersion_model(a);
|
|
||||||
for(j=1;j<=wp.ncf;++j)
|
|
||||||
pp[i+1][j]=a[j];
|
|
||||||
}
|
|
||||||
a[wp.ncf]-=d[wp.ncf];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void dispersion_model_input()
|
|
||||||
{
|
|
||||||
FILE *fp;
|
|
||||||
int i,j;
|
|
||||||
|
|
||||||
fp = openfile("xi2d.data");
|
|
||||||
XX.n = (int)sqrt(filesize(fp)*0.99)+1;
|
|
||||||
|
|
||||||
XX.rs = dmatrix(1,XX.n,1,XX.n);
|
|
||||||
XX.rp = dmatrix(1,XX.n,1,XX.n);
|
|
||||||
XX.x = dmatrix(1,XX.n,1,XX.n);
|
|
||||||
XX.e = dmatrix(1,XX.n,1,XX.n);
|
|
||||||
|
|
||||||
for(i=1;i<=XX.n;++i)
|
|
||||||
for(j=1;j<=XX.n;++j)
|
|
||||||
fscanf(fp,"%lf %lf %lf %lf",&XX.rs[i][j],&XX.rp[i][j],&XX.x[i][j],&XX.e[i][j]);
|
|
||||||
|
|
||||||
fclose(fp);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
double chi2_dispersion_model(double *a)
|
|
||||||
{
|
|
||||||
int i,j;
|
|
||||||
double xx,r,chi2=0;
|
|
||||||
|
|
||||||
for(i=1;i<=nparams_g8;++i)
|
|
||||||
{
|
|
||||||
aa_g8[i] = a[i];
|
|
||||||
if(a[i]<=0)return(1.0E7);
|
|
||||||
}
|
|
||||||
|
|
||||||
for(i=2;i<=XX.n;++i)
|
|
||||||
for(j=2;j<=XX.n;++j)
|
|
||||||
{
|
|
||||||
xx = kaiser_distortion(XX.rs[i][j],XX.rp[i][j]);
|
|
||||||
/* printf("%f %f %f %f %f\n",XX.rs[i][j],XX.rp[i][j],XX.x[i][j],xx,xx); */
|
|
||||||
chi2 += (xx-XX.x[i][j])*(xx-XX.x[i][j])/(XX.e[i][j]*XX.e[i][j]);
|
|
||||||
}
|
|
||||||
niter_g8++;
|
|
||||||
printf("ITER %d %e ",niter_g8,chi2);
|
|
||||||
for(i=1;i<=nparams_g8;++i)
|
|
||||||
printf("%e ",a[i]);
|
|
||||||
printf("\n");
|
|
||||||
fflush(stdout);
|
|
||||||
|
|
||||||
if(niter_g8%100==0)
|
|
||||||
{
|
|
||||||
for(i=1;i<=100;++i)
|
|
||||||
{
|
|
||||||
r = exp((log(40)-log(0.1))/(100-1.)*(i-1) + log(0.1));
|
|
||||||
xx = scale_dependent_dispersion(r);
|
|
||||||
printf("PVD %d %f %f\n",niter_g8,r,xx);
|
|
||||||
}
|
|
||||||
fflush(stdout);
|
|
||||||
}
|
|
||||||
|
|
||||||
return(chi2);
|
|
||||||
}
|
|
||||||
|
|
||||||
double kaiser_distortion(double rs, double rp)
|
|
||||||
{
|
|
||||||
double s1,rlim=60,rr;
|
|
||||||
static int prev=-1;
|
|
||||||
|
|
||||||
if(prev==-1 || prev!=RESET_COSMOLOGY)
|
|
||||||
{
|
|
||||||
prev=RESET_COSMOLOGY;
|
|
||||||
/*
|
|
||||||
BETA = pow(OMEGA_M,0.6)/qromo(func_galaxy_bias,HOD.M_low,HOD.M_max,midpnt)*
|
|
||||||
GALAXY_DENSITY;
|
|
||||||
*/
|
|
||||||
printf("kaiser> BETA= %f SIGV= %f\n",BETA,SIGV);
|
|
||||||
}
|
|
||||||
|
|
||||||
rs_g8=rs;
|
|
||||||
rp_g8=rp;
|
|
||||||
rr=sqrt(rs*rs+rp*rp);
|
|
||||||
/* if(rr*1.5>10)rlim=rr*5.5; */
|
|
||||||
/* s1=qromo(func_kaiser,-rlim,rlim,midpnt); */
|
|
||||||
s1=qtrap(func_kaiser,-rlim,rlim,1.0E-3);
|
|
||||||
return(s1-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
double linear_kaiser_distortion(double r, double z)
|
|
||||||
{
|
|
||||||
double mu;
|
|
||||||
|
|
||||||
mu= sqrt(1 - z/r*z/r);
|
|
||||||
mu = z/r;
|
|
||||||
return xi_prime(r,mu);
|
|
||||||
}
|
|
||||||
|
|
||||||
double func_kaiser(double z)
|
|
||||||
{
|
|
||||||
double r,mu,v,x,sigv;
|
|
||||||
|
|
||||||
r=sqrt(z*z+rs_g8*rs_g8);
|
|
||||||
mu=z/r;
|
|
||||||
v=(rp_g8-z)*100.0;
|
|
||||||
|
|
||||||
sigv = scale_dependent_dispersion(r);
|
|
||||||
/*
|
|
||||||
if(v*z<0)
|
|
||||||
sigv*=scale_dependent_skewness(r);
|
|
||||||
*/
|
|
||||||
/*
|
|
||||||
x=(1+one_halo_real_space(r)+two_halo_real_space(r))*
|
|
||||||
exp(-ROOT2*fabs(v)/sigv)/ROOT2/sigv*100.0;
|
|
||||||
*/
|
|
||||||
x=(1+xi_prime(r,mu)+one_halo_real_space(r))*exp(-ROOT2*fabs(v)/sigv)/ROOT2/sigv*100.0;
|
|
||||||
return(x);
|
|
||||||
}
|
|
||||||
double scale_dependent_skewness(double r)
|
|
||||||
{
|
|
||||||
return 1.5;
|
|
||||||
}
|
|
||||||
|
|
||||||
double scale_dependent_dispersion(double r)
|
|
||||||
{
|
|
||||||
static int niter=-1,flag=0;
|
|
||||||
static double *z,*x,*y;
|
|
||||||
double a;
|
|
||||||
int i;
|
|
||||||
|
|
||||||
if(niter!=niter_g8)
|
|
||||||
{
|
|
||||||
niter = niter_g8;
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
flag++;
|
|
||||||
x=dvector(1,nparams_g8+1);
|
|
||||||
y=dvector(1,nparams_g8+1);
|
|
||||||
z=dvector(1,nparams_g8+1);
|
|
||||||
y[1] = 0;
|
|
||||||
x[1] = log(0.01);
|
|
||||||
for(i=2;i<=nparams_g8+1;++i)
|
|
||||||
x[i] = rr_g8[i-1];
|
|
||||||
}
|
|
||||||
for(i=2;i<=nparams_g8+1;++i)
|
|
||||||
y[i] = aa_g8[i-1];
|
|
||||||
spline(x,y,nparams_g8+1,1.0E+30,1.0E+30,z);
|
|
||||||
}
|
|
||||||
r=log(r);
|
|
||||||
if(r>rr_g8[nparams_g8])return(aa_g8[nparams_g8]);
|
|
||||||
splint(x,y,z,nparams_g8+1,r,&a);
|
|
||||||
return(a);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This function tabulates the spherically averaged correlation function.
|
|
||||||
* Equation (A7) in Madgwick et al.
|
|
||||||
*/
|
|
||||||
double xi_bar(double r)
|
|
||||||
{
|
|
||||||
static int flag=0,prev=-1;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int n=100,i;
|
|
||||||
static double rmin,rmax,lgr,a;
|
|
||||||
|
|
||||||
if(!flag || prev!=RESET_KAISER)
|
|
||||||
{
|
|
||||||
if(OUTPUT>1)
|
|
||||||
printf("Tabulating xi_bar...\n");
|
|
||||||
prev=RESET_KAISER;
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=malloc(n*sizeof(double));
|
|
||||||
x--;
|
|
||||||
y=malloc(n*sizeof(double));
|
|
||||||
y--;
|
|
||||||
y2=malloc(n*sizeof(double));
|
|
||||||
y2--;
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
rmin=-1.9;
|
|
||||||
rmin=log10(R_MIN_2HALO);
|
|
||||||
rmax=log10(80.0);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
lgr=(rmax-rmin)*(i-1.0)/(n-1.0)+rmin;
|
|
||||||
x[i]=pow(10.0,lgr);
|
|
||||||
y[i]=qtrap(f_xibar,0.0,x[i],1.0E-4)*3/(x[i]*x[i]*x[i]);
|
|
||||||
//printf("XIBAR %f %e\n",x[i],y[i]);
|
|
||||||
}
|
|
||||||
spline(x,y,n,1.0E30,1.0E30,y2);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(r<x[1])return(-1);
|
|
||||||
splint(x,y,y2,n,r,&a);
|
|
||||||
//if(a<xi_t(r))return(xi_t(r));
|
|
||||||
return(a);
|
|
||||||
}
|
|
||||||
|
|
||||||
double f_xibar(double r)
|
|
||||||
{
|
|
||||||
double x;
|
|
||||||
x=two_halo_real_space(r);
|
|
||||||
/* x=one_halo_real_space(r)+two_halo_real_space(r); */
|
|
||||||
return(x*r*r);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This function tabulates the xi(r)*r^4 dr function.
|
|
||||||
* Equation (A8)
|
|
||||||
*/
|
|
||||||
double xi_2bar(double r)
|
|
||||||
{
|
|
||||||
static int flag=0,prev=-1;
|
|
||||||
static double *x,*y,*y2,rmin;
|
|
||||||
int n=100,i;
|
|
||||||
double rmax,lgr,a;
|
|
||||||
|
|
||||||
if(!flag || prev!=RESET_KAISER)
|
|
||||||
{
|
|
||||||
if(OUTPUT>1)
|
|
||||||
printf("Tabulating xi_2bar...\n");
|
|
||||||
prev=RESET_KAISER;
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=malloc(n*sizeof(double));
|
|
||||||
x--;
|
|
||||||
y=malloc(n*sizeof(double));
|
|
||||||
y--;
|
|
||||||
y2=malloc(n*sizeof(double));
|
|
||||||
y2--;
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
rmin=-1.9;
|
|
||||||
rmin = log10(R_MIN_2HALO);
|
|
||||||
rmax=log10(80.0);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
lgr=(rmax-rmin)*(i-1.0)/(n-1.0)+rmin;
|
|
||||||
x[i]=pow(10.0,lgr);
|
|
||||||
y[i]=qtrap(f_xi2bar,0.0,x[i],1.0E-4)*5/(x[i]*x[i]*x[i]*x[i]*x[i]);
|
|
||||||
//printf("XI2BAR %f %e\n",x[i],y[i]);
|
|
||||||
}
|
|
||||||
spline(x,y,n,1.0E30,1.0E30,y2);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(r<x[1])return(-1);
|
|
||||||
splint(x,y,y2,n,r,&a);
|
|
||||||
// if(a<xi_t(r))return(xi_t(r));
|
|
||||||
return(a);
|
|
||||||
}
|
|
||||||
|
|
||||||
double f_xi2bar(double r)
|
|
||||||
{
|
|
||||||
double x;
|
|
||||||
x=two_halo_real_space(r);
|
|
||||||
/* x=one_halo_real_space(r)+two_halo_real_space(r); */
|
|
||||||
return(x*r*r*r*r);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* These are Legendre polynomials
|
|
||||||
*/
|
|
||||||
double Lpoly(double x, int i)
|
|
||||||
{
|
|
||||||
switch(i) {
|
|
||||||
case 0: return(1.0);
|
|
||||||
case 2: return(0.5*(3*x*x-1));
|
|
||||||
case 4: return((35*x*x*x*x-30*x*x+3)/8.0);
|
|
||||||
/*case 4: return((384*x*x*x*x+1152*x*x*(x*x-1)+144*(x*x-1)*(x*x-1))/(16.*24.));*/
|
|
||||||
default: return(0.0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
double xi_harmonic(double r, int i)
|
|
||||||
{
|
|
||||||
switch(i){
|
|
||||||
case 0: return((1+2.*BETA/3.+BETA*BETA/5.)*xi_t(r));
|
|
||||||
case 2: return((4.*BETA/3.+4.*BETA*BETA/7.)*(xi_t(r)-xi_bar(r)));
|
|
||||||
case 4: return(8.*BETA*BETA/35.*(xi_t(r)+2.5*xi_bar(r)-3.5*xi_2bar(r)));
|
|
||||||
default: return(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
double xi_prime(double r, double mu)
|
|
||||||
{
|
|
||||||
double x0,x2,x4;
|
|
||||||
x0=xi_harmonic(r,0)*Lpoly(mu,0);
|
|
||||||
x2=xi_harmonic(r,2)*Lpoly(mu,2);
|
|
||||||
x4=xi_harmonic(r,4)*Lpoly(mu,4);
|
|
||||||
return(x0+x2+x4);
|
|
||||||
}
|
|
||||||
|
|
||||||
double xi_t(double r)
|
|
||||||
{
|
|
||||||
return(two_halo_real_space(r));
|
|
||||||
return(one_halo_real_space(r)+two_halo_real_space(r));
|
|
||||||
}
|
|
|
@ -1,469 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <string.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#ifdef PARALLEL
|
|
||||||
#include <mpi.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* External functions from wp_minimization.c
|
|
||||||
*/
|
|
||||||
void wp_input(void);
|
|
||||||
double mcmc_initialize(double *a, double **cov1, double *avg1, double *start_dev);
|
|
||||||
|
|
||||||
/* Internal functions.
|
|
||||||
*/
|
|
||||||
double chi2_wp_wrapper(double *a);
|
|
||||||
|
|
||||||
int USE_IWEIGHT = 0;
|
|
||||||
|
|
||||||
|
|
||||||
/******************************************************************
|
|
||||||
*
|
|
||||||
* HOD.free[] also controls which variables will be held constant/vary
|
|
||||||
* during MCMC minimization. Since this routine will also so z-space
|
|
||||||
* minimization if requested, indices>6 are cosmological.
|
|
||||||
*
|
|
||||||
* i variable
|
|
||||||
* --- --------
|
|
||||||
* [1] -> M_min
|
|
||||||
* [2] -> M1
|
|
||||||
* [3] -> alpha
|
|
||||||
* [4] -> M_cut
|
|
||||||
* [5] -> sigmaM
|
|
||||||
* [6] -> CVIR_FAC
|
|
||||||
* [7] -> MaxCen (or M_cen_max)
|
|
||||||
* [8] -> M_sat_break
|
|
||||||
* [9] -> alpha1
|
|
||||||
*
|
|
||||||
* [10]-> OMEGA_M
|
|
||||||
* [11]-> SIGMA_8
|
|
||||||
* [12]-> VBIAS
|
|
||||||
* [13]-> VBIAS_C
|
|
||||||
* [14]-> GAMMA
|
|
||||||
* [15]-> SPECTRAL_INDX
|
|
||||||
*
|
|
||||||
* [0] -> The galaxy_density will be considered data with errors on it,
|
|
||||||
* and therefore no variable will be fixed by the galaxy density.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
void mcmc_minimization()
|
|
||||||
{
|
|
||||||
double stepfac=1;
|
|
||||||
double error=1,tolerance=0,**cov1,**tmp,*a,*avg1,chi2,chi2prev,
|
|
||||||
**evect,*eval,*aprev,*atemp,**tmp1,*opar,x1,fsat,**chain,*start_dev,*eval_prev;
|
|
||||||
int n,i,j,k,nrot,niter=0,count=0,imax_chain=100000,NSTEP=50,NSTEP_MAX=10000,convergence=0;
|
|
||||||
long IDUM=-555;
|
|
||||||
|
|
||||||
int *pcheck,pcnt,ptot=20,firstflag=1,*iweight,total_weight,icvir;
|
|
||||||
double t0,tprev,temp,chi2a,chi2b;
|
|
||||||
|
|
||||||
FILE *fpmcmc;
|
|
||||||
char fname[1000];
|
|
||||||
|
|
||||||
sprintf(fname,"%s.MCMC",Task.root_filename);
|
|
||||||
fpmcmc = fopen(fname,"w");
|
|
||||||
|
|
||||||
opar=dvector(1,100);
|
|
||||||
|
|
||||||
MCMC=Task.MCMC;
|
|
||||||
|
|
||||||
pcheck=calloc(ptot,sizeof(int));
|
|
||||||
|
|
||||||
wp_input();
|
|
||||||
|
|
||||||
Work.imodel=2;
|
|
||||||
Work.chi2=1;
|
|
||||||
|
|
||||||
OUTPUT=0;
|
|
||||||
|
|
||||||
srand48(32498793);
|
|
||||||
|
|
||||||
/* Find the number of free parameters in the minimization
|
|
||||||
* for the real-space correlation function.
|
|
||||||
*/
|
|
||||||
for(n=0,i=1;i<100;++i)
|
|
||||||
{
|
|
||||||
n+=HOD.free[i];
|
|
||||||
if(OUTPUT)
|
|
||||||
printf("mcmc_min> free[%i] = %d\n",i,HOD.free[i]);
|
|
||||||
}
|
|
||||||
wp.ncf=n;
|
|
||||||
|
|
||||||
/* Find out which free parameter is for CVIR_FAC
|
|
||||||
*/
|
|
||||||
j=0;
|
|
||||||
if(HOD.free[6])
|
|
||||||
for(i=0;i<6;++i)
|
|
||||||
if(HOD.free[i])j++;
|
|
||||||
icvir=j+1;
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
if(HOD.free[0])
|
|
||||||
{
|
|
||||||
wp.ngal = GALAXY_DENSITY;
|
|
||||||
wp.ngal_err = 0.1*wp.ngal;
|
|
||||||
FIX_PARAM = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(OUTPUT)
|
|
||||||
printf("mcmc_min> %d free parameters\n",n);
|
|
||||||
|
|
||||||
a=dvector(1,n);
|
|
||||||
start_dev=dvector(1,n);
|
|
||||||
aprev=dvector(1,n);
|
|
||||||
atemp=dvector(1,n);
|
|
||||||
cov1=dmatrix(1,n,1,n);
|
|
||||||
avg1=dvector(1,n);
|
|
||||||
|
|
||||||
tmp=dmatrix(1,n,1,n);
|
|
||||||
tmp1=dmatrix(1,n,1,1);
|
|
||||||
evect=dmatrix(1,n,1,n);
|
|
||||||
eval=dvector(1,n);
|
|
||||||
eval_prev=dvector(1,n);
|
|
||||||
|
|
||||||
chain=dmatrix(1,imax_chain,1,n);
|
|
||||||
iweight = ivector(1,imax_chain);
|
|
||||||
for(i=1;i<=imax_chain;++i)
|
|
||||||
iweight[i] = 0;
|
|
||||||
|
|
||||||
IDUM=IDUM_MCMC;
|
|
||||||
|
|
||||||
|
|
||||||
chi2prev=mcmc_initialize(a,cov1,avg1,start_dev);
|
|
||||||
niter++;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
aprev[i] = a[i];
|
|
||||||
chain[1][i] = a[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
pcnt=0;
|
|
||||||
pcheck[pcnt]=1;
|
|
||||||
|
|
||||||
stepfac=1;
|
|
||||||
while(niter<NSTEP)
|
|
||||||
{
|
|
||||||
pcnt++;
|
|
||||||
if(pcnt==ptot)
|
|
||||||
{
|
|
||||||
for(j=i=0;i<ptot;++i)j+=pcheck[i];
|
|
||||||
stepfac = stepfac*pow(0.9,5-j);
|
|
||||||
if(!ThisTask)printf("STEPFAC %f %d %d\n",stepfac,j,count);
|
|
||||||
pcnt=0;
|
|
||||||
}
|
|
||||||
/* stepfac=0.7; */
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] = (1+gasdev(&IDUM)*start_dev[i]*stepfac)*aprev[i];
|
|
||||||
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
RESET_COSMOLOGY++;
|
|
||||||
j=0;
|
|
||||||
for(i=1;i<=N_HOD_PARAMS;++i)if(HOD.free[i])j++;
|
|
||||||
i=N_HOD_PARAMS;
|
|
||||||
if(HOD.free[++i])OMEGA_M = a[++j];
|
|
||||||
if(HOD.free[++i])SIGMA_8 = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS_C = a[++j];
|
|
||||||
if(HOD.free[++i])GAMMA = a[++j];
|
|
||||||
if(HOD.free[++i])SPECTRAL_INDX = a[++j];
|
|
||||||
}
|
|
||||||
if(VBIAS_C<0)continue;
|
|
||||||
|
|
||||||
/* Hard-wire CVIR variation
|
|
||||||
*/
|
|
||||||
if(HOD.free[6])
|
|
||||||
CVIR_FAC = a[icvir];
|
|
||||||
|
|
||||||
chi2=chi2_wp_wrapper(a);
|
|
||||||
|
|
||||||
pcheck[pcnt]=1;
|
|
||||||
if(!(chi2<chi2prev || drand48() <= exp(-(chi2-chi2prev)/2)))
|
|
||||||
{
|
|
||||||
if(USE_IWEIGHT)
|
|
||||||
iweight[niter+1]++;
|
|
||||||
pcheck[pcnt]=0;
|
|
||||||
continue;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
niter++;
|
|
||||||
iweight[niter]++;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
chain[niter][i]=a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
avg1[i] += a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
aprev[i] = a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
cov1[i][j] += a[i]*a[j];
|
|
||||||
chi2prev=chi2;
|
|
||||||
|
|
||||||
if(!ThisTask){
|
|
||||||
fprintf(fpmcmc,"%d %d ",niter,count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%e ",a[i]);
|
|
||||||
printf("%e\n",chi2);fflush(fpmcmc);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
stepfac=1.6/sqrt(n);
|
|
||||||
pcnt=-1;
|
|
||||||
t0 = second();
|
|
||||||
|
|
||||||
NSTEP = niter;
|
|
||||||
|
|
||||||
while(niter<imax_chain)
|
|
||||||
{
|
|
||||||
stepfac=1.6/sqrt(n);
|
|
||||||
|
|
||||||
if(convergence)goto SKIP_MATRIX;
|
|
||||||
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
{
|
|
||||||
avg1[j]=0;
|
|
||||||
for(k=1;k<=n;++k)
|
|
||||||
cov1[j][k]=0;
|
|
||||||
}
|
|
||||||
total_weight = 0;
|
|
||||||
for(i=1;i<=niter;++i)
|
|
||||||
{
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
{
|
|
||||||
avg1[j]+=chain[i][j]*iweight[i];
|
|
||||||
for(k=1;k<=n;++k)
|
|
||||||
cov1[j][k]+=chain[i][j]*chain[i][k]*iweight[i];
|
|
||||||
}
|
|
||||||
total_weight+=iweight[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
tmp[i][j] = cov1[i][j]/total_weight - avg1[i]*avg1[j]/(total_weight*total_weight);
|
|
||||||
|
|
||||||
jacobi(tmp,n,eval,evect,&nrot);
|
|
||||||
gaussj(evect,n,tmp1,1);
|
|
||||||
|
|
||||||
SKIP_MATRIX:
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
atemp[i] = gasdev(&IDUM)*sqrt(eval[i])*stepfac;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(a[i]=0,j=1;j<=n;++j)
|
|
||||||
a[i] += atemp[j]*evect[j][i];
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] += aprev[i];
|
|
||||||
|
|
||||||
/* We seem to be having a problem with this.
|
|
||||||
* So, broadcast the model params from the root processor.
|
|
||||||
*/
|
|
||||||
#ifdef PARALLEL
|
|
||||||
MPI_Bcast(&a[1],n,MPI_DOUBLE_PRECISION,0,MPI_COMM_WORLD);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
RESET_COSMOLOGY++;
|
|
||||||
j=0;
|
|
||||||
for(i=1;i<=N_HOD_PARAMS;++i)if(HOD.free[i])j++;
|
|
||||||
i=N_HOD_PARAMS;
|
|
||||||
if(HOD.free[++i])OMEGA_M = a[++j];
|
|
||||||
if(HOD.free[++i])SIGMA_8 = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS_C = a[++j];
|
|
||||||
if(HOD.free[++i])GAMMA = a[++j];
|
|
||||||
if(HOD.free[++i])SPECTRAL_INDX = a[++j];
|
|
||||||
/* if(HOD.free[++i])SIGV = a[++j]; */
|
|
||||||
}
|
|
||||||
if(VBIAS_C<0)continue;
|
|
||||||
|
|
||||||
/* Hard-wire CVIR variation
|
|
||||||
*/
|
|
||||||
if(HOD.free[6])
|
|
||||||
CVIR_FAC = a[icvir];
|
|
||||||
|
|
||||||
|
|
||||||
chi2=chi2_wp_wrapper(a);
|
|
||||||
|
|
||||||
tprev = t0;
|
|
||||||
t0 = second();
|
|
||||||
++count;
|
|
||||||
|
|
||||||
pcheck[pcnt]=0;
|
|
||||||
if(!(chi2<chi2prev || drand48() <= exp(-(chi2-chi2prev)/2)))
|
|
||||||
{
|
|
||||||
if(USE_IWEIGHT)
|
|
||||||
iweight[niter+1]++;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
pcheck[pcnt]=1;
|
|
||||||
|
|
||||||
niter++;
|
|
||||||
if(!convergence)NSTEP = niter;
|
|
||||||
iweight[niter]++;
|
|
||||||
|
|
||||||
if(niter%NSTEP_MAX==0 && !convergence && niter>NSTEP_MAX)
|
|
||||||
{
|
|
||||||
convergence = 1;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x1=fabs(eval[i]-eval_prev[i])/eval_prev[i];
|
|
||||||
if(x1>0.01)convergence = 0;
|
|
||||||
printf("CONVERGENCE CHECK %d %d %e %e %e\n",niter/NSTEP_MAX,i,x1,eval[i],eval_prev[i]);
|
|
||||||
}
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
eval_prev[i] = eval[i];
|
|
||||||
convergence = 0;
|
|
||||||
|
|
||||||
if(convergence)
|
|
||||||
printf("CONVERGENCE ACCOMPLISHED %d %d \n",niter,count);
|
|
||||||
}
|
|
||||||
if(niter==NSTEP_MAX)
|
|
||||||
{
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
eval_prev[i] = eval[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
chain[niter][i]=a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
avg1[i] += a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
aprev[i] = a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
cov1[i][j] += a[i]*a[j];
|
|
||||||
chi2prev=chi2;
|
|
||||||
|
|
||||||
if(!ThisTask) {
|
|
||||||
fprintf(fpmcmc,"%d %d ",niter,count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%e ",a[i]);
|
|
||||||
printf("%e\n",chi2);fflush(fpmcmc);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
double chi2_wp_wrapper(double *a)
|
|
||||||
{
|
|
||||||
static int flag=1;
|
|
||||||
static double *b;
|
|
||||||
int i,j;
|
|
||||||
|
|
||||||
if(flag)
|
|
||||||
{
|
|
||||||
b=dvector(1,100);
|
|
||||||
flag=0;
|
|
||||||
}
|
|
||||||
|
|
||||||
for(j=0,i=1;i<=N_HOD_PARAMS;++i) {
|
|
||||||
if(HOD.free[i] && i!=5) {
|
|
||||||
if(a[++j]<=0) { printf("NEG %d %d %e\n",i,j,a[j]); return(1.0E7); } }
|
|
||||||
if(HOD.free[i] && i==5) {
|
|
||||||
++j; }
|
|
||||||
}
|
|
||||||
|
|
||||||
i=0;j=0;
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M_min */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M1 */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=a[j];} /* alpha */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M_cut */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* sigma_logM */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=a[j];} /* cvir_fac */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* MaxCen */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M_sat_break */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=a[j];} /* alpha1 */
|
|
||||||
|
|
||||||
return(chi2_wp(b));
|
|
||||||
}
|
|
||||||
|
|
||||||
double mcmc_initialize(double *a, double **cov1, double *avg1, double *start_dev)
|
|
||||||
{
|
|
||||||
int i,j=0;
|
|
||||||
double x1,x2,omega_m;
|
|
||||||
long IDUM = -556;
|
|
||||||
|
|
||||||
omega_m = 1;
|
|
||||||
if(MCMC>1)
|
|
||||||
omega_m = OMEGA_M;
|
|
||||||
|
|
||||||
i=0;j=0;
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M_min/omega_m);start_dev[j]=0.001; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M1/omega_m);start_dev[j]=0.001; } //.0005
|
|
||||||
if(HOD.free[++i]){ a[++j]=HOD.alpha;start_dev[j]=0.03; } //.005
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M_cut/omega_m);start_dev[j]=0.01; } //.001
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.sigma_logM);start_dev[j]=0.01; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=CVIR_FAC;start_dev[j]=0.02; }
|
|
||||||
if(HOD.pdfc==7) {
|
|
||||||
if(HOD.free[++i])a[++j]=log10(HOD.M_cen_max/omega_m); start_dev[j]=0.001; }
|
|
||||||
else {
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.MaxCen; start_dev[j]=0.02; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M_sat_break/omega_m);start_dev[j]=0.001; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=HOD.alpha1;start_dev[j]=0.02; }
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
if(HOD.free[++i])a[++j]=OMEGA_M;
|
|
||||||
if(HOD.free[++i])a[++j]=SIGMA_8;
|
|
||||||
if(HOD.free[++i])a[++j]=VBIAS;
|
|
||||||
if(HOD.free[++i])a[++j]=VBIAS_C;
|
|
||||||
if(HOD.free[++i])a[++j]=GAMMA;
|
|
||||||
if(HOD.free[++i])a[++j]=SPECTRAL_INDX;
|
|
||||||
}
|
|
||||||
if(!ThisTask)
|
|
||||||
{
|
|
||||||
printf("INITIAL VALUES: ");
|
|
||||||
for(i=1;i<=wp.ncf;++i)printf("%e ",a[i]);
|
|
||||||
printf("\n");
|
|
||||||
}
|
|
||||||
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
{
|
|
||||||
avg1[i]=a[i];
|
|
||||||
for(j=1;j<=wp.ncf;++j)
|
|
||||||
cov1[i][j]=a[i]*a[j];
|
|
||||||
}
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
RESET_COSMOLOGY++;
|
|
||||||
j=0;
|
|
||||||
for(i=1;i<=N_HOD_PARAMS;++i)if(HOD.free[i])j++;
|
|
||||||
i=N_HOD_PARAMS;
|
|
||||||
if(HOD.free[++i]){ OMEGA_M = a[++j]; start_dev[j] = 0.01; }
|
|
||||||
if(HOD.free[++i]){ SIGMA_8 = a[++j]; start_dev[j] = 0.01; }
|
|
||||||
if(HOD.free[++i]){ VBIAS = a[++j]; start_dev[j] = 0.01; }
|
|
||||||
if(HOD.free[++i]){ VBIAS_C = a[++j]; start_dev[j] = 0.02; }
|
|
||||||
if(HOD.free[++i]){ GAMMA = a[++j]; start_dev[j] = 0.015; }
|
|
||||||
if(HOD.free[++i]){ SPECTRAL_INDX = a[++j]; start_dev[j] = 0.02; }
|
|
||||||
}
|
|
||||||
|
|
||||||
x1=chi2_wp_wrapper(a);
|
|
||||||
|
|
||||||
x2=0;
|
|
||||||
|
|
||||||
if(!ThisTask) {
|
|
||||||
printf("TRY 0 ");
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
printf("%.4e ",a[i]);
|
|
||||||
printf("%e\n",x1+x2);fflush(stdout);
|
|
||||||
printf("INITIAL CHI2: %e %e\n",x1,x2);
|
|
||||||
fflush(stdout);
|
|
||||||
}
|
|
||||||
return(x1+x2);
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,539 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <string.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#ifdef PARALLEL
|
|
||||||
#include <mpi.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
|
|
||||||
/* External functions from wp_minimization.c
|
|
||||||
*/
|
|
||||||
void wp_input(void);
|
|
||||||
void wp_color_input(void);
|
|
||||||
double chi2_wp_color(double *a);
|
|
||||||
double chi2_wp_color_wrapper(double *a);
|
|
||||||
|
|
||||||
/* inteernal functions
|
|
||||||
*/
|
|
||||||
double mcmc_color_initialize(double *a, double **cov1, double *avg1, double *start_dev);
|
|
||||||
|
|
||||||
|
|
||||||
void mcmc_color_minimization()
|
|
||||||
{
|
|
||||||
double stepfac=1;
|
|
||||||
double error=1,tolerance=0,**cov1,**tmp,*a,*avg1,chi2,chi2prev,
|
|
||||||
**evect,*eval,*aprev,*atemp,**tmp1,*opar,x1,fsat,**chain,*start_dev,*eval_prev;
|
|
||||||
int n,i,j,k,nrot,niter=0,count=0,imax_chain=100000,NSTEP=50,NSTEP_MAX=10000,convergence=0;
|
|
||||||
long IDUM=-555;
|
|
||||||
|
|
||||||
int *pcheck,pcnt,ptot=20,firstflag=1,*iweight,total_weight;
|
|
||||||
double t0,tprev,temp,chi2a,chi2b;
|
|
||||||
|
|
||||||
opar=dvector(1,100);
|
|
||||||
|
|
||||||
MCMC=Task.MCMC;
|
|
||||||
|
|
||||||
pcheck=calloc(ptot,sizeof(int));
|
|
||||||
|
|
||||||
Work.imodel=2;
|
|
||||||
Work.chi2=1;
|
|
||||||
|
|
||||||
|
|
||||||
OUTPUT=1;
|
|
||||||
|
|
||||||
|
|
||||||
fprintf(stderr,"\n\nMCMC OF W_P(R_P) COLOR DATA..........\n");
|
|
||||||
fprintf(stderr, "--------------------------------------------\n\n");
|
|
||||||
|
|
||||||
HOD.blue_fraction = 0.5857; /* <- Millenium fraction (sloan);; SDSS fraction -> 0.565; */
|
|
||||||
HOD.blue_fraction = 0.6555; /* <- Millenium fraction (B-V>0.8) */
|
|
||||||
HOD.blue_fraction = 0.565; /* SDSS -19,-20 */
|
|
||||||
HOD.blue_fraction = 0.492; /* SDSS -20,-21 */
|
|
||||||
HOD.blue_fraction = 0.379; /* SDSS -21 */
|
|
||||||
|
|
||||||
wp_color.ON = 1;
|
|
||||||
|
|
||||||
wp_color_input();
|
|
||||||
|
|
||||||
|
|
||||||
srand48(32498793);
|
|
||||||
|
|
||||||
/* Find the number of free parameters in the minimization
|
|
||||||
* for the real-space correlation function.
|
|
||||||
*/
|
|
||||||
for(n=0,i=1;i<12;++i)
|
|
||||||
{
|
|
||||||
n+=HOD.free[i];
|
|
||||||
/* if(i>N_HOD_PARAMS && HOD.free[i])MCMC=3;*/
|
|
||||||
if(OUTPUT)
|
|
||||||
printf("mcmc_min> free[%i] = %d\n",i,HOD.free[i]);
|
|
||||||
}
|
|
||||||
|
|
||||||
// add 3 parameters for the color stuff
|
|
||||||
n+=3;
|
|
||||||
wp.ncf=n;
|
|
||||||
|
|
||||||
if(HOD.free[0])
|
|
||||||
{
|
|
||||||
wp.ngal = GALAXY_DENSITY;
|
|
||||||
wp.ngal_err = 0.1*wp.ngal;
|
|
||||||
FIX_PARAM = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(OUTPUT)
|
|
||||||
printf("mcmc_min> %d free parameters\n",n);
|
|
||||||
|
|
||||||
a=dvector(1,n);
|
|
||||||
start_dev=dvector(1,n);
|
|
||||||
aprev=dvector(1,n);
|
|
||||||
atemp=dvector(1,n);
|
|
||||||
cov1=dmatrix(1,n,1,n);
|
|
||||||
avg1=dvector(1,n);
|
|
||||||
|
|
||||||
tmp=dmatrix(1,n,1,n);
|
|
||||||
tmp1=dmatrix(1,n,1,1);
|
|
||||||
evect=dmatrix(1,n,1,n);
|
|
||||||
eval=dvector(1,n);
|
|
||||||
eval_prev=dvector(1,n);
|
|
||||||
|
|
||||||
chain=dmatrix(1,imax_chain,1,n);
|
|
||||||
iweight = ivector(1,imax_chain);
|
|
||||||
for(i=1;i<=imax_chain;++i)
|
|
||||||
iweight[i] = 0;
|
|
||||||
|
|
||||||
IDUM=IDUM_MCMC;
|
|
||||||
|
|
||||||
//chi2prev=mcmc_initialize(a,cov1,avg1,start_dev);
|
|
||||||
chi2prev=mcmc_color_initialize(a,cov1,avg1,start_dev);
|
|
||||||
//initial_color_values(a,pp,yy);
|
|
||||||
|
|
||||||
niter++;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
aprev[i] = a[i];
|
|
||||||
chain[1][i] = a[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
pcnt=0;
|
|
||||||
pcheck[pcnt]=1;
|
|
||||||
|
|
||||||
stepfac=1;
|
|
||||||
while(niter<NSTEP)
|
|
||||||
{
|
|
||||||
pcnt++;
|
|
||||||
if(pcnt==ptot)
|
|
||||||
{
|
|
||||||
for(j=i=0;i<ptot;++i)j+=pcheck[i];
|
|
||||||
stepfac = stepfac*pow(0.9,5-j);
|
|
||||||
if(!ThisTask)printf("STEPFAC %f %d %d\n",stepfac,j,count);
|
|
||||||
pcnt=0;
|
|
||||||
}
|
|
||||||
/* stepfac=0.7; */
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] = (1+gasdev(&IDUM)*start_dev[i]*stepfac)*aprev[i];
|
|
||||||
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
RESET_COSMOLOGY++;
|
|
||||||
j=0;
|
|
||||||
for(i=1;i<=N_HOD_PARAMS;++i)if(HOD.free[i])j++;
|
|
||||||
i=N_HOD_PARAMS;
|
|
||||||
if(HOD.free[++i])OMEGA_M = a[++j];
|
|
||||||
if(HOD.free[++i])SIGMA_8 = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS_C = a[++j];
|
|
||||||
if(HOD.free[++i])GAMMA = a[++j];
|
|
||||||
if(HOD.free[++i])SPECTRAL_INDX = a[++j];
|
|
||||||
/* if(HOD.free[++i])SIGV = a[++j]; */
|
|
||||||
}
|
|
||||||
if(VBIAS_C<0)continue;
|
|
||||||
|
|
||||||
/* Hard-wire CVIR variation
|
|
||||||
*/
|
|
||||||
if(HOD.free[6])
|
|
||||||
CVIR_FAC = a[3];
|
|
||||||
|
|
||||||
chi2=chi2_wp_color_wrapper(a);
|
|
||||||
|
|
||||||
if(!ThisTask){
|
|
||||||
printf("TRY %d ",++count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%.4e ",a[i]);
|
|
||||||
printf("%e\n",chi2);fflush(stdout);
|
|
||||||
}
|
|
||||||
|
|
||||||
pcheck[pcnt]=1;
|
|
||||||
if(!(chi2<chi2prev || drand48() <= exp(-(chi2-chi2prev)/2)))
|
|
||||||
{
|
|
||||||
/* This for loop puts the prev element in the chain is
|
|
||||||
* the current trial point is rejected.
|
|
||||||
*/
|
|
||||||
/* For the initialization, don't use this: we need
|
|
||||||
* separate elements for estimating the covariance matrix.
|
|
||||||
*/
|
|
||||||
/*
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] = aprev[i];
|
|
||||||
chi2 = chi2prev;
|
|
||||||
*/
|
|
||||||
pcheck[pcnt]=0;
|
|
||||||
continue;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
niter++;
|
|
||||||
iweight[niter]++;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
chain[niter][i]=a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
avg1[i] += a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
aprev[i] = a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
cov1[i][j] += a[i]*a[j];
|
|
||||||
chi2prev=chi2;
|
|
||||||
|
|
||||||
if(!ThisTask){
|
|
||||||
printf("ACCEPT %d %d ",niter,count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%e ",a[i]);
|
|
||||||
printf("%e\n",chi2);fflush(stdout);
|
|
||||||
printf("HSTATS %d %e %e %e %e\n",niter,HOD.M_min,number_weighted_halo_mass(),
|
|
||||||
number_weighted_central_mass(),
|
|
||||||
qromo(func_satellite_density,log(HOD.M_low),log(HOD.M_max),midpnt)/GALAXY_DENSITY);
|
|
||||||
printf("FSAT %d %e %e %e %e\n",niter,HOD.M_min,wp.fsat_red,wp.fsat_blue,wp.fsat_all);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
RESTART_POINT:
|
|
||||||
|
|
||||||
stepfac=1.6/sqrt(n);
|
|
||||||
pcnt=-1;
|
|
||||||
t0 = second();
|
|
||||||
|
|
||||||
NSTEP = niter;
|
|
||||||
|
|
||||||
while(niter<imax_chain)
|
|
||||||
{
|
|
||||||
pcnt++;
|
|
||||||
if(pcnt==ptot)
|
|
||||||
{
|
|
||||||
for(j=i=0;i<ptot;++i)j+=pcheck[i];
|
|
||||||
//stepfac=1.6/sqrt(n);
|
|
||||||
//stepfac=0.6/sqrt(n);
|
|
||||||
// stepfac = stepfac*pow(0.9,6-j);
|
|
||||||
stepfac = 0.25;
|
|
||||||
stepfac = 0.5;
|
|
||||||
stepfac=1.6/sqrt(n);
|
|
||||||
if(!ThisTask)printf("STEPFAC %f %d %d\n",stepfac,j,count);
|
|
||||||
pcnt=0;
|
|
||||||
}
|
|
||||||
stepfac=1.6/sqrt(n);
|
|
||||||
//stepfac = 0;
|
|
||||||
|
|
||||||
if(convergence)goto SKIP_MATRIX;
|
|
||||||
// if(niter>NSTEP_MAX && niter%NSTEP_MAX!=0)goto SKIP_MATRIX;
|
|
||||||
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
{
|
|
||||||
avg1[j]=0;
|
|
||||||
for(k=1;k<=n;++k)
|
|
||||||
cov1[j][k]=0;
|
|
||||||
}
|
|
||||||
total_weight = 0;
|
|
||||||
for(i=1;i<=niter;++i)
|
|
||||||
{
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
{
|
|
||||||
avg1[j]+=chain[i][j]*iweight[i];
|
|
||||||
for(k=1;k<=n;++k)
|
|
||||||
cov1[j][k]+=chain[i][j]*chain[i][k]*iweight[i];
|
|
||||||
}
|
|
||||||
total_weight+=iweight[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
tmp[i][j] = cov1[i][j]/total_weight - avg1[i]*avg1[j]/(total_weight*total_weight);
|
|
||||||
|
|
||||||
jacobi(tmp,n,eval,evect,&nrot);
|
|
||||||
gaussj(evect,n,tmp1,1);
|
|
||||||
|
|
||||||
SKIP_MATRIX:
|
|
||||||
if(RESTART==4)convergence = 1;
|
|
||||||
|
|
||||||
if(RESTART && count==0)stepfac=0;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
atemp[i] = gasdev(&IDUM)*sqrt(eval[i])*stepfac;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(a[i]=0,j=1;j<=n;++j)
|
|
||||||
a[i] += atemp[j]*evect[j][i];
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] += aprev[i];
|
|
||||||
|
|
||||||
/* We seem to be having a problem with this.
|
|
||||||
* So, broadcast the model params from the root processor.
|
|
||||||
*/
|
|
||||||
#ifdef PARALLEL
|
|
||||||
MPI_Bcast(&a[1],n,MPI_DOUBLE_PRECISION,0,MPI_COMM_WORLD);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// CHeck that the chi2 for the last point in the restart chain
|
|
||||||
// is recovered.
|
|
||||||
/*
|
|
||||||
if(RESTART && !count)
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] = aprev[i];
|
|
||||||
*/
|
|
||||||
if(RESTART==5)
|
|
||||||
{
|
|
||||||
j = count+1;
|
|
||||||
if(j>4000)exit(0);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] = chain[j][i];
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
if(!ThisTask)
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
printf("COV %d %d %e ",count,i,sqrt(eval[i]));
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
printf("%e ",evect[j][i]);
|
|
||||||
printf("\n");
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Using only variances
|
|
||||||
*/
|
|
||||||
//for(i=1;i<=n;++i)
|
|
||||||
// a[i] = aprev[i] + gasdev(&IDUM)*sqrt(tmp[i][i])*stepfac;
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
RESET_COSMOLOGY++;
|
|
||||||
j=0;
|
|
||||||
for(i=1;i<=N_HOD_PARAMS;++i)if(HOD.free[i])j++;
|
|
||||||
i=N_HOD_PARAMS;
|
|
||||||
if(HOD.free[++i])OMEGA_M = a[++j];
|
|
||||||
if(HOD.free[++i])SIGMA_8 = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS_C = a[++j];
|
|
||||||
if(HOD.free[++i])GAMMA = a[++j];
|
|
||||||
if(HOD.free[++i])SPECTRAL_INDX = a[++j];
|
|
||||||
/* if(HOD.free[++i])SIGV = a[++j]; */
|
|
||||||
}
|
|
||||||
if(VBIAS_C<0)continue;
|
|
||||||
|
|
||||||
/* Hard-wire CVIR variation
|
|
||||||
*/
|
|
||||||
if(HOD.free[6])
|
|
||||||
CVIR_FAC = a[3];
|
|
||||||
|
|
||||||
chi2=chi2_wp_color_wrapper(a);
|
|
||||||
|
|
||||||
tprev = t0;
|
|
||||||
t0 = second();
|
|
||||||
++count;
|
|
||||||
if(!ThisTask) {
|
|
||||||
printf("TRY %d ",count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%.4e ",a[i]);
|
|
||||||
if(RESTART==2) {
|
|
||||||
printf("%e %e %.2f\n",chi2,chi2/(1+exp(-count/100.0)),
|
|
||||||
timediff(tprev,t0));fflush(stdout); }
|
|
||||||
else {
|
|
||||||
printf("%e %.2f\n",chi2,
|
|
||||||
timediff(tprev,t0));fflush(stdout); }
|
|
||||||
}
|
|
||||||
if(0) {
|
|
||||||
printf("CPU%02d %d ",ThisTask,count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%.4e ",a[i]);
|
|
||||||
if(RESTART==2) {
|
|
||||||
printf("%e %e %.2f\n",chi2,chi2/(1+exp(-count/100.0)),
|
|
||||||
timediff(tprev,t0));fflush(stdout); }
|
|
||||||
else {
|
|
||||||
printf("%e %.2f\n",chi2,
|
|
||||||
timediff(tprev,t0));fflush(stdout); }
|
|
||||||
}
|
|
||||||
|
|
||||||
pcheck[pcnt]=0;
|
|
||||||
if(!(chi2<chi2prev || drand48() <= exp(-(chi2-chi2prev)/2)))
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] = aprev[i];
|
|
||||||
chi2 = chi2prev;
|
|
||||||
*/
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
pcheck[pcnt]=1;
|
|
||||||
|
|
||||||
// if(NSTEP<NSTEP_MAX)NSTEP++;
|
|
||||||
niter++;
|
|
||||||
if(!convergence)NSTEP = niter;
|
|
||||||
iweight[niter]++;
|
|
||||||
|
|
||||||
if(niter%NSTEP_MAX==0 && !convergence && niter>NSTEP_MAX)
|
|
||||||
{
|
|
||||||
convergence = 1;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x1=fabs(eval[i]-eval_prev[i])/eval_prev[i];
|
|
||||||
if(x1>0.01)convergence = 0;
|
|
||||||
printf("CONVERGENCE CHECK %d %d %e %e %e\n",niter/NSTEP_MAX,i,x1,eval[i],eval_prev[i]);
|
|
||||||
}
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
eval_prev[i] = eval[i];
|
|
||||||
convergence = 0;
|
|
||||||
|
|
||||||
if(convergence)
|
|
||||||
printf("CONVERGENCE ACCOMPLISHED %d %d \n",niter,count);
|
|
||||||
}
|
|
||||||
if(niter==NSTEP_MAX)
|
|
||||||
{
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
eval_prev[i] = eval[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
chain[niter][i]=a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
avg1[i] += a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
aprev[i] = a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
cov1[i][j] += a[i]*a[j];
|
|
||||||
chi2prev=chi2;
|
|
||||||
|
|
||||||
if(!ThisTask) {
|
|
||||||
printf("ACCEPT %d %d ",niter,count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%e ",a[i]);
|
|
||||||
printf("%e\n",chi2);fflush(stdout);
|
|
||||||
|
|
||||||
printf("FSAT %d %e %e %e %e\n",niter,HOD.M_min,wp.fsat_red,wp.fsat_blue,wp.fsat_all);
|
|
||||||
if(MCMC==1)
|
|
||||||
{
|
|
||||||
printf("HSTATS %d %e %e %e %e\n",niter,HOD.M_min,number_weighted_halo_mass(),
|
|
||||||
number_weighted_central_mass(),
|
|
||||||
qromo(func_satellite_density,log(HOD.M_low),log(HOD.M_max),midpnt)/GALAXY_DENSITY);
|
|
||||||
|
|
||||||
fsat = qromo(func_satfrac,log(HOD.M_low),log(HOD.M_max),midpnt)/GALAXY_DENSITY;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
double chi2_wp_color_wrapper(double *a)
|
|
||||||
{
|
|
||||||
static int flag=1;
|
|
||||||
static double *b;
|
|
||||||
int i,j;
|
|
||||||
|
|
||||||
if(flag)
|
|
||||||
{
|
|
||||||
b=dvector(1,100);
|
|
||||||
flag=0;
|
|
||||||
}
|
|
||||||
|
|
||||||
for(j=0,i=1;i<=N_HOD_PARAMS;++i) {
|
|
||||||
if(HOD.free[i] && i!=5) {
|
|
||||||
if(a[++j]<=0) { printf("NEG %d %d %e\n",i,j,a[j]); return(1.0E7); } }
|
|
||||||
if(HOD.free[i] && i==5) {
|
|
||||||
++j; }
|
|
||||||
}
|
|
||||||
|
|
||||||
i=0;j=0;
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M_min */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M1 */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=a[j];} /* alpha */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M_cut */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* sigma_logM */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=a[j];} /* cvir_fac */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* MaxCen */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M_sat_break */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=a[j];} /* alpha1 */
|
|
||||||
|
|
||||||
// now the 3 color params
|
|
||||||
++j;
|
|
||||||
b[j] = a[j];
|
|
||||||
++j;
|
|
||||||
b[j] = a[j];
|
|
||||||
++j;
|
|
||||||
b[j] = a[j];
|
|
||||||
|
|
||||||
muh(1);
|
|
||||||
|
|
||||||
return(chi2_wp_color(b));
|
|
||||||
}
|
|
||||||
|
|
||||||
double mcmc_color_initialize(double *a, double **cov1, double *avg1, double *start_dev)
|
|
||||||
{
|
|
||||||
int i,j=0;
|
|
||||||
double x1,x2,omega_m;
|
|
||||||
long IDUM = -556;
|
|
||||||
|
|
||||||
i=0;j=0;
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M_min); start_dev[j]=0.001; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M1); start_dev[j] = 0.001; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=HOD.alpha; start_dev[j] = 0.03; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M_cut); start_dev[j] = 0.01; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.sigma_logM); start_dev[j] = 0.01; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=CVIR_FAC; start_dev[j] = 0.02; }
|
|
||||||
if(HOD.pdfc>=7){
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M_cen_max); start_dev[j] = 0.001; }}
|
|
||||||
else {
|
|
||||||
if(HOD.free[++i]) { a[++j]=log10(HOD.MaxCen); start_dev[j] = 0.001; }}
|
|
||||||
|
|
||||||
a[++j] = HOD.fblue0_sat;
|
|
||||||
start_dev[j] = 0.01;
|
|
||||||
a[++j] = HOD.sigma_fblue_sat;
|
|
||||||
start_dev[j] = 0.01;
|
|
||||||
a[++j] = HOD.sigma_fblue_cen;
|
|
||||||
start_dev[j] = 0.01;
|
|
||||||
|
|
||||||
if(!ThisTask)
|
|
||||||
{
|
|
||||||
printf("INITIAL VALUES: ");
|
|
||||||
for(i=1;i<=wp.ncf;++i)printf("%e ",a[i]);
|
|
||||||
printf("\n");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
{
|
|
||||||
avg1[i]=a[i];
|
|
||||||
for(j=1;j<=wp.ncf;++j)
|
|
||||||
cov1[i][j]=a[i]*a[j];
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
x1=chi2_wp_color_wrapper(a);
|
|
||||||
x2 = 0;
|
|
||||||
|
|
||||||
if(!ThisTask) {
|
|
||||||
printf("TRY 0 ");
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
printf("%.4e ",a[i]);
|
|
||||||
printf("%e\n",x1+x2);fflush(stdout);
|
|
||||||
printf("INITIAL CHI2: %e %e\n",x1,x2);
|
|
||||||
fflush(stdout);
|
|
||||||
}
|
|
||||||
return(x1+x2);
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,632 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <string.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#ifdef PARALLEL
|
|
||||||
#include <mpi.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* External functions from wp_minimization.c
|
|
||||||
*/
|
|
||||||
void wp_input(void);
|
|
||||||
double mcmc_initialize(double *a, double **cov1, double *avg1, double *start_dev);
|
|
||||||
|
|
||||||
/* Internal functions.
|
|
||||||
*/
|
|
||||||
double chi2_wp_wrapper(double *a);
|
|
||||||
void mcmc_restart2(double *start_dev, int np);
|
|
||||||
int mcmc_restart3(double **chain, int n, double *chi2_prev, int *iweight);
|
|
||||||
|
|
||||||
int USE_IWEIGHT = 0;
|
|
||||||
|
|
||||||
/******************************************************************
|
|
||||||
*
|
|
||||||
* HOD.free[] also controls which variables will be held constant/vary
|
|
||||||
* during MCMC minimization. Since this routine will also so z-space
|
|
||||||
* minimization if requested, indices>6 are cosmological.
|
|
||||||
*
|
|
||||||
* i variable
|
|
||||||
* --- --------
|
|
||||||
* [1] -> M_min
|
|
||||||
* [2] -> M1
|
|
||||||
* [3] -> alpha
|
|
||||||
* [4] -> M_cut
|
|
||||||
* [5] -> sigmaM
|
|
||||||
* [6] -> CVIR_FAC
|
|
||||||
* [7] -> MaxCen (or M_cen_max)
|
|
||||||
* [8] -> M_sat_break
|
|
||||||
* [9] -> alpha1
|
|
||||||
*
|
|
||||||
* [10]-> OMEGA_M
|
|
||||||
* [11]-> SIGMA_8
|
|
||||||
* [12]-> VBIAS
|
|
||||||
* [13]-> VBIAS_C
|
|
||||||
* [14]-> GAMMA
|
|
||||||
* [15]-> SPECTRAL_INDX
|
|
||||||
*
|
|
||||||
* [0] -> The galaxy_density will be considered data with errors on it,
|
|
||||||
* and therefore no variable will be fixed by the galaxy density.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
void mcmc_minimization()
|
|
||||||
{
|
|
||||||
double stepfac=1;
|
|
||||||
double error=1,tolerance=0,**cov1,**tmp,*a,*avg1,chi2,chi2prev,
|
|
||||||
**evect,*eval,*aprev,*atemp,**tmp1,*opar,x1,fsat,**chain,*start_dev,*eval_prev;
|
|
||||||
int n,i,j,k,nrot,niter=0,count=0,imax_chain=100000,NSTEP=150,NSTEP_MAX=1000,convergence=0;
|
|
||||||
long IDUM=-555;
|
|
||||||
|
|
||||||
int *pcheck,pcnt,ptot=20,firstflag=1,*iweight,total_weight;
|
|
||||||
double t0,tprev,temp;
|
|
||||||
|
|
||||||
opar=dvector(1,100);
|
|
||||||
|
|
||||||
MCMC=Task.MCMC;
|
|
||||||
|
|
||||||
pcheck=calloc(ptot,sizeof(int));
|
|
||||||
|
|
||||||
if(MCMC>1 && !COVAR)
|
|
||||||
wp.esys=0.05;
|
|
||||||
|
|
||||||
if(!ThisTask)printf("ESYS %f %d\n",wp.esys,MCMC);
|
|
||||||
wp_input();
|
|
||||||
|
|
||||||
Work.imodel=2;
|
|
||||||
Work.chi2=1;
|
|
||||||
|
|
||||||
/*
|
|
||||||
OUTPUT=0;
|
|
||||||
*/
|
|
||||||
|
|
||||||
srand48(32498793);
|
|
||||||
|
|
||||||
/* Find the number of free parameters in the minimization
|
|
||||||
* for the real-space correlation function.
|
|
||||||
*/
|
|
||||||
for(n=0,i=1;i<100;++i)
|
|
||||||
{
|
|
||||||
n+=HOD.free[i];
|
|
||||||
/* if(i>N_HOD_PARAMS && HOD.free[i])MCMC=3;*/
|
|
||||||
if(OUTPUT)
|
|
||||||
printf("mcmc_min> free[%i] = %d\n",i,HOD.free[i]);
|
|
||||||
}
|
|
||||||
wp.ncf=n;
|
|
||||||
|
|
||||||
if(HOD.free[0])
|
|
||||||
{
|
|
||||||
wp.ngal = GALAXY_DENSITY;
|
|
||||||
wp.ngal_err = 0.1*wp.ngal;
|
|
||||||
FIX_PARAM = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(OUTPUT)
|
|
||||||
printf("mcmc_min> %d free parameters\n",n);
|
|
||||||
|
|
||||||
a=dvector(1,n);
|
|
||||||
start_dev=dvector(1,n);
|
|
||||||
aprev=dvector(1,n);
|
|
||||||
atemp=dvector(1,n);
|
|
||||||
cov1=dmatrix(1,n,1,n);
|
|
||||||
avg1=dvector(1,n);
|
|
||||||
|
|
||||||
tmp=dmatrix(1,n,1,n);
|
|
||||||
tmp1=dmatrix(1,n,1,1);
|
|
||||||
evect=dmatrix(1,n,1,n);
|
|
||||||
eval=dvector(1,n);
|
|
||||||
eval_prev=dvector(1,n);
|
|
||||||
|
|
||||||
chain=dmatrix(1,imax_chain,1,n);
|
|
||||||
iweight = ivector(1,imax_chain);
|
|
||||||
for(i=1;i<=imax_chain;++i)
|
|
||||||
iweight[i] = 0;
|
|
||||||
|
|
||||||
IDUM=IDUM_MCMC;
|
|
||||||
|
|
||||||
if(RESTART)
|
|
||||||
{
|
|
||||||
niter = mcmc_restart3(chain,n,&chi2prev,iweight);
|
|
||||||
if(niter < NSTEP)
|
|
||||||
{
|
|
||||||
if(ThisTask==0)
|
|
||||||
fprintf(stderr,"Not enough points in restart chain: %d<=%d\n",niter,NSTEP);
|
|
||||||
exit(0);
|
|
||||||
}
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
aprev[i] = chain[niter][i];
|
|
||||||
goto RESTART_POINT;
|
|
||||||
}
|
|
||||||
|
|
||||||
chi2prev=mcmc_initialize(a,cov1,avg1,start_dev);
|
|
||||||
niter++;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
aprev[i] = a[i];
|
|
||||||
chain[1][i] = a[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
pcnt=0;
|
|
||||||
pcheck[pcnt]=1;
|
|
||||||
|
|
||||||
if(RESTART==2)
|
|
||||||
{
|
|
||||||
mcmc_restart2(start_dev,n);
|
|
||||||
}
|
|
||||||
|
|
||||||
stepfac=1;
|
|
||||||
while(niter<NSTEP)
|
|
||||||
{
|
|
||||||
pcnt++;
|
|
||||||
if(pcnt==ptot)
|
|
||||||
{
|
|
||||||
for(j=i=0;i<ptot;++i)j+=pcheck[i];
|
|
||||||
stepfac = stepfac*pow(0.9,5-j);
|
|
||||||
if(!ThisTask)printf("STEPFAC %f %d %d\n",stepfac,j,count);
|
|
||||||
pcnt=0;
|
|
||||||
}
|
|
||||||
/* stepfac=0.7; */
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] = (1+gasdev(&IDUM)*start_dev[i]*stepfac)*aprev[i];
|
|
||||||
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
RESET_COSMOLOGY++;
|
|
||||||
j=0;
|
|
||||||
for(i=1;i<=N_HOD_PARAMS;++i)if(HOD.free[i])j++;
|
|
||||||
i=N_HOD_PARAMS;
|
|
||||||
if(HOD.free[++i])OMEGA_M = a[++j];
|
|
||||||
if(HOD.free[++i])SIGMA_8 = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS_C = a[++j];
|
|
||||||
if(HOD.free[++i])GAMMA = a[++j];
|
|
||||||
if(HOD.free[++i])SPECTRAL_INDX = a[++j];
|
|
||||||
/* if(HOD.free[++i])SIGV = a[++j]; */
|
|
||||||
}
|
|
||||||
if(VBIAS_C<0)continue;
|
|
||||||
|
|
||||||
/* Hard-wire CVIR variation
|
|
||||||
*/
|
|
||||||
if(HOD.free[6])
|
|
||||||
CVIR_FAC = a[3];
|
|
||||||
|
|
||||||
/* Draw random value of cvir from prior.
|
|
||||||
*/
|
|
||||||
/* if(CVIR_FAC<0.3 || CVIR_FAC>1.2)continue; */
|
|
||||||
/* CVIR_FAC = 0.9*drand48()+0.3; */
|
|
||||||
/* GAMMA = gasdev(&IDUM)*0.02 + 0.15; */
|
|
||||||
|
|
||||||
chi2=chi2_wp_wrapper(a);
|
|
||||||
|
|
||||||
if(MCMC>2 && chi2<1.0E7)chi2+=chi2_zspace(a);
|
|
||||||
|
|
||||||
if(!ThisTask){
|
|
||||||
printf("TRY %d ",++count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%.4e ",a[i]);
|
|
||||||
printf("%e\n",chi2);fflush(stdout);
|
|
||||||
}
|
|
||||||
|
|
||||||
pcheck[pcnt]=1;
|
|
||||||
if(!(chi2<chi2prev || drand48() <= exp(-(chi2-chi2prev)/2)))
|
|
||||||
{
|
|
||||||
/* This for loop puts the prev element in the chain is
|
|
||||||
* the current trial point is rejected.
|
|
||||||
*/
|
|
||||||
/* For the initialization, don't use this: we need
|
|
||||||
* separate elements for estimating the covariance matrix.
|
|
||||||
*/
|
|
||||||
/*
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] = aprev[i];
|
|
||||||
chi2 = chi2prev;
|
|
||||||
*/
|
|
||||||
if(USE_IWEIGHT)
|
|
||||||
iweight[niter+1]++;
|
|
||||||
pcheck[pcnt]=0;
|
|
||||||
continue;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
niter++;
|
|
||||||
iweight[niter]++;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
chain[niter][i]=a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
avg1[i] += a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
aprev[i] = a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
cov1[i][j] += a[i]*a[j];
|
|
||||||
chi2prev=chi2;
|
|
||||||
|
|
||||||
if(!ThisTask){
|
|
||||||
printf("ACCEPT %d %d ",niter,count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%e ",a[i]);
|
|
||||||
printf("%e\n",chi2);fflush(stdout);
|
|
||||||
printf("HSTATS %d %e %e %e %e\n",niter,HOD.M_min,number_weighted_halo_mass(),
|
|
||||||
number_weighted_central_mass(),
|
|
||||||
qromo(func_satellite_density,log(HOD.M_low),log(HOD.M_max),midpnt)/GALAXY_DENSITY);
|
|
||||||
|
|
||||||
fsat = qromo(func_satfrac,log(HOD.M_low),log(HOD.M_max),midpnt)/GALAXY_DENSITY;
|
|
||||||
printf("FSAT %d %e %e %e %e\n",niter,fsat,HOD.M_min,HOD.sigma_logM,CVIR_FAC);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
RESTART_POINT:
|
|
||||||
|
|
||||||
stepfac=1.6/sqrt(n);
|
|
||||||
pcnt=-1;
|
|
||||||
t0 = second();
|
|
||||||
|
|
||||||
NSTEP = niter;
|
|
||||||
|
|
||||||
while(niter<imax_chain)
|
|
||||||
{
|
|
||||||
pcnt++;
|
|
||||||
if(pcnt==ptot)
|
|
||||||
{
|
|
||||||
for(j=i=0;i<ptot;++i)j+=pcheck[i];
|
|
||||||
//stepfac=1.6/sqrt(n);
|
|
||||||
//stepfac=0.6/sqrt(n);
|
|
||||||
// stepfac = stepfac*pow(0.9,6-j);
|
|
||||||
stepfac = 0.25;
|
|
||||||
stepfac = 0.5;
|
|
||||||
stepfac=1.6/sqrt(n);
|
|
||||||
if(!ThisTask)printf("STEPFAC %f %d %d\n",stepfac,j,count);
|
|
||||||
pcnt=0;
|
|
||||||
}
|
|
||||||
//stepfac = 0;
|
|
||||||
|
|
||||||
if(convergence)goto SKIP_MATRIX;
|
|
||||||
// if(niter>NSTEP_MAX && niter%NSTEP_MAX!=0)goto SKIP_MATRIX;
|
|
||||||
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
{
|
|
||||||
avg1[j]=0;
|
|
||||||
for(k=1;k<=n;++k)
|
|
||||||
cov1[j][k]=0;
|
|
||||||
}
|
|
||||||
total_weight = 0;
|
|
||||||
for(i=1;i<=niter;++i)
|
|
||||||
{
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
{
|
|
||||||
avg1[j]+=chain[i][j]*iweight[i];
|
|
||||||
for(k=1;k<=n;++k)
|
|
||||||
cov1[j][k]+=chain[i][j]*chain[i][k]*iweight[i];
|
|
||||||
}
|
|
||||||
total_weight+=iweight[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
tmp[i][j] = cov1[i][j]/total_weight - avg1[i]*avg1[j]/(total_weight*total_weight);
|
|
||||||
|
|
||||||
jacobi(tmp,n,eval,evect,&nrot);
|
|
||||||
gaussj(evect,n,tmp1,1);
|
|
||||||
|
|
||||||
SKIP_MATRIX:
|
|
||||||
if(RESTART==4)convergence = 1;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
atemp[i] = gasdev(&IDUM)*sqrt(eval[i])*stepfac;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(a[i]=0,j=1;j<=n;++j)
|
|
||||||
a[i] += atemp[j]*evect[j][i];
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] += aprev[i];
|
|
||||||
|
|
||||||
if(!ThisTask)
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
printf("COV %d %d %e ",count,i,sqrt(eval[i]));
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
printf("%e ",evect[j][i]);
|
|
||||||
printf("\n");
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Using only variances
|
|
||||||
*/
|
|
||||||
//for(i=1;i<=n;++i)
|
|
||||||
// a[i] = aprev[i] + gasdev(&IDUM)*sqrt(tmp[i][i])*stepfac;
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
RESET_COSMOLOGY++;
|
|
||||||
j=0;
|
|
||||||
for(i=1;i<=N_HOD_PARAMS;++i)if(HOD.free[i])j++;
|
|
||||||
i=N_HOD_PARAMS;
|
|
||||||
if(HOD.free[++i])OMEGA_M = a[++j];
|
|
||||||
if(HOD.free[++i])SIGMA_8 = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS = a[++j];
|
|
||||||
if(HOD.free[++i])VBIAS_C = a[++j];
|
|
||||||
if(HOD.free[++i])GAMMA = a[++j];
|
|
||||||
if(HOD.free[++i])SPECTRAL_INDX = a[++j];
|
|
||||||
/* if(HOD.free[++i])SIGV = a[++j]; */
|
|
||||||
}
|
|
||||||
if(VBIAS_C<0)continue;
|
|
||||||
|
|
||||||
/* Hard-wire CVIR variation
|
|
||||||
*/
|
|
||||||
if(HOD.free[6])
|
|
||||||
CVIR_FAC = a[3];
|
|
||||||
|
|
||||||
/* Draw random value of cvir from prior.
|
|
||||||
*/
|
|
||||||
/* CVIR_FAC = a[n]; */
|
|
||||||
/* if(CVIR_FAC<0.3 || CVIR_FAC>1.2)continue; */
|
|
||||||
/* CVIR_FAC = 0.7*drand48()+0.3; */
|
|
||||||
/* GAMMA = gasdev(&IDUM)*0.02 + 0.15; */
|
|
||||||
// printf("GAMMA %d %f %f\n",count+1,GAMMA,CVIR_FAC);
|
|
||||||
|
|
||||||
chi2=chi2_wp_wrapper(a);
|
|
||||||
if(MCMC>2 && chi2<1.0E7)chi2+=chi2_zspace(a);
|
|
||||||
|
|
||||||
tprev = t0;
|
|
||||||
t0 = second();
|
|
||||||
if(!ThisTask) {
|
|
||||||
printf("TRY %d ",++count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%.4e ",a[i]);
|
|
||||||
printf("%e %.2f\n",chi2,timediff(tprev,t0));fflush(stdout);
|
|
||||||
}
|
|
||||||
|
|
||||||
pcheck[pcnt]=0;
|
|
||||||
if(!(chi2<chi2prev || drand48() <= exp(-(chi2-chi2prev)/2)))
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
a[i] = aprev[i];
|
|
||||||
chi2 = chi2prev;
|
|
||||||
*/
|
|
||||||
if(USE_IWEIGHT)
|
|
||||||
iweight[niter+1]++;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
pcheck[pcnt]=1;
|
|
||||||
|
|
||||||
// if(NSTEP<NSTEP_MAX)NSTEP++;
|
|
||||||
niter++;
|
|
||||||
if(!convergence)NSTEP = niter;
|
|
||||||
iweight[niter]++;
|
|
||||||
|
|
||||||
if(niter%NSTEP_MAX==0 && !convergence && niter>NSTEP_MAX)
|
|
||||||
{
|
|
||||||
convergence = 1;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x1=fabs(eval[i]-eval_prev[i])/eval_prev[i];
|
|
||||||
if(x1>0.01)convergence = 0;
|
|
||||||
printf("CONVERGENCE CHECK %d %d %e %e %e\n",niter/NSTEP_MAX,i,x1,eval[i],eval_prev[i]);
|
|
||||||
}
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
eval_prev[i] = eval[i];
|
|
||||||
convergence = 0;
|
|
||||||
|
|
||||||
if(convergence)
|
|
||||||
printf("CONVERGENCE ACCOMPLISHED %d %d \n",niter,count);
|
|
||||||
}
|
|
||||||
if(niter==NSTEP_MAX)
|
|
||||||
{
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
eval_prev[i] = eval[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
chain[niter][i]=a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
avg1[i] += a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
aprev[i] = a[i];
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
cov1[i][j] += a[i]*a[j];
|
|
||||||
chi2prev=chi2;
|
|
||||||
|
|
||||||
if(!ThisTask) {
|
|
||||||
printf("ACCEPT %d %d ",niter,count);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
printf("%e ",a[i]);
|
|
||||||
printf("%e\n",chi2);fflush(stdout);
|
|
||||||
|
|
||||||
printf("HSTATS %d %e %e %e %e\n",niter,HOD.M_min,number_weighted_halo_mass(),
|
|
||||||
number_weighted_central_mass(),
|
|
||||||
qromo(func_satellite_density,log(HOD.M_low),log(HOD.M_max),midpnt)/GALAXY_DENSITY);
|
|
||||||
|
|
||||||
fsat = qromo(func_satfrac,log(HOD.M_low),log(HOD.M_max),midpnt)/GALAXY_DENSITY;
|
|
||||||
printf("FSAT %d %e %e %e %e\n",niter,fsat,HOD.M_min,HOD.sigma_logM,CVIR_FAC);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
double chi2_wp_wrapper(double *a)
|
|
||||||
{
|
|
||||||
static int flag=1;
|
|
||||||
static double *b;
|
|
||||||
int i,j;
|
|
||||||
|
|
||||||
if(flag)
|
|
||||||
{
|
|
||||||
b=dvector(1,100);
|
|
||||||
flag=0;
|
|
||||||
}
|
|
||||||
|
|
||||||
for(j=0,i=1;i<=N_HOD_PARAMS;++i) {
|
|
||||||
if(HOD.free[i] && i!=5) {
|
|
||||||
if(a[++j]<=0) { printf("NEG %d %d %e\n",i,j,a[j]); return(1.0E7); } }
|
|
||||||
if(HOD.free[i] && i==5) {
|
|
||||||
++j; }
|
|
||||||
}
|
|
||||||
|
|
||||||
i=0;j=0;
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M_min */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M1 */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=a[j];} /* alpha */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M_cut */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* sigma_logM */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=a[j];} /* cvir_fac */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* MaxCen */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=pow(10.0,a[j]);} /* M_sat_break */
|
|
||||||
if(HOD.free[++i]){j++;b[j]=a[j];} /* alpha1 */
|
|
||||||
|
|
||||||
return(chi2_wp(b));
|
|
||||||
}
|
|
||||||
|
|
||||||
double mcmc_initialize(double *a, double **cov1, double *avg1, double *start_dev)
|
|
||||||
{
|
|
||||||
int i,j=0;
|
|
||||||
double x1,x2;
|
|
||||||
long IDUM = -556;
|
|
||||||
|
|
||||||
i=0;j=0;
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M_min);start_dev[j]=0.001; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M1);start_dev[j]=0.001; } //.0005
|
|
||||||
if(HOD.free[++i]){ a[++j]=HOD.alpha;start_dev[j]=0.03; } //.005
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M_cut);start_dev[j]=0.01; } //.001
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.sigma_logM);start_dev[j]=0.01; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=CVIR_FAC;start_dev[j]=0.02; }
|
|
||||||
if(HOD.pdfc==7) {
|
|
||||||
if(HOD.free[++i])a[++j]=log10(HOD.M_cen_max); start_dev[j]=0.001; }
|
|
||||||
else {
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.MaxCen; start_dev[j]=0.02; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=log10(HOD.M_sat_break);start_dev[j]=0.001; }
|
|
||||||
if(HOD.free[++i]){ a[++j]=HOD.alpha1;start_dev[j]=0.02; }
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
if(HOD.free[++i])a[++j]=OMEGA_M;
|
|
||||||
if(HOD.free[++i])a[++j]=SIGMA_8;
|
|
||||||
if(HOD.free[++i])a[++j]=VBIAS;
|
|
||||||
if(HOD.free[++i])a[++j]=VBIAS_C;
|
|
||||||
if(HOD.free[++i])a[++j]=GAMMA;
|
|
||||||
if(HOD.free[++i])a[++j]=SPECTRAL_INDX;
|
|
||||||
}
|
|
||||||
printf("INITIAL VALUES: ");
|
|
||||||
for(i=1;i<=wp.ncf;++i)printf("%e ",a[i]);
|
|
||||||
printf("\n");
|
|
||||||
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
{
|
|
||||||
avg1[i]=a[i];
|
|
||||||
for(j=1;j<=wp.ncf;++j)
|
|
||||||
cov1[i][j]=a[i]*a[j];
|
|
||||||
}
|
|
||||||
|
|
||||||
if(MCMC>1)
|
|
||||||
{
|
|
||||||
RESET_COSMOLOGY++;
|
|
||||||
j=0;
|
|
||||||
for(i=1;i<=N_HOD_PARAMS;++i)if(HOD.free[i])j++;
|
|
||||||
i=N_HOD_PARAMS;
|
|
||||||
if(HOD.free[++i]){ OMEGA_M = a[++j]; start_dev[j] = 0.01; }
|
|
||||||
if(HOD.free[++i]){ SIGMA_8 = a[++j]; start_dev[j] = 0.01; }
|
|
||||||
if(HOD.free[++i]){ VBIAS = a[++j]; start_dev[j] = 0.01; }
|
|
||||||
if(HOD.free[++i]){ VBIAS_C = a[++j]; start_dev[j] = 0.02; }
|
|
||||||
if(HOD.free[++i]){ GAMMA = a[++j]; start_dev[j] = 0.015; }
|
|
||||||
if(HOD.free[++i]){ SPECTRAL_INDX = a[++j]; start_dev[j] = 0.02; }
|
|
||||||
}
|
|
||||||
|
|
||||||
x1=chi2_wp_wrapper(a);
|
|
||||||
|
|
||||||
if(MCMC>2)
|
|
||||||
x2=chi2_zspace(a);
|
|
||||||
else
|
|
||||||
x2=0;
|
|
||||||
|
|
||||||
if(!ThisTask) {
|
|
||||||
printf("TRY 0 ");
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
printf("%.4e ",a[i]);
|
|
||||||
printf("%e\n",x1+x2);fflush(stdout);
|
|
||||||
printf("INITIAL CHI2: %e %e\n",x1,x2);
|
|
||||||
fflush(stdout);
|
|
||||||
}
|
|
||||||
return(x1+x2);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This is to look at a chain and get the variances in each parameter.
|
|
||||||
*/
|
|
||||||
void mcmc_restart2(double *start_dev, int np)
|
|
||||||
{
|
|
||||||
int n,i,j,k,i1,i2;
|
|
||||||
FILE *fp;
|
|
||||||
char aa[100];
|
|
||||||
float xbar[10],xsqr[10],x;
|
|
||||||
|
|
||||||
fp = openfile(RESTART_FILE);
|
|
||||||
n = filesize(fp);
|
|
||||||
|
|
||||||
for(i=0;i<np;++i)
|
|
||||||
xbar[i] = xsqr[i] = 0;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
fscanf(fp,"%s %d %d",aa,&i1,&i2);
|
|
||||||
for(j=0;j<np;++j)
|
|
||||||
{
|
|
||||||
fscanf(fp,"%f",&x);
|
|
||||||
xbar[j] += x;
|
|
||||||
xsqr[j] += x*x;
|
|
||||||
}
|
|
||||||
fgets(aa,100,fp);
|
|
||||||
}
|
|
||||||
for(i=0;i<np;++i)
|
|
||||||
{
|
|
||||||
xbar[i]/=n;
|
|
||||||
xsqr[i]/=n;
|
|
||||||
xsqr[i] = sqrt(xsqr[i] - xbar[i]*xbar[i]);
|
|
||||||
start_dev[i+1] = xsqr[i];
|
|
||||||
if(!ThisTask)
|
|
||||||
fprintf(stdout,"RESTART_DEV %f %f\n",xbar[i],xsqr[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int mcmc_restart3(double **chain, int n, double *chi2_prev, int *iweight)
|
|
||||||
{
|
|
||||||
FILE *fp;
|
|
||||||
char aa[100];
|
|
||||||
int niter,i,j,i1,i2,iprev;
|
|
||||||
double x,*a,chi2;
|
|
||||||
|
|
||||||
fp = openfile(RESTART_FILE);
|
|
||||||
niter = filesize(fp);
|
|
||||||
|
|
||||||
a = dvector(1,n);
|
|
||||||
|
|
||||||
fscanf(fp,"%s %d %d",aa,&i1,&i2);
|
|
||||||
rewind(fp);
|
|
||||||
iprev = i2 - 1;
|
|
||||||
for(i=1;i<=niter;++i)
|
|
||||||
{
|
|
||||||
fscanf(fp,"%s %d %d",aa,&i1,&i2);
|
|
||||||
if(USE_IWEIGHT)
|
|
||||||
iweight[i] = i2 - iprev;
|
|
||||||
else
|
|
||||||
iweight[i] = 1;
|
|
||||||
iprev = i2;
|
|
||||||
for(j=1;j<=n;++j)
|
|
||||||
fscanf(fp,"%lf",&chain[i][j]);
|
|
||||||
fscanf(fp,"%lf",&x);
|
|
||||||
}
|
|
||||||
*chi2_prev = 20000*x; // set it to automatically take the first element
|
|
||||||
//*chi2_prev = x;
|
|
||||||
|
|
||||||
/* Normalize all the masses by OMEGA_M
|
|
||||||
*/
|
|
||||||
for(i=1;i<=niter;++i)
|
|
||||||
{
|
|
||||||
chain[i][1] -= log10(chain[i][4]);
|
|
||||||
chain[i][3] -= log10(chain[i][4]);
|
|
||||||
}
|
|
||||||
return niter;
|
|
||||||
}
|
|
|
@ -1,39 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* This function calculates M_star (non-linear mass scale) for the given
|
|
||||||
* cosmological paramters.
|
|
||||||
*/
|
|
||||||
|
|
||||||
double sigma_Mmdelta_c(double lnM);
|
|
||||||
double pnorm1;
|
|
||||||
|
|
||||||
double mstar()
|
|
||||||
{
|
|
||||||
double sig,lnMmin,lnMmax,M_star;
|
|
||||||
|
|
||||||
sig=sigmac(8.0);
|
|
||||||
pnorm1 = SIGMA_8/sig;
|
|
||||||
|
|
||||||
lnMmin=log(1e7);
|
|
||||||
lnMmax=log(1e18);
|
|
||||||
M_star=zbrent(sigma_Mmdelta_c,lnMmin,lnMmax,1e-5);
|
|
||||||
M_star=exp(M_star);
|
|
||||||
if(!ThisTask)
|
|
||||||
fprintf(stderr,"M_star = %e h^{-1}M_sol\n",M_star);
|
|
||||||
return(M_star);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*** solve for M_* ***/
|
|
||||||
double sigma_Mmdelta_c(double lnM)
|
|
||||||
{
|
|
||||||
double sig,M,rm;
|
|
||||||
|
|
||||||
M=exp(lnM);
|
|
||||||
rm=pow(3.0*M/(4.0*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
sig=pnorm1*sigmac(rm);
|
|
||||||
|
|
||||||
return sig-DELTA_CRIT;
|
|
||||||
}
|
|
|
@ -1,204 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* This is my implementation of the Halo Model fitting function
|
|
||||||
* described in Appendix C of Smith, Peacock, et al. 2003 MNRAS 341, 1311
|
|
||||||
*
|
|
||||||
* Comparison to Smith et al. program halofit.f output is successful.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Internal functions
|
|
||||||
*/
|
|
||||||
double func_nl(double r);
|
|
||||||
void tabulate_pk_nl(double *kk, double *pknl, int nk);
|
|
||||||
|
|
||||||
/* This returns the linear power
|
|
||||||
* Delta = 4pi*k^3 P(k)/(2pi)^3
|
|
||||||
*/
|
|
||||||
double linear_power_spectrum(double xk)
|
|
||||||
{
|
|
||||||
static double *kk,*pknl,*y2,pnorm=-1,ahi,bhi;
|
|
||||||
static int flag=1,nk=1000,prev_cosmology=0;
|
|
||||||
double a,psp,x1[4],y1[4];
|
|
||||||
int i;
|
|
||||||
|
|
||||||
if(pnorm<0 || prev_cosmology!=RESET_COSMOLOGY)
|
|
||||||
{
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
pnorm*=pnorm;
|
|
||||||
prev_cosmology=RESET_COSMOLOGY;
|
|
||||||
}
|
|
||||||
if(ITRANS>0)
|
|
||||||
psp=pow(xk,SPECTRAL_INDX)*pow(transfnc(xk),2.);
|
|
||||||
else
|
|
||||||
psp=pow(xk,SPECTRAL_INDX);
|
|
||||||
psp=psp*pnorm*xk*xk*xk/(2*PI*PI);
|
|
||||||
return(psp);
|
|
||||||
}
|
|
||||||
|
|
||||||
double nonlinear_power_spectrum(double xk)
|
|
||||||
{
|
|
||||||
static double *kk,*pknl,*y2,pnorm=-1,ahi,bhi;
|
|
||||||
static int flag=1,nk=1000,prev_cosmology=0;
|
|
||||||
double a,psp,x1[4],y1[4],xklog;
|
|
||||||
int i;
|
|
||||||
|
|
||||||
if(flag || RESET_COSMOLOGY!=prev_cosmology)
|
|
||||||
{
|
|
||||||
prev_cosmology=RESET_COSMOLOGY;
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
flag=0;
|
|
||||||
kk=dvector(1,nk);
|
|
||||||
pknl=dvector(1,nk);
|
|
||||||
y2=dvector(1,nk);
|
|
||||||
tabulate_pk_nl(kk,pknl,nk);
|
|
||||||
spline(kk,pknl,nk,1.0E+30,1.0E+30,y2);
|
|
||||||
|
|
||||||
/* This takes the last four points in the power spectrum at high k
|
|
||||||
* and fits a power law to them for extrapolation.
|
|
||||||
*/
|
|
||||||
for(i=0;i<4;++i)
|
|
||||||
{
|
|
||||||
x1[i]=(kk[nk-3+i]);
|
|
||||||
y1[i]=(pknl[nk-3+i]);
|
|
||||||
}
|
|
||||||
least_squares(x1,y1,4,&ahi,&bhi);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
xklog=log(xk);
|
|
||||||
|
|
||||||
/* If xk is less than the smallest k value tabulates, return linear power.
|
|
||||||
*/
|
|
||||||
if(xklog<kk[1])
|
|
||||||
return(linear_power_spectrum(xk));
|
|
||||||
|
|
||||||
/* If xk larger than highest k, return extrapolation.
|
|
||||||
*/
|
|
||||||
if(xklog>kk[nk])
|
|
||||||
return((exp((ahi+bhi*xklog))));
|
|
||||||
|
|
||||||
splint(kk,pknl,y2,nk,xklog,&a);
|
|
||||||
return(exp(a));
|
|
||||||
|
|
||||||
}
|
|
||||||
void tabulate_pk_nl(double *kk, double *pknl, int nk)
|
|
||||||
{
|
|
||||||
double r_nl,pnorm,DeltaQ,DeltaLin,DeltaH,psp,neff,s1,s2,n1,n2,ncurve,
|
|
||||||
lnk_lo,lnk_hi,dlnk,xk1,y,xk,fy;
|
|
||||||
double an,bn,cn,f1b,f2b,f3b,alpha,beta,gamma,nu,mu;
|
|
||||||
int i,j,n=10000;
|
|
||||||
|
|
||||||
/* First normalize the linear power spectrum.
|
|
||||||
*/
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
|
|
||||||
/* Calculate the non-linear scale.
|
|
||||||
*/
|
|
||||||
r_nl = exp(zbrent(func_nl,log(0.01),log(10.0),1.0E-4));
|
|
||||||
if(OUTPUT)
|
|
||||||
fprintf(stdout,"R_NL= %f\n",r_nl);
|
|
||||||
|
|
||||||
/* Calculate the effective spectral index at the non-linear scale.
|
|
||||||
*/
|
|
||||||
s1=pnorm*sigmac(-r_nl*0.999);
|
|
||||||
s2=pnorm*sigmac(-r_nl*1.001);
|
|
||||||
neff=-(3+2*(s2-s1)/0.002);
|
|
||||||
if(OUTPUT)
|
|
||||||
fprintf(stderr,"neff= %f\n",neff);
|
|
||||||
|
|
||||||
/* Spectral curvature.
|
|
||||||
*/
|
|
||||||
lnk_hi=10.0;
|
|
||||||
lnk_lo=-10.0;
|
|
||||||
dlnk=(lnk_hi-lnk_lo)/n;
|
|
||||||
s1=0;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
xk1=exp(lnk_lo+(i-0.5)*dlnk);
|
|
||||||
y=xk1*r_nl;
|
|
||||||
DeltaLin=linear_power_spectrum(xk1);
|
|
||||||
s1+=DeltaLin*y*y*(1-y*y)*exp(-y*y)*dlnk;
|
|
||||||
}
|
|
||||||
ncurve=(3+neff)*(3+neff)+4*s1;
|
|
||||||
if(OUTPUT)
|
|
||||||
fprintf(stderr,"ncurve= %f\n",ncurve);
|
|
||||||
|
|
||||||
/* Coefficients of the model.
|
|
||||||
*/
|
|
||||||
an=pow(10.0,1.4861 + 1.8369*neff + 1.6762*neff*neff + 0.7940*neff*neff*neff +
|
|
||||||
0.1670*pow(neff,4.0) - 0.6202*ncurve);
|
|
||||||
bn=pow(10.0,0.9463 + 0.9466*neff + 0.3084*neff*neff - 0.9400*ncurve);
|
|
||||||
|
|
||||||
cn= pow(10.0,-0.2807 + 0.6669*neff + 0.3214*neff*neff - 0.0793*ncurve);
|
|
||||||
|
|
||||||
gamma = 0.8649 + 0.2989*neff + 0.1631*ncurve;
|
|
||||||
alpha = 1.3884 + 0.3700*neff - 0.1452*neff*neff;
|
|
||||||
beta = 0.8291 + 0.9854*neff + 0.3401*neff*neff;
|
|
||||||
mu = pow(10.0,-3.5442 + 0.1908*neff);
|
|
||||||
nu = pow(10.0, 0.9589 + 1.2857*neff);
|
|
||||||
|
|
||||||
/* Testing the parameter dependence.
|
|
||||||
* TESTING TESTING
|
|
||||||
*/
|
|
||||||
/*
|
|
||||||
alpha *= 0.3;
|
|
||||||
beta *= 0.3;
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Omega-dependent functions (FLAT LAMBDA COSMOLOGY)
|
|
||||||
*/
|
|
||||||
f1b = pow(OMEGA_M,-0.0307);
|
|
||||||
f2b = pow(OMEGA_M,-0.0585);
|
|
||||||
f3b = pow(OMEGA_M,+0.0743);
|
|
||||||
|
|
||||||
|
|
||||||
/* Tabulate the power spectrum
|
|
||||||
*/
|
|
||||||
lnk_lo=log(0.001);
|
|
||||||
lnk_hi=log(1000.0);
|
|
||||||
dlnk=(lnk_hi-lnk_lo)/(nk-1);
|
|
||||||
|
|
||||||
for(i=1;i<=nk;++i)
|
|
||||||
{
|
|
||||||
xk=exp(lnk_lo+(i-1)*dlnk);
|
|
||||||
y=xk*r_nl;
|
|
||||||
fy=y/4.0 + y*y/8.0;
|
|
||||||
|
|
||||||
/* TEST */
|
|
||||||
/* fy*=1.2; */
|
|
||||||
|
|
||||||
DeltaLin=linear_power_spectrum(xk);
|
|
||||||
|
|
||||||
DeltaQ = DeltaLin*pow(1+DeltaLin,beta)/(1+alpha*DeltaLin)*exp(-fy);
|
|
||||||
|
|
||||||
DeltaH = an*pow(y,3*f1b)/(1+bn*pow(y,f2b)+pow(cn*f3b*y,3-gamma));
|
|
||||||
|
|
||||||
DeltaH*= 1.0/(1+mu/y+nu/(y*y));
|
|
||||||
|
|
||||||
kk[i]=log(xk);
|
|
||||||
pknl[i]=log(DeltaQ + DeltaH);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This is a function to find the non-linear scale. Similar to M_star,
|
|
||||||
* but here we're using a Guassian smoothing window rather than top hat.
|
|
||||||
* (And we're finding the scale at which the variance = 1, not 1.686).
|
|
||||||
*/
|
|
||||||
double func_nl(double r)
|
|
||||||
{
|
|
||||||
static int prev_cosmology=0;
|
|
||||||
double sig;
|
|
||||||
static double pnorm=-1;
|
|
||||||
|
|
||||||
if(pnorm<0 || RESET_COSMOLOGY!=prev_cosmology)
|
|
||||||
pnorm=SIGMA_8/sigmac(8.0);
|
|
||||||
prev_cosmology=RESET_COSMOLOGY;
|
|
||||||
|
|
||||||
r=exp(r);
|
|
||||||
sig=pnorm*sigmac(-r);
|
|
||||||
return sig-1.0;
|
|
||||||
}
|
|
|
@ -1,231 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* These routines control the real-space one-halo term.
|
|
||||||
* For specifics, see:
|
|
||||||
*
|
|
||||||
* Berlind, A.\ A., \& Weinberg, D.\ H.\ 2002, \apj, 575, 587
|
|
||||||
* Zheng, Z. 2003, \apj, 610, 61
|
|
||||||
* Tinker, Weinberg, Zheng, Zehavi 2005 Apj 631 (App B)
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Local functions.
|
|
||||||
*/
|
|
||||||
void calc_real_space_one_halo(double *r, double *xi, int n);
|
|
||||||
double func1(double m);
|
|
||||||
double func1cs(double m);
|
|
||||||
double func1satsat(double m);
|
|
||||||
double func1_xcorr(double m);
|
|
||||||
double one_halo_ss(double r);
|
|
||||||
double one_halo_cs(double r);
|
|
||||||
|
|
||||||
double *xi_cs_g2,*xi_ss_g2,*xi_rad_g2;
|
|
||||||
|
|
||||||
/* These are the local globals to use during the qromo integration
|
|
||||||
*/
|
|
||||||
double r_g2;
|
|
||||||
|
|
||||||
|
|
||||||
/* This function tabulates the one-halo real-space term for spline interpolation.
|
|
||||||
* If the requested radius is out-of-bounds of the tabulated function, a value of
|
|
||||||
* zero is returned.
|
|
||||||
*/
|
|
||||||
double one_halo_real_space(double r)
|
|
||||||
{
|
|
||||||
static int flag=0;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int i,n=100;
|
|
||||||
double a;
|
|
||||||
|
|
||||||
if(!HOD.pdfs)return(0);
|
|
||||||
|
|
||||||
if(!flag || RESET_FLAG_1H)
|
|
||||||
{
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
RESET_FLAG_1H=0;
|
|
||||||
calc_real_space_one_halo(x,y,n);
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
}
|
|
||||||
if(r>x[n])return(0);
|
|
||||||
if(r<x[1])return(0);
|
|
||||||
splint(x,y,y2,n,r,&a);
|
|
||||||
return(a);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Here we calculate the one-halo real space term
|
|
||||||
* logarithmically spaced in r. The minimum value of r = 0.01 Mpc/h. The maximum
|
|
||||||
* value of r is set to be approximately twice the virial radius of M_max.
|
|
||||||
*
|
|
||||||
* Only halos with virial radii greater than 1/2 the separation
|
|
||||||
* contribute to the 1-halo term.
|
|
||||||
* Terminate integrations when r>2*R_vir(M_max).
|
|
||||||
*/
|
|
||||||
void calc_real_space_one_halo(double *r, double *xi, int n)
|
|
||||||
{
|
|
||||||
static int ncnt=0;
|
|
||||||
double fac,s1,rhi=1,rlo=-2,dr,mlo,x1,x2;
|
|
||||||
int i,j;
|
|
||||||
FILE *fp;
|
|
||||||
char fname[100];
|
|
||||||
|
|
||||||
ncnt++;
|
|
||||||
rlo=log(0.01);
|
|
||||||
rhi=log(1.9*pow(3*HOD.M_max/(4*PI*DELTA_HALO*RHO_CRIT*OMEGA_M),1.0/3.0));
|
|
||||||
dr=(rhi-rlo)/(n-1);
|
|
||||||
|
|
||||||
if(OUTPUT>1)
|
|
||||||
printf("calc_one_halo> starting...\n");
|
|
||||||
if(!XCORR)
|
|
||||||
GALAXY_DENSITY2 = GALAXY_DENSITY;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
r_g2=r[i]=exp((i-1)*dr + rlo);
|
|
||||||
fac=1.0/(2*PI*r_g2*r_g2*GALAXY_DENSITY*GALAXY_DENSITY2);
|
|
||||||
|
|
||||||
mlo = 4./3.*PI*RHO_CRIT*DELTA_HALO*OMEGA_M*pow(r[i]*.5,3.0);
|
|
||||||
if(mlo<HOD.M_low)
|
|
||||||
mlo = HOD.M_low;
|
|
||||||
|
|
||||||
if(XCORR)
|
|
||||||
s1=fac*qromo(func1_xcorr,log(mlo),log(HOD.M_max),midpnt)*0.5;
|
|
||||||
else
|
|
||||||
s1=fac*qromo(func1,log(mlo),log(HOD.M_max),midpnt);
|
|
||||||
|
|
||||||
xi[i]=s1;
|
|
||||||
if(OUTPUT>1)
|
|
||||||
printf("calc_one_halo> %f %e %e\n",r[i],s1,fac);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This is the function passed to qromo in the above routine.
|
|
||||||
* It is the number density of
|
|
||||||
* galaxy pairs in halos of mass m at separation r_g2.
|
|
||||||
* See Equation (11) from Berlind & Weinberg.
|
|
||||||
*/
|
|
||||||
double func1(double m)
|
|
||||||
{
|
|
||||||
double N,n,fac2,rvir,f_ss,f_cs,cvir,x,rfof,ncen,nsat;
|
|
||||||
|
|
||||||
m=exp(m);
|
|
||||||
cvir=halo_concentration(m)*CVIR_FAC;
|
|
||||||
|
|
||||||
n=dndM_interp(m);
|
|
||||||
|
|
||||||
nsat=N_sat(m);
|
|
||||||
ncen=N_cen(m);
|
|
||||||
|
|
||||||
rvir=2*pow(3.0*m/(4*DELTA_HALO*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
|
|
||||||
/* Break up the contribution of pairs into
|
|
||||||
* central-satellite (cs) and satellite-satellite (ss) pairs.
|
|
||||||
*/
|
|
||||||
f_ss=dFdx_ss(r_g2/rvir,cvir)*moment_ss(m)*0.5;
|
|
||||||
f_cs=dFdx_cs(r_g2/rvir,cvir)*nsat*ncen;
|
|
||||||
x=n*(f_ss+f_cs)/rvir*m;
|
|
||||||
return(x);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
double func1satsat(double m)
|
|
||||||
{
|
|
||||||
double N,n,fac2,rvir,f_ss,f_cs,cvir,x,rfof,ncen,nsat;
|
|
||||||
|
|
||||||
m=exp(m);
|
|
||||||
cvir=halo_concentration(m)*CVIR_FAC;
|
|
||||||
|
|
||||||
n=dndM_interp(m);
|
|
||||||
|
|
||||||
nsat=N_sat(m);
|
|
||||||
ncen=N_cen(m);
|
|
||||||
|
|
||||||
rvir=2*pow(3.0*m/(4*DELTA_HALO*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
|
|
||||||
/* Break up the contribution of pairs into
|
|
||||||
* central-satellite (cs) and satellite-satellite (ss) pairs.
|
|
||||||
*/
|
|
||||||
f_ss=dFdx_ss(r_g2/rvir,cvir)*moment_ss(m)*0.5;
|
|
||||||
x=n*(f_ss)/rvir*m;
|
|
||||||
return(x);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
double func1cs(double m)
|
|
||||||
{
|
|
||||||
double N,n,fac2,rvir,f_ss,f_cs,cvir,x,rfof,ncen,nsat;
|
|
||||||
|
|
||||||
m=exp(m);
|
|
||||||
cvir=halo_concentration(m)*CVIR_FAC;
|
|
||||||
|
|
||||||
n=dndM_interp(m);
|
|
||||||
|
|
||||||
nsat=N_sat(m);
|
|
||||||
ncen=N_cen(m);
|
|
||||||
|
|
||||||
rvir=2*pow(3.0*m/(4*DELTA_HALO*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
|
|
||||||
/* Break up the contribution of pairs into
|
|
||||||
* central-satellite (cs) and satellite-satellite (ss) pairs.
|
|
||||||
*/
|
|
||||||
f_cs=dFdx_cs(r_g2/rvir,cvir)*nsat*ncen;
|
|
||||||
x=n*(f_cs)/rvir*m;
|
|
||||||
|
|
||||||
return(x);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Same as above, only now we're calculating the number of pairs
|
|
||||||
* in the cross-correlation.
|
|
||||||
*
|
|
||||||
* NB! -- We're assuming that the satellite galaxy profiles
|
|
||||||
* of both HODs are the same.
|
|
||||||
*/
|
|
||||||
double func1_xcorr(double m)
|
|
||||||
{
|
|
||||||
double N,n,fac2,rvir,f_ss=0,f_cs=0,cvir,x,rfof,ncen1,nsat1,ncen2,nsat2;
|
|
||||||
|
|
||||||
m=exp(m);
|
|
||||||
cvir=halo_concentration(m)*CVIR_FAC;
|
|
||||||
n=dndM_interp(m);
|
|
||||||
|
|
||||||
nsat1=N_sat(m);
|
|
||||||
ncen1=N_cen(m);
|
|
||||||
|
|
||||||
nsat2=N_sat2(m);
|
|
||||||
ncen2=N_cen2(m);
|
|
||||||
|
|
||||||
rvir=2*pow(3.0*m/(4*DELTA_HALO*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
|
|
||||||
/* Break up the contribution of pairs into
|
|
||||||
* central-satellite (cs) and satellite-satellite (ss) pairs.
|
|
||||||
* But for x-corr, we have c1-s2, c2-s1, s1-s2.
|
|
||||||
*/
|
|
||||||
f_ss=dFdx_ss(r_g2/rvir,cvir)*nsat1*nsat2;
|
|
||||||
f_cs=dFdx_cs(r_g2/rvir,cvir)*(nsat1*ncen2 + nsat2*ncen1);
|
|
||||||
x=n*(f_ss+f_cs)/rvir*m;
|
|
||||||
|
|
||||||
return(x);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
/* The public version doesn't currently support cross-correlations.
|
|
||||||
*/
|
|
||||||
double N_sat2(double m)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
double N_cen2(double m)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
|
@ -1,175 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
double m_g3,r_g3,*x_g3,*y_g3,*z_g3;
|
|
||||||
double n_g3;
|
|
||||||
int flag_g3=0;
|
|
||||||
|
|
||||||
double func_ng(double m);
|
|
||||||
double func_ng2(double m);
|
|
||||||
|
|
||||||
/* The restr
|
|
||||||
*/
|
|
||||||
|
|
||||||
double restricted_number_density(double r)
|
|
||||||
{
|
|
||||||
static int flag=1;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int i,n=50,j;
|
|
||||||
double mlimit,dlogm,logm,mmin,sum=0,t0,t1,s1,s2,s3,m,r1,r2,ng2,rlim,rmin,rmax;
|
|
||||||
|
|
||||||
if(flag)
|
|
||||||
{
|
|
||||||
n_g3 = n;
|
|
||||||
x_g3=dvector(1,n);
|
|
||||||
y_g3=dvector(1,n);
|
|
||||||
z_g3=dvector(1,n);
|
|
||||||
flag=0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Reset the static variables in this function.
|
|
||||||
*/
|
|
||||||
func_ng2(-1);
|
|
||||||
|
|
||||||
r_g3=r;
|
|
||||||
ng2=GALAXY_DENSITY*GALAXY_DENSITY;
|
|
||||||
|
|
||||||
/* Calculate the maximum allowable halo mass, which had
|
|
||||||
* rvir = r_g3 - rvir(M_low).
|
|
||||||
*/
|
|
||||||
r1=pow(3.*HOD.M_low/(4.*PI*DELTA_HALO*RHO_CRIT*OMEGA_M),1.0/3.0);
|
|
||||||
rlim = r_g3 - r1;
|
|
||||||
mlimit=log(4./3.*DELTA_HALO*RHO_CRIT*PI*rlim*rlim*rlim*OMEGA_M);
|
|
||||||
if(mlimit>log(HOD.M_max))mlimit=log(HOD.M_max);
|
|
||||||
mmin=log(HOD.M_low);
|
|
||||||
|
|
||||||
if(HOD.color==2)
|
|
||||||
{
|
|
||||||
dlogm=(mlimit-mmin)/(n-1);
|
|
||||||
m = mmin;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
if(N_avg(exp(m))>0)break;
|
|
||||||
m += dlogm;
|
|
||||||
}
|
|
||||||
mmin = m;
|
|
||||||
r1=pow(3.*exp(mmin)/(4.*PI*DELTA_HALO*RHO_CRIT*OMEGA_M),1.0/3.0);
|
|
||||||
rlim = r_g3 - r1;
|
|
||||||
mlimit=log(4./3.*DELTA_HALO*RHO_CRIT*PI*rlim*rlim*rlim*OMEGA_M);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(EXCLUSION==2) {
|
|
||||||
dlogm=(mlimit-mmin)/(n-1);
|
|
||||||
x_g3[1] = mmin;
|
|
||||||
y_g3[1] = qromo(func_galaxy_density,mmin,mmin+dlogm,midpnt);
|
|
||||||
for(i=2;i<=n;++i)
|
|
||||||
{
|
|
||||||
x_g3[i] = i*dlogm+mmin;
|
|
||||||
y_g3[i] = y_g3[i-1] + qromo(func_galaxy_density,(i-1)*dlogm+mmin,mmin+i*dlogm,midpnt);
|
|
||||||
}
|
|
||||||
spline(x_g3,y_g3,n,1.0E+30,1.0E+30,z_g3);
|
|
||||||
s1 = qromo(func_ng2,mmin,mlimit,midpnt);
|
|
||||||
return(sqrt(s1));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Calculate the double integral at specified masses.
|
|
||||||
*/
|
|
||||||
dlogm=(mlimit-mmin)/(n-1);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
logm=(i-0.5)*dlogm+mmin;
|
|
||||||
m_g3=exp(logm);
|
|
||||||
r2 = pow(3*m_g3/(4*PI*DELTA_HALO*RHO_CRIT*OMEGA_M),1.0/3.0);
|
|
||||||
if(EXCLUSION==3) {
|
|
||||||
if(ellipsoidal_exclusion_probability(r1/r2,r_g3/(r1+r2))==0)break; }
|
|
||||||
else {
|
|
||||||
if(r1+r2>r_g3)break; }
|
|
||||||
s1=qtrap(func_ng,mmin,mlimit,1.0E-4);
|
|
||||||
sum+=s1*m_g3*dlogm;
|
|
||||||
if(s1==0)break;
|
|
||||||
if(sum>=ng2)break;
|
|
||||||
}
|
|
||||||
return sqrt(sum);
|
|
||||||
}
|
|
||||||
|
|
||||||
double func_ng2(double m)
|
|
||||||
{
|
|
||||||
static double fac2=-1,fac1=-1;
|
|
||||||
double s1,rv1,n,N,m1,mx;
|
|
||||||
|
|
||||||
if(m<0)
|
|
||||||
{
|
|
||||||
fac1=fac2=-1;
|
|
||||||
return(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
m1=exp(m);
|
|
||||||
if(fac2<0)
|
|
||||||
fac2=pow(3.0/(4.*PI*DELTA_HALO*RHO_CRIT*OMEGA_M),1.0/3.0);
|
|
||||||
if(fac1<0)
|
|
||||||
fac1=4./3.*PI*RHO_CRIT*DELTA_HALO*OMEGA_M;
|
|
||||||
|
|
||||||
rv1 = r_g3 - pow(m1,1.0/3.0)*fac2;
|
|
||||||
rv1 = rv1;
|
|
||||||
mx = fac1*rv1*rv1*rv1;
|
|
||||||
|
|
||||||
n=dndM_interp(m1);
|
|
||||||
N=N_avg(m1);
|
|
||||||
splint(x_g3,y_g3,z_g3,n_g3,log(mx),&s1);
|
|
||||||
return(n*N*s1*m1);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
double func_ng(double m)
|
|
||||||
{
|
|
||||||
static double fac2=-1;
|
|
||||||
double s1,rv1,rv2,exfac=1,n,N;
|
|
||||||
|
|
||||||
m=exp(m);
|
|
||||||
if(fac2<0)
|
|
||||||
fac2=pow(3.0/(4*DELTA_HALO*PI*RHO_CRIT*OMEGA_M),1.0/3.0);
|
|
||||||
rv1=pow(m_g3,1.0/3.0)*fac2;
|
|
||||||
rv2=pow(m,1.0/3.0)*fac2;
|
|
||||||
|
|
||||||
if(EXCLUSION==3)
|
|
||||||
{
|
|
||||||
if(0.5*(rv1+rv2)>r_g3)return(0);
|
|
||||||
if(1.5*(rv1+rv2)>r_g3)exfac=ellipsoidal_exclusion_probability(rv2/rv1,r_g3/(rv2+rv1));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if(rv1+rv2>r_g3)return(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
n=dndM_interp(m)*dndM_interp(m_g3);
|
|
||||||
N=N_avg(m)*N_avg(m_g3);
|
|
||||||
return(exfac*n*N*m);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This is the probability that two halos do not overlap, given their
|
|
||||||
* radii and separation. Of course, for spherical halos P(x) is a step function
|
|
||||||
* at x = (r1+r2)/r_sep = 1, but for ellipsoidal halos there is a chance
|
|
||||||
* that they could be closer. In detail, P(x) changes depending on the mass
|
|
||||||
* ratio of the halos, but using tabulated values does not appear to make
|
|
||||||
* significant difference in the results for xi_2h(r). The function below is
|
|
||||||
* a fit to Monte Carlo results for a halos with a distribution of axis ratios
|
|
||||||
* which is lognormal in e_b = (1-b/a) and e_c = (1-c/a) with dispersions of 0.2
|
|
||||||
* mean <b/a>=0.9 and <c/a>=0.8 (pretty reasonable values).
|
|
||||||
*/
|
|
||||||
double ellipsoidal_exclusion_probability(double rv, double r)
|
|
||||||
{
|
|
||||||
static int flag=0,nr=101,nratio=31;
|
|
||||||
static double **xprob,*rad,*ratio,rhi,rlo,mhi,mlo,dr,dm;
|
|
||||||
float x1,x2,x3;
|
|
||||||
int i,j,im,ir;
|
|
||||||
FILE *fp;
|
|
||||||
|
|
||||||
if(rv<1)rv=1.0/rv;
|
|
||||||
|
|
||||||
r=(r-0.8)/0.29;
|
|
||||||
if(r>1)return(1.0);
|
|
||||||
if(r<0)return(0.0);
|
|
||||||
return(3*r*r-2*r*r*r);
|
|
||||||
}
|
|
|
@ -1,5 +0,0 @@
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
void test(int argc, char **argv)
|
|
||||||
{
|
|
||||||
}
|
|
|
@ -1,140 +0,0 @@
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <stdlib.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
// Transfer function of Eisenstein & Hu 1998
|
|
||||||
// (Equation numbers refer to this paper)
|
|
||||||
|
|
||||||
double calc_tf_eh(double k);
|
|
||||||
|
|
||||||
double tf_eisenstein_hu(double k)
|
|
||||||
{
|
|
||||||
static int flag=0,prev_cosmo=0;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int n=1000,i;
|
|
||||||
double a,rlo=1.0E-4,rhi=1.0E+4,dlogr,klo;
|
|
||||||
double xi_linear_int();
|
|
||||||
|
|
||||||
if(!flag || RESET_COSMOLOGY!=prev_cosmo)
|
|
||||||
{
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
|
|
||||||
dlogr = (log(rhi)-log(rlo))/(n-1);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
x[i] = exp((i-1)*dlogr)*rlo;
|
|
||||||
y[i] = log(calc_tf_eh(x[i]));
|
|
||||||
//printf("TK %e %e %e %e %e\n",x[i],exp(y[i]),exp(y[i]),exp(y[i]),exp(y[i]));
|
|
||||||
x[i] = log(x[i]);
|
|
||||||
}
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
}
|
|
||||||
|
|
||||||
splint(x,y,y2,n,log(k),&a);
|
|
||||||
return(exp(a));
|
|
||||||
}
|
|
||||||
|
|
||||||
double calc_tf_eh(double k)
|
|
||||||
{
|
|
||||||
double rk,e,thet,thetsq,thetpf,b1,b2,zd,ze,rd,re,rke,s,rks,q,y,g;
|
|
||||||
double ab,a1,a2,ac,bc,f,c1,c2,tc,bb,bn,ss,tb,tk_eh;
|
|
||||||
double h,hsq,om_mhsq,om_b,om_m;
|
|
||||||
|
|
||||||
// set up cosmology
|
|
||||||
h = HUBBLE;
|
|
||||||
om_m = OMEGA_M;
|
|
||||||
om_b = OMEGA_B;
|
|
||||||
|
|
||||||
// convert k to Mpc^-1 rather than hMpc^-1
|
|
||||||
rk=k*h;
|
|
||||||
hsq=h*h;
|
|
||||||
om_mhsq=om_m*hsq;
|
|
||||||
|
|
||||||
// constants
|
|
||||||
e=exp(1.);
|
|
||||||
thet=2.728/2.7;
|
|
||||||
thetsq=thet*thet;
|
|
||||||
thetpf=thetsq*thetsq;
|
|
||||||
|
|
||||||
// Equation 4 - redshift of drag epoch
|
|
||||||
b1=0.313*pow(om_mhsq,-0.419)*(1.+0.607*pow(om_mhsq,0.674));
|
|
||||||
b2=0.238*pow(om_mhsq,0.223);
|
|
||||||
zd=1291.*(1.+b1*pow(om_b*hsq,b2))*pow(om_mhsq,0.251)
|
|
||||||
/(1.+0.659*pow(om_mhsq,0.828));
|
|
||||||
|
|
||||||
// Equation 2 - redshift of matter-radiation equality
|
|
||||||
ze=2.50e4*om_mhsq/thetpf;
|
|
||||||
|
|
||||||
// value of R=(ratio of baryon-photon momentum density) at drag epoch
|
|
||||||
rd=31500.*om_b*hsq/(thetpf*zd);
|
|
||||||
|
|
||||||
// value of R=(ratio of baryon-photon momentum density) at epoch of matter-radiation equality
|
|
||||||
re=31500.*om_b*hsq/(thetpf*ze);
|
|
||||||
|
|
||||||
// Equation 3 - scale of ptcle horizon at matter-radiation equality
|
|
||||||
rke=7.46e-2*om_mhsq/(thetsq);
|
|
||||||
|
|
||||||
// Equation 6 - sound horizon at drag epoch
|
|
||||||
s=(2./3./rke)*sqrt(6./re)*log((sqrt(1.+rd)+sqrt(rd+re))/(1.+sqrt(re)));
|
|
||||||
|
|
||||||
// Equation 7 - silk damping scale
|
|
||||||
rks=1.6*pow(om_b*hsq,0.52)*pow(om_mhsq,0.73)*(1.+pow(10.4*om_mhsq,-0.95));
|
|
||||||
|
|
||||||
// Equation 10 - define q
|
|
||||||
q=rk/13.41/rke;
|
|
||||||
|
|
||||||
// Equations 11 - CDM transfer function fits
|
|
||||||
a1=pow(46.9*om_mhsq,0.670)*(1.+pow(32.1*om_mhsq,-0.532));
|
|
||||||
a2=pow(12.0*om_mhsq,0.424)*(1.+pow(45.0*om_mhsq,-0.582));
|
|
||||||
ac=pow(a1,(-om_b/om_m))*pow(a2,pow(-(om_b/om_m),3.));
|
|
||||||
|
|
||||||
// Equations 12 - CDM transfer function fits
|
|
||||||
b1=0.944/(1.+pow(458.*om_mhsq,-0.708));
|
|
||||||
b2=pow(0.395*om_mhsq,-0.0266);
|
|
||||||
bc=1./(1.+b1*(pow(1.-om_b/om_m,b2)-1.));
|
|
||||||
|
|
||||||
// Equation 18
|
|
||||||
f=1./(1.+pow(rk*s/5.4,4.));
|
|
||||||
|
|
||||||
// Equation 20
|
|
||||||
c1=14.2 + 386./(1.+69.9*pow(q,1.08));
|
|
||||||
c2=14.2/ac + 386./(1.+69.9*pow(q,1.08));
|
|
||||||
|
|
||||||
// Equation 17 - CDM transfer function
|
|
||||||
tc=f*log(e+1.8*bc*q)/(log(e+1.8*bc*q)+c1*q*q) +
|
|
||||||
(1.-f)*log(e+1.8*bc*q)/(log(e+1.8*bc*q)+c2*q*q);
|
|
||||||
|
|
||||||
// Equation 15
|
|
||||||
y=(1.+ze)/(1.+zd);
|
|
||||||
g=y*(-6.*sqrt(1.+y)+(2.+3.*y)*log((sqrt(1.+y)+1.)/(sqrt(1.+y)-1.)));
|
|
||||||
|
|
||||||
// Equation 14
|
|
||||||
ab=g*2.07*rke*s/pow(1.+rd,0.75);
|
|
||||||
|
|
||||||
// Equation 23
|
|
||||||
bn=8.41*pow(om_mhsq,0.435);
|
|
||||||
|
|
||||||
// Equation 22
|
|
||||||
ss=s/pow(1.+pow(bn/rk/s,3.),1./3.);
|
|
||||||
|
|
||||||
// Equation 24
|
|
||||||
bb=0.5+(om_b/om_m) + (3.-2.*om_b/om_m)*sqrt(pow(17.2*om_mhsq,2.)+1.);
|
|
||||||
|
|
||||||
// Equations 19 & 21
|
|
||||||
tb=log(e+1.8*q)/(log(e+1.8*q)+c1*q*q)/(1+pow(rk*s/5.2,2.));
|
|
||||||
tb=(tb+ab*exp(-pow(rk/rks,1.4))/(1.+pow(bb/rk/s,3.)))*sin(rk*ss)/rk/ss;
|
|
||||||
|
|
||||||
// Equation 8
|
|
||||||
tk_eh=(om_b/om_m)*tb+(1.-om_b/om_m)*tc;
|
|
||||||
|
|
||||||
return tk_eh;
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,70 +0,0 @@
|
||||||
/* PROGRAM TRANSFERFUNCTION
|
|
||||||
|
|
||||||
--- transfnc(xk)
|
|
||||||
--- compute the transfer function T(k) of the power spectrum
|
|
||||||
--- T(k) defined as P(k) = k^{xindx}*T^{2}(k)
|
|
||||||
|
|
||||||
* itrans=type of transfer function
|
|
||||||
0 -> no change (returns 1)
|
|
||||||
4 -> Efstathiou, Bond & White transfer function with Gamma as
|
|
||||||
specified (eqn. 7)
|
|
||||||
5 -> Eisnstein & Hu
|
|
||||||
11 -> read in TF from file (usually CMBFAST)
|
|
||||||
|
|
||||||
NOTE: xk is in h/Mpc and is defined as k=2pi/lambda (not k=1/lambda)
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <stdlib.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* EBW CDM parameters */
|
|
||||||
|
|
||||||
#define aa 6.4
|
|
||||||
#define bb 3.0
|
|
||||||
#define cc 1.7
|
|
||||||
#define xnu 1.13
|
|
||||||
#define twopi 6.283185
|
|
||||||
#define xnuinv -0.884956
|
|
||||||
|
|
||||||
double transfnc(double xk)
|
|
||||||
{
|
|
||||||
double transf;
|
|
||||||
double q,t1,t2;
|
|
||||||
|
|
||||||
if(xk==0.)
|
|
||||||
{
|
|
||||||
transf=1.;
|
|
||||||
return (double)transf;
|
|
||||||
}
|
|
||||||
|
|
||||||
switch(ITRANS)
|
|
||||||
{
|
|
||||||
case 0:
|
|
||||||
transf=1.;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 4:
|
|
||||||
q = xk/GAMMA;
|
|
||||||
t1=aa*q+pow((bb*q),1.5)+(cc*q)*(cc*q);
|
|
||||||
t2=pow(t1,xnu);
|
|
||||||
transf=pow((1.+t2),xnuinv);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 5:
|
|
||||||
transf = tf_eisenstein_hu(xk);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 11:
|
|
||||||
transf = transfunc_file(xk);
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
fprintf(stderr,"transfnc> Unrecognized transfer function %d \n",ITRANS);
|
|
||||||
exit(-1);
|
|
||||||
break;
|
|
||||||
|
|
||||||
}
|
|
||||||
return (double)transf;
|
|
||||||
}
|
|
|
@ -1,59 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* This routine reads in a transfer function from a file.
|
|
||||||
* - col 1 = k [h/Mpc]
|
|
||||||
* - col 2 = T(k)
|
|
||||||
* other columns not used.
|
|
||||||
*
|
|
||||||
* The TF is considered to be un-normalized, and will normalize all values
|
|
||||||
* by the entry in the first line.
|
|
||||||
*
|
|
||||||
* The TF is stored in arrays an spline interpolation is used at all k values.
|
|
||||||
* The interpolation is in log(k)/log(TF) to preserve the power-law dependence
|
|
||||||
* of T(k) on k outside the k-range of the file.
|
|
||||||
*/
|
|
||||||
|
|
||||||
double transfunc_file(double xk)
|
|
||||||
{
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
static int flag=1,n;
|
|
||||||
int i;
|
|
||||||
double t,x0;
|
|
||||||
FILE *fp;
|
|
||||||
char a[1000];
|
|
||||||
float x1,x2;
|
|
||||||
|
|
||||||
if(flag)
|
|
||||||
{
|
|
||||||
flag=0;
|
|
||||||
|
|
||||||
fp=openfile(Files.TF_file);
|
|
||||||
n=filesize(fp);
|
|
||||||
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
fscanf(fp,"%f %f",&x1,&x2);
|
|
||||||
x[i]=x1;
|
|
||||||
y[i]=x2;
|
|
||||||
if(i==1)x0=y[i];
|
|
||||||
fgets(a,1000,fp);
|
|
||||||
y[i]/=x0;
|
|
||||||
x[i]=log(x[i]);
|
|
||||||
y[i]=log(y[i]);
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
spline(x,y,n,1.0E+30,1.0E+30,y2);
|
|
||||||
}
|
|
||||||
xk=log(xk);
|
|
||||||
splint(x,y,y2,n,xk,&t);
|
|
||||||
return(exp(t));
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
|
@ -1,511 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <time.h>
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
|
|
||||||
/* This is the two-halo term of the correlation function in both real space.
|
|
||||||
* This is solved in Fourier space and requires the
|
|
||||||
* non-linear power spectrum P_nl(k), which is from the model of Smith et al.
|
|
||||||
* (see Smith et al, astro-ph/0207664).
|
|
||||||
*
|
|
||||||
* For specifics see Berlind & Weinberg (2002), Zheng (2003), Tinker et al (2005)
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Internal functions.
|
|
||||||
*/
|
|
||||||
double func2(double m);
|
|
||||||
double func2_cen(double m);
|
|
||||||
double func2_sat(double m);
|
|
||||||
double func5(double xk);
|
|
||||||
double func_mlimit(double m);
|
|
||||||
void calc_real_space_two_halo(double *r, double *xi, int *n);
|
|
||||||
double HOD2_two_halo_real_space(double r);
|
|
||||||
|
|
||||||
/* the restricted number density.
|
|
||||||
*/
|
|
||||||
double NG_MINUS2;
|
|
||||||
|
|
||||||
/* Globals needed for the qromo functions.
|
|
||||||
*/
|
|
||||||
double r_g1,
|
|
||||||
k1;
|
|
||||||
|
|
||||||
/* Global checkflag to stop doing the restricted
|
|
||||||
* number density.
|
|
||||||
*/
|
|
||||||
int checkflag;
|
|
||||||
|
|
||||||
/* This tabulates the two-halo real-space term for future
|
|
||||||
* spline interpolation.
|
|
||||||
*/
|
|
||||||
double two_halo_real_space(double r)
|
|
||||||
{
|
|
||||||
static int flag=0,n=45;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int i;
|
|
||||||
double max=16,min=9,a,rvir_min;
|
|
||||||
float x1,x2;
|
|
||||||
FILE *fp;
|
|
||||||
|
|
||||||
// if(r<25)
|
|
||||||
// return(nbody_two_halo(r));
|
|
||||||
|
|
||||||
if(!flag || RESET_FLAG_2H)
|
|
||||||
{
|
|
||||||
if(!LINEAR_PSP)
|
|
||||||
nonlinear_sigmac(8.0);
|
|
||||||
n=30;
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
RESET_FLAG_2H=0;
|
|
||||||
flag=1;
|
|
||||||
if(OUTPUT>1)
|
|
||||||
fprintf(stdout,"Calculating real-space two-halo term...\n");
|
|
||||||
calc_real_space_two_halo(x,y,&n);
|
|
||||||
if(!HOD.color==2)
|
|
||||||
check_for_smoothness(x,y,n,1.5);
|
|
||||||
XI_MAX_RADIUS=x[n];
|
|
||||||
if(XCORR)
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
a = HOD2_two_halo_real_space(x[i]);
|
|
||||||
y[i] = a*y[i];
|
|
||||||
if(y[i]<0)y[i]=-1;
|
|
||||||
else y[i] = sqrt(y[i]);
|
|
||||||
}
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(r<R_MIN_2HALO)return(-1);
|
|
||||||
if(r>XI_MAX_RADIUS)return(-1);
|
|
||||||
splint(x,y,y2,n,r,&a);
|
|
||||||
|
|
||||||
/* This check is against the spline interpolation, which
|
|
||||||
* sometimes has (smoothness) problems with the sharp truncation of xi_2h
|
|
||||||
* at small separations.
|
|
||||||
*/
|
|
||||||
if(a<-1)return(-1);
|
|
||||||
return(a);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
void calc_real_space_two_halo(double *r, double *xi, int *nn)
|
|
||||||
{
|
|
||||||
double xtemp[200],rtemp[200];
|
|
||||||
double mlimit,s2,rlo,rhi=90,dr,klo,tolerance=1.0e-7,s1;
|
|
||||||
int i,j,imin=0,n;
|
|
||||||
double t0,t1,t2,t1s=0,t2s=0;
|
|
||||||
|
|
||||||
n=*nn;
|
|
||||||
|
|
||||||
/* Set the minimum separation of two-halo pairs.
|
|
||||||
*/
|
|
||||||
if(HOD.color)
|
|
||||||
{
|
|
||||||
while(N_avg(HOD.M_low)<0.001)
|
|
||||||
HOD.M_low*=1.01;
|
|
||||||
}
|
|
||||||
|
|
||||||
rlo = 2.2*pow(3*HOD.M_low/(4*DELTA_HALO*PI*OMEGA_M*RHO_CRIT),1.0/3.0);
|
|
||||||
if(EXCLUSION==3)
|
|
||||||
rlo = rlo/1.3;
|
|
||||||
if(EXCLUSION==4)
|
|
||||||
rlo = rlo/2.1;
|
|
||||||
R_MIN_2HALO = rlo;
|
|
||||||
|
|
||||||
rlo = log(rlo);
|
|
||||||
dr=(log(rhi)-rlo)/(n-1);
|
|
||||||
|
|
||||||
checkflag=0;
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
r_g1=r[i]=exp(rlo+dr*(i-1));
|
|
||||||
|
|
||||||
if(r_g1>30)
|
|
||||||
{
|
|
||||||
GALAXY_BIAS = qromo(func_galaxy_bias,log(HOD.M_low),log(HOD.M_max),midpnt)/GALAXY_DENSITY;
|
|
||||||
xi[i]=xi_interp(r_g1)*GALAXY_BIAS*GALAXY_BIAS;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Fourier transform. If BOX_SIZE specified, then truncate
|
|
||||||
* transform at that k. If no box, take integral to k=0.
|
|
||||||
*/
|
|
||||||
klo = 0;
|
|
||||||
if(BOX_SIZE)klo=1/BOX_SIZE;
|
|
||||||
|
|
||||||
j=16;
|
|
||||||
s1 = qromo(func5,klo,j*TWOPI/r_g1,midpnt);
|
|
||||||
s2 = s1;
|
|
||||||
klo = j*TWOPI/r_g1;
|
|
||||||
|
|
||||||
while(fabs(s1)>tolerance*s2) {
|
|
||||||
j+=16;
|
|
||||||
s1 = qromo(func5,klo,j*TWOPI/r_g1,midpnt);
|
|
||||||
s2 += s1;
|
|
||||||
klo = j*TWOPI/r_g1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Divide the integral by the restricted number density.
|
|
||||||
* (This is calculated in the pk_gg_2h function.)
|
|
||||||
*/
|
|
||||||
s2=s2/NG_MINUS2;
|
|
||||||
|
|
||||||
/* Correction factor b/c we haven't been
|
|
||||||
* including all halos.
|
|
||||||
*/
|
|
||||||
xi[i]=(NG_MINUS2/GALAXY_DENSITY/GALAXY_DENSITY)*(1+s2)-1;
|
|
||||||
if(isnan(xi[i]))xi[i]=-1;
|
|
||||||
|
|
||||||
if(xi[i]==-1)imin=i;
|
|
||||||
|
|
||||||
if(OUTPUT>1)
|
|
||||||
printf("calc_2halo> %f %f %d\n",r[i],xi[i],checkflag);
|
|
||||||
//printf("calc_2halo> %f %f %d\n",r[i],xi[i],checkflag);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Eliminate all entries which have xi=-1
|
|
||||||
* (to eliminate a "wavy" spline fit at small r
|
|
||||||
*/
|
|
||||||
for(j=0,i=imin+1;i<=n;++i)
|
|
||||||
{
|
|
||||||
j++;
|
|
||||||
xtemp[j]=xi[i];
|
|
||||||
rtemp[j]=r[i];
|
|
||||||
}
|
|
||||||
n=j;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
r[i]=rtemp[i];
|
|
||||||
xi[i]=xtemp[i];
|
|
||||||
}
|
|
||||||
*nn=n;
|
|
||||||
R_MIN_2HALO=r[1];
|
|
||||||
|
|
||||||
/*printf("calc_2halo> %d %d %f\n",imin,n,r[1]);*/
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* This calculates and tabulates the galaxy power spectrum. This is done
|
|
||||||
* by taking the galaxy-number-weighted halo bias (with scale-dependent
|
|
||||||
* halo bias and extended structure of halos taken into account) and multiplying
|
|
||||||
* it by the non-linear matter power spectrum.
|
|
||||||
*
|
|
||||||
* The galaxy-number-weighted average is an integral over the halo mass function
|
|
||||||
* (see Equations B10 & B12 in Appendix B of Tinker et al.) over all allowed halo
|
|
||||||
* pairs.
|
|
||||||
*
|
|
||||||
* The allowed number of halo pairs is controlled by the type of halo exclusion used:
|
|
||||||
* EXCLUSION = 1 --> only halos with Rvir < r/2
|
|
||||||
* EXCLUSION = 2 --> only halo PAIRS with R1+R2 < r ("spherical eclusion")
|
|
||||||
* EXCLUSION = 3 --> same as 3
|
|
||||||
* EXCLUSION = 4 --> only halos with Rvir < r
|
|
||||||
*
|
|
||||||
* 1 and 4 are fast b/c the integral is separable, calculated once and squared. Can drastically
|
|
||||||
* underestimate the number of small-sep pairs.
|
|
||||||
*
|
|
||||||
* for 2/3, I've incorporated the approximation in Tinker etal 2005 called the n_g-matched
|
|
||||||
* method, where instead of actually doing the double integral over halo_mass_1 and halo_mass_2,
|
|
||||||
* i calculate the number density of that type of exclusion, and calculate the effective
|
|
||||||
* radius for the 1/4-type exlcusion-- ie, halos with Rvir < [x]*r where 0.5<[x]<1.0.
|
|
||||||
*/
|
|
||||||
|
|
||||||
double psp_gg_2h(double k, double r)
|
|
||||||
{
|
|
||||||
static double rp=-1,*x,*y,*y2;
|
|
||||||
static int flag=0;
|
|
||||||
int n=60,i;
|
|
||||||
double a,dk,klo=-3,khi=3,xk,s1,s2,mhi,mlo,mhi1,mlo1;
|
|
||||||
|
|
||||||
double t1,t0,ttot1,ttot2;
|
|
||||||
|
|
||||||
|
|
||||||
/* The fourier transform is done at each r, so tabulate the power spectrum
|
|
||||||
* at all k for a given r. If r has changed, re-tabulate.
|
|
||||||
*/
|
|
||||||
if(rp!=r)
|
|
||||||
{
|
|
||||||
mlo=HOD.M_low;
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
flag=1;
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
dk=(khi-klo)/n;
|
|
||||||
|
|
||||||
switch(EXCLUSION) {
|
|
||||||
case 1:
|
|
||||||
mhi=4./3.*DELTA_HALO*RHO_CRIT*PI*r*r*r*OMEGA_M*0.125;
|
|
||||||
if(mhi>HOD.M_max)mhi=HOD.M_max;
|
|
||||||
NG_MINUS2 = qromo(func_galaxy_density,log(mlo),log(mhi),midpnt);
|
|
||||||
NG_MINUS2*=NG_MINUS2;
|
|
||||||
for(i=n;i>=1;--i)
|
|
||||||
{
|
|
||||||
xk=pow(10.0,klo+dk*i);
|
|
||||||
k1=xk;
|
|
||||||
if(nfw_transform(xk,mhi)<0.999)
|
|
||||||
a=qromo(func2,log(mlo),log(mhi),midpnt);
|
|
||||||
x[i]=log(xk);
|
|
||||||
if(LINEAR_PSP)
|
|
||||||
y[i]=log(linear_power_spectrum(xk)*a*a);
|
|
||||||
else
|
|
||||||
y[i]=log(nonlinear_power_spectrum(xk)*a*a);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 2:
|
|
||||||
case 3:
|
|
||||||
if(!checkflag)
|
|
||||||
s2=restricted_number_density(r);
|
|
||||||
else
|
|
||||||
s2=GALAXY_DENSITY;
|
|
||||||
|
|
||||||
mhi=4./3.*DELTA_HALO*RHO_CRIT*PI*r*r*r*OMEGA_M*0.125;
|
|
||||||
if(s2>=GALAXY_DENSITY || mhi>HOD.M_max)
|
|
||||||
{
|
|
||||||
s2=GALAXY_DENSITY;
|
|
||||||
mhi=log(HOD.M_max);
|
|
||||||
checkflag=1;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
mhi=0;
|
|
||||||
NG_MINUS2=s2;
|
|
||||||
if(N_avg(HOD.M_low*1.001)>0)
|
|
||||||
{
|
|
||||||
if(qromo(func_galaxy_density,log(HOD.M_low),log(HOD.M_low*1.0001),midpnt)
|
|
||||||
>NG_MINUS2)mhi=log(HOD.M_low*1.0001);
|
|
||||||
}
|
|
||||||
if(qromo(func_galaxy_density,log(HOD.M_low),log(HOD.M_max*4.0),midpnt)
|
|
||||||
<NG_MINUS2)mhi=log(HOD.M_max);
|
|
||||||
if(!mhi)
|
|
||||||
mhi=zbrent(func_mlimit,log(HOD.M_low*1.0001),log(HOD.M_max*4.0),1.0E-4);
|
|
||||||
if(mhi>log(HOD.M_max))mhi=log(HOD.M_max);
|
|
||||||
}
|
|
||||||
NG_MINUS2=s2*s2;
|
|
||||||
for(i=n;i>=1;--i)
|
|
||||||
{
|
|
||||||
xk=pow(10.0,klo+dk*i);
|
|
||||||
k1=xk;
|
|
||||||
if(nfw_transform(xk,exp(mhi))<0.999) {
|
|
||||||
if(HOD.pdfc==7)/* || HOD.pdfc==6 || HOD.pdfc==9 || HOD.pdfc==8)*/
|
|
||||||
{
|
|
||||||
a = qromo(func2_cen,log(HOD.M_low),log(HOD.M_cen_max),midpnt);
|
|
||||||
a += qromo(func2_sat,log(HOD.M_low),log(HOD.M_max),midpnt);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
MAG_21_CHECK:
|
|
||||||
a=qromo(func2,log(mlo),mhi,midpnt);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
x[i]=log(xk);
|
|
||||||
if(LINEAR_PSP)
|
|
||||||
y[i]=log(linear_power_spectrum(xk)*a*a);
|
|
||||||
else
|
|
||||||
y[i]=log(nonlinear_power_spectrum(xk)*a*a);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 4: // where max halo mass is M(R=r) rather than M(R=r/2)
|
|
||||||
mhi=4./3.*DELTA_HALO*RHO_CRIT*PI*r*r*r*OMEGA_M;
|
|
||||||
if(mhi>HOD.M_max)mhi=HOD.M_max;
|
|
||||||
NG_MINUS2 = qromo(func_galaxy_density,log(mlo),log(mhi),midpnt);
|
|
||||||
NG_MINUS2*=NG_MINUS2;
|
|
||||||
for(i=n;i>=1;--i)
|
|
||||||
{
|
|
||||||
xk=pow(10.0,klo+dk*i);
|
|
||||||
k1=xk;
|
|
||||||
if(nfw_transform(xk,mhi)<0.999)
|
|
||||||
a=qromo(func2,log(mlo),log(mhi),midpnt);
|
|
||||||
x[i]=log(xk);
|
|
||||||
if(LINEAR_PSP)
|
|
||||||
y[i]=log(linear_power_spectrum(xk)*a*a);
|
|
||||||
else
|
|
||||||
y[i]=log(nonlinear_power_spectrum(xk)*a*a);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
endrun("Error: invalid choice of EXCLUSION");
|
|
||||||
}
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
rp=r;
|
|
||||||
}
|
|
||||||
k=log(k);
|
|
||||||
splint(x,y,y2,n,k,&a);
|
|
||||||
return(exp(a));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* The routine called by qromo for the integral in Zheng's Eq [7]
|
|
||||||
*/
|
|
||||||
double func2(double m)
|
|
||||||
{
|
|
||||||
double n,N,b,yg,x,Ncen,Nsat;
|
|
||||||
|
|
||||||
m=exp(m);
|
|
||||||
n=dndM_interp(m);
|
|
||||||
b=bias_interp(m,r_g1);
|
|
||||||
Ncen=N_cen(m);
|
|
||||||
Nsat=N_sat(m);
|
|
||||||
yg=nfw_transform(k1,m);
|
|
||||||
x = n*(Ncen + Nsat*yg)*b*m;
|
|
||||||
return(x);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* The routine called by qromo for the integral in Zheng's Eq [7]
|
|
||||||
* FOR CENTRAL GALAXIES ONLY: This means no Fourier transform of NFW profile.
|
|
||||||
*/
|
|
||||||
double func2_cen(double m)
|
|
||||||
{
|
|
||||||
double n,N,b,yg,x;
|
|
||||||
|
|
||||||
m=exp(m);
|
|
||||||
n=dndM_interp(m);
|
|
||||||
b=bias_interp(m,r_g1);
|
|
||||||
N=N_cen(m);
|
|
||||||
x=n*N*b*m;
|
|
||||||
return(x);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* The routine called by qromo for the integral in Zheng's Eq [7]
|
|
||||||
* FOR SATELLITE GALAXIES ONLY.
|
|
||||||
*/
|
|
||||||
double func2_sat(double m)
|
|
||||||
{
|
|
||||||
double n,N,b,yg,x;
|
|
||||||
|
|
||||||
m=exp(m);
|
|
||||||
n=dndM_interp(m);
|
|
||||||
b=bias_interp(m,r_g1);
|
|
||||||
N=N_sat(m);
|
|
||||||
yg=nfw_transform(k1,m);
|
|
||||||
x=n*N*b*yg*m;
|
|
||||||
return(x);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* This is the integrand of the Fourier transform
|
|
||||||
* of the two-halo power spectrum to correlation function
|
|
||||||
*/
|
|
||||||
double func5(double xk)
|
|
||||||
{
|
|
||||||
double psp1;
|
|
||||||
double xk1,xk2,x3;
|
|
||||||
|
|
||||||
if(xk==0)return(0);
|
|
||||||
psp1=psp_gg_2h(xk,r_g1);
|
|
||||||
xk1=r_g1*xk;
|
|
||||||
psp1*=sin(xk1)/xk1/xk;
|
|
||||||
return(psp1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This is the function sent to zbrent to calculate the halo mass
|
|
||||||
* which gives the matched restricted number density.
|
|
||||||
*/
|
|
||||||
double func_mlimit(double m)
|
|
||||||
{
|
|
||||||
double s1;
|
|
||||||
if(N_avg(exp(m))>0)
|
|
||||||
s1=qromo(func_galaxy_density,log(HOD.M_low),m,midpnt);
|
|
||||||
else
|
|
||||||
s1=0;
|
|
||||||
return(s1-NG_MINUS2);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* This tabulates the two-halo real-space term
|
|
||||||
* for the second HOD function for future
|
|
||||||
* spline interpolation.
|
|
||||||
*/
|
|
||||||
double HOD2_two_halo_real_space(double r)
|
|
||||||
{
|
|
||||||
static int flag=0,n=45;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int i;
|
|
||||||
double max=16,min=9,a,rvir_min,galtemp;
|
|
||||||
float x1,x2;
|
|
||||||
FILE *fp;
|
|
||||||
|
|
||||||
if(!flag || RESET_FLAG_2H)
|
|
||||||
{
|
|
||||||
/* Switch HODs temporarily
|
|
||||||
*/
|
|
||||||
HODt.M_min = HOD.M_min;
|
|
||||||
HODt.M_low = HOD.M_low;
|
|
||||||
HODt.M1 = HOD.M1;
|
|
||||||
HODt.alpha = HOD.alpha;
|
|
||||||
HODt.M_cen_max = HOD.M_cen_max;
|
|
||||||
HODt.sigma_logM = HOD.sigma_logM;
|
|
||||||
HODt.M_max = HOD.M_max;
|
|
||||||
HODt.pdfc = HOD.pdfc;
|
|
||||||
HODt.pdfs = HOD.pdfs;
|
|
||||||
galtemp = GALAXY_DENSITY;
|
|
||||||
|
|
||||||
HOD.M_min = HOD2.M_min;
|
|
||||||
HOD.M_low = HOD2.M_low;
|
|
||||||
HOD.M1 = HOD2.M1;
|
|
||||||
HOD.alpha = HOD2.alpha;
|
|
||||||
HOD.M_cen_max = HOD2.M_cen_max;
|
|
||||||
HOD.sigma_logM = HOD2.sigma_logM;
|
|
||||||
HOD.M_max = HOD2.M_max;
|
|
||||||
HOD.pdfc = HOD2.pdfc;
|
|
||||||
HOD.pdfs = HOD2.pdfs;
|
|
||||||
GALAXY_DENSITY = GALAXY_DENSITY2;
|
|
||||||
set_HOD_params();
|
|
||||||
|
|
||||||
if(!LINEAR_PSP)
|
|
||||||
nonlinear_sigmac(8.0);
|
|
||||||
n=30;
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
RESET_FLAG_2H=0;
|
|
||||||
flag=1;
|
|
||||||
if(OUTPUT)
|
|
||||||
fprintf(stdout,"Calculating HOD2 real-space two-halo term...\n");
|
|
||||||
calc_real_space_two_halo(x,y,&n);
|
|
||||||
check_for_smoothness(x,y,n,1.5);
|
|
||||||
XI_MAX_RADIUS=x[n];
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
|
|
||||||
/* Switch HODs back
|
|
||||||
*/
|
|
||||||
HOD.M_min = HODt.M_min;
|
|
||||||
HOD.M_low = HODt.M_low;
|
|
||||||
HOD.M1 = HODt.M1;
|
|
||||||
HOD.alpha = HODt.alpha;
|
|
||||||
HOD.M_cen_max = HODt.M_cen_max;
|
|
||||||
HOD.sigma_logM = HODt.sigma_logM;
|
|
||||||
HOD.M_max = HODt.M_max;
|
|
||||||
HOD.pdfc = HODt.pdfc;
|
|
||||||
HOD.pdfs = HODt.pdfs;
|
|
||||||
GALAXY_DENSITY = galtemp;
|
|
||||||
set_HOD_params();
|
|
||||||
}
|
|
||||||
|
|
||||||
if(r>XI_MAX_RADIUS)return(-1);
|
|
||||||
if(r<R_MIN_2HALO)return(-1);
|
|
||||||
splint(x,y,y2,n,r,&a);
|
|
||||||
|
|
||||||
/* This check is against the spline interpolation, which
|
|
||||||
* sometimes has (smoothness) problems with the sharp truncation of xi_2h
|
|
||||||
* at small separations.
|
|
||||||
*/
|
|
||||||
if(a<-1)return(-1);
|
|
||||||
return(a);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,745 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <string.h>
|
|
||||||
#include <math.h>
|
|
||||||
#include <time.h>
|
|
||||||
|
|
||||||
#ifdef PARALLEL
|
|
||||||
#include <mpi.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* This is a series of routines to calculate the projected correlation
|
|
||||||
* function from the real-space one (HOD calculation) and then chi2
|
|
||||||
* minimize the parameters based on the SDSS data.
|
|
||||||
*/
|
|
||||||
int FIT_WITH_COSMO = 0,
|
|
||||||
FIRST_CALL = 0;
|
|
||||||
|
|
||||||
double rp_g1;
|
|
||||||
double func_wp(double z);
|
|
||||||
double func_wp_rspace(double z);
|
|
||||||
double func_wp_matter(double z);
|
|
||||||
double chi2_wp(double *a);
|
|
||||||
|
|
||||||
void wp_input(void);
|
|
||||||
void initial_wp_values(double *a, double **pp, double *yy);
|
|
||||||
|
|
||||||
/* This integrates the calculated real-space correlation function
|
|
||||||
* along the line-of-sight to get the projected correlation function (wp(rp).
|
|
||||||
* The value passed if the projected separation.
|
|
||||||
*
|
|
||||||
* In most SDSS work, the maximum line of sight separation considered when
|
|
||||||
* claculating wp is pi=40 Mpc/h, which is the default, but can be set
|
|
||||||
* in the parameter file if desired.
|
|
||||||
*
|
|
||||||
* NB! - note that this routine uses a correction for redshift space distortions.
|
|
||||||
*/
|
|
||||||
double projected_xi(double r)
|
|
||||||
{
|
|
||||||
double x,zmax;
|
|
||||||
|
|
||||||
rp_g1=r*r;
|
|
||||||
two_halo_real_space(1.0);
|
|
||||||
zmax=sqrt(XI_MAX_RADIUS*XI_MAX_RADIUS-rp_g1);
|
|
||||||
if(zmax>wp.pi_max)zmax=wp.pi_max;
|
|
||||||
zmax = wp.pi_max;
|
|
||||||
x=2*qromo(func_wp,log(0.001),log(zmax),midpnt);
|
|
||||||
return(x);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Same as above, but it projects the real-space correlation function
|
|
||||||
* directly, with no correction for redshift-space effects.
|
|
||||||
*/
|
|
||||||
double projected_xi_rspace(double r)
|
|
||||||
{
|
|
||||||
double x,zmax;
|
|
||||||
|
|
||||||
rp_g1=r*r;
|
|
||||||
two_halo_real_space(1.0);
|
|
||||||
zmax=sqrt(XI_MAX_RADIUS*XI_MAX_RADIUS-rp_g1);
|
|
||||||
if(zmax>wp.pi_max)zmax=wp.pi_max;
|
|
||||||
zmax = wp.pi_max;
|
|
||||||
x=2*qromo(func_wp_rspace,log(0.001),log(zmax),midpnt);
|
|
||||||
return(x);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Same as above but for matter.
|
|
||||||
* I've set the maximum line-of-sight separation to be 50 Mpc/h,
|
|
||||||
* which should be good for visual comparison purposes.
|
|
||||||
*/
|
|
||||||
double projected_xi_matter(double r)
|
|
||||||
{
|
|
||||||
double x,zmax;
|
|
||||||
|
|
||||||
rp_g1=r*r;
|
|
||||||
zmax=50.0;
|
|
||||||
x=2*qtrap(func_wp_matter,log(0.001),log(zmax),1.0E-3);
|
|
||||||
return(x);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Function called from qromo/qtrap to get xi->wp
|
|
||||||
* Note that the two-halo term has the linear Kaiser distortion correction.
|
|
||||||
*/
|
|
||||||
double func_wp(double z)
|
|
||||||
{
|
|
||||||
double r;
|
|
||||||
z=exp(z);
|
|
||||||
r=sqrt(rp_g1 + z*z);
|
|
||||||
return(z*(one_halo_real_space(r)+linear_kaiser_distortion(r,z)));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Function called from qromo/qtrap to get xi->wpm but without
|
|
||||||
* correction for redshift-space distortions in the two-halo term
|
|
||||||
*/
|
|
||||||
double func_wp_rspace(double z)
|
|
||||||
{
|
|
||||||
double r;
|
|
||||||
z=exp(z);
|
|
||||||
r=sqrt(rp_g1 + z*z);
|
|
||||||
return(z*(one_halo_real_space(r)+two_halo_real_space(r)));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Function called from qromo/qtrap to get xi->wp (dark matter)
|
|
||||||
*/
|
|
||||||
double func_wp_matter(double z)
|
|
||||||
{
|
|
||||||
double r;
|
|
||||||
z=exp(z);
|
|
||||||
r=sqrt(rp_g1 + z*z);
|
|
||||||
return(z*(xi_interp(r)));
|
|
||||||
}
|
|
||||||
|
|
||||||
/********************************************************************
|
|
||||||
* Below is the actual minimization of the wp data.
|
|
||||||
* Relevant variables: [default]
|
|
||||||
*
|
|
||||||
* COVAR -> [1]=use covariance matrixl; 0=diagonal error bars
|
|
||||||
* DEPROJECTED -> [1]=we're fitting a real-space xi(r) [0]= fitting wp(rp)
|
|
||||||
*
|
|
||||||
* HOD.free[] is a vector which holds 1/0 as to whether or not a parameter is going
|
|
||||||
* to be help constant during the chi^2 minimization. 1==vary 0==constant. The default
|
|
||||||
* on any will be [0].
|
|
||||||
*
|
|
||||||
* i variable
|
|
||||||
* --- --------
|
|
||||||
* [1] -> M_min
|
|
||||||
* [2] -> M1
|
|
||||||
* [3] -> alpha
|
|
||||||
* [4] -> M_cut
|
|
||||||
* [5] -> sigmaM
|
|
||||||
* [6] -> CVIR_FAC
|
|
||||||
* [7] -> MaxCen (M_cen_max)
|
|
||||||
*
|
|
||||||
* Currently I have no checks on whether the values of this vector line
|
|
||||||
* up correctly with the specific HOD pdfs, so double-check hod.bat files.
|
|
||||||
*
|
|
||||||
* Once the code is finished, it will output the values of the HOD parameters
|
|
||||||
* to a file called [filename].fit (+ the bias, satellite fraction, and chi^2).
|
|
||||||
* Then it outputs the mean <N>_M to a file called [filename].HOD.
|
|
||||||
* Then it will go through all the TASKS asked for in the hod.bat file.
|
|
||||||
*/
|
|
||||||
|
|
||||||
void wp_minimization(char *fname)
|
|
||||||
{
|
|
||||||
int n,niter,i,j;
|
|
||||||
double *a,**pp,*yy,FTOL=1.0E-3,chi2min,s1,dlogm,m;
|
|
||||||
FILE *fp;
|
|
||||||
char aa[1000];
|
|
||||||
|
|
||||||
fprintf(stderr,"\n\nCHI2 MINIMIZATION OF W_P(R_P) DATA..........\n");
|
|
||||||
fprintf(stderr, "--------------------------------------------\n\n");
|
|
||||||
|
|
||||||
OUTPUT = 0;
|
|
||||||
FIRST_CALL = 1;
|
|
||||||
|
|
||||||
if(POWELL)
|
|
||||||
FTOL=1.0E-3;
|
|
||||||
else
|
|
||||||
FTOL=1.0E-4;
|
|
||||||
|
|
||||||
for(n=0,i=1;i<=N_HOD_PARAMS;++i)
|
|
||||||
{
|
|
||||||
n+=HOD.free[i];
|
|
||||||
if(!OUTPUT)continue;
|
|
||||||
printf("wp_min> free[%i] = %d\n",i,HOD.free[i]);
|
|
||||||
}
|
|
||||||
if(XCORR)n*=2;
|
|
||||||
if(OUTPUT)printf("wp_min> Number of free parameters: %d\n",n);
|
|
||||||
|
|
||||||
printf("FNAME %s\n",Task.root_filename);
|
|
||||||
wp_input();
|
|
||||||
|
|
||||||
wp.ncf=n;
|
|
||||||
a=dvector(1,n);
|
|
||||||
if(POWELL)
|
|
||||||
pp=dmatrix(1,n,1,n);
|
|
||||||
else
|
|
||||||
pp=dmatrix(1,n+1,1,n);
|
|
||||||
yy=dvector(1,n+1);
|
|
||||||
|
|
||||||
|
|
||||||
initial_wp_values(a,pp,yy);
|
|
||||||
printf("IVALS %e %e %e %e\n",a[1],a[2],a[3],a[4]);
|
|
||||||
|
|
||||||
|
|
||||||
if(POWELL)
|
|
||||||
{
|
|
||||||
if(OUTPUT)printf("wp_min> starting powell.\n");
|
|
||||||
powell(a,pp,n,FTOL,&niter,&chi2min,chi2_wp);
|
|
||||||
chi2min = chi2_wp(a);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if(OUTPUT)printf("wp_min> starting amoeba.\n");
|
|
||||||
amoeba(pp,yy,n,FTOL,chi2_wp,&niter);
|
|
||||||
for(i=1;i<=n;++i)a[i]=pp[1][i];
|
|
||||||
chi2min = chi2_wp(a);
|
|
||||||
}
|
|
||||||
|
|
||||||
s1=qromo(func_galaxy_bias,log(HOD.M_low),log(HOD.M_max),midpnt);
|
|
||||||
GALAXY_BIAS=s1/GALAXY_DENSITY;
|
|
||||||
|
|
||||||
printf("POWELL %e %e ",chi2min,HOD.M_min);
|
|
||||||
for(i=1;i<=n;++i)printf("%e ",a[i]);
|
|
||||||
printf(" %f\n",GALAXY_BIAS);
|
|
||||||
|
|
||||||
/* These outputs are for easy cut & paste into
|
|
||||||
* another batch file.
|
|
||||||
*/
|
|
||||||
//output_parameter_file(fname);
|
|
||||||
|
|
||||||
/* Output the fit and the HOD curve.
|
|
||||||
*/
|
|
||||||
printf("FNAME2 %s\n",Task.root_filename);
|
|
||||||
sprintf(aa,"%s.fit",Task.root_filename);
|
|
||||||
fp=fopen(aa,"w");
|
|
||||||
fprintf(fp,"%e %e ",chi2min,HOD.M_min);
|
|
||||||
for(i=1;i<=n;++i)fprintf(fp,"%e ",a[i]);
|
|
||||||
fprintf(fp," %f\n",GALAXY_BIAS);
|
|
||||||
fclose(fp);
|
|
||||||
|
|
||||||
sprintf(aa,"%s.HOD",Task.root_filename);
|
|
||||||
fp=fopen(aa,"w");
|
|
||||||
dlogm=(log(HOD.M_max)-log(HOD.M_low))/99;
|
|
||||||
for(i=1;i<=100;++i)
|
|
||||||
{
|
|
||||||
m=exp((i-1)*dlogm)*HOD.M_low;
|
|
||||||
fprintf(fp,"%e %e %e %e\n",m,N_cen(m),N_sat(m),N_avg(m));
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
|
|
||||||
fprintf(stderr,"here\n");
|
|
||||||
free_dvector(a,1,n);
|
|
||||||
if(POWELL)
|
|
||||||
free_dmatrix(pp,1,n,1,n);
|
|
||||||
else
|
|
||||||
free_dmatrix(pp,1,n+1,1,n);
|
|
||||||
free_dvector(yy,1,n+1);
|
|
||||||
fprintf(stderr,"here\n");
|
|
||||||
|
|
||||||
free_dvector(wp.r,1,wp.np);
|
|
||||||
free_dvector(wp.x,1,wp.np);
|
|
||||||
free_dvector(wp.e,1,wp.np);
|
|
||||||
if(COVAR)
|
|
||||||
free_dmatrix(wp.covar,1,wp.np,1,wp.np);
|
|
||||||
fprintf(stderr,"done in wp_min\n");
|
|
||||||
}
|
|
||||||
|
|
||||||
double integrated_wp_bin(double r)
|
|
||||||
{
|
|
||||||
return(projected_xi(r)*r);
|
|
||||||
}
|
|
||||||
double integrated_xi_bin(double r)
|
|
||||||
{
|
|
||||||
//return((1+one_halo_real_space(r))*r*r);
|
|
||||||
return((one_halo_real_space(r)+two_halo_real_space(r))*r*r);
|
|
||||||
}
|
|
||||||
|
|
||||||
double chi2_wp(double *a)
|
|
||||||
{
|
|
||||||
static int flag=1,niter=0,ichi=-1;
|
|
||||||
static double *x,mmin_prev=0,t0=-1,t1,sig_prev=0,chi2_prev,chi2_array[10];
|
|
||||||
double **tmp,**tmp2,chi2,x1,ta1,ta2,dt1h,dt2h,par_chi,chi2ngal;
|
|
||||||
int i,j,k,ncf_hod;
|
|
||||||
|
|
||||||
double rlo,rhi,rmin,rmax,dlogr,integrated_wp_bin();
|
|
||||||
|
|
||||||
if(FIRST_CALL)
|
|
||||||
{
|
|
||||||
flag = 1;
|
|
||||||
FIRST_CALL = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
t0 = clock();
|
|
||||||
if(HOD.free[1])FIX_PARAM = 0;
|
|
||||||
|
|
||||||
wp.iter=niter;
|
|
||||||
|
|
||||||
for(j=0,i=1;i<=N_HOD_PARAMS;++i)
|
|
||||||
if(HOD.free[i])
|
|
||||||
if(a[++j]<=0) { printf("%d %e\n",j,a[j]); return(1.0E7); }
|
|
||||||
ncf_hod = j;
|
|
||||||
|
|
||||||
RESET_FLAG_1H=1;
|
|
||||||
RESET_FLAG_2H=1;
|
|
||||||
RESET_KAISER++;
|
|
||||||
|
|
||||||
i=0;j=0;
|
|
||||||
if(HOD.free[++i])HOD.M_min=a[++j];
|
|
||||||
if(HOD.free[++i])HOD.M1=a[++j];
|
|
||||||
if(HOD.free[++i])HOD.alpha=a[++j];
|
|
||||||
if(HOD.free[++i])HOD.M_cut=a[++j];
|
|
||||||
if(HOD.free[++i])HOD.sigma_logM=a[++j];
|
|
||||||
|
|
||||||
if(HOD.pdfc!=9) {
|
|
||||||
if(HOD.free[++i])CVIR_FAC=a[++j];
|
|
||||||
if(HOD.pdfc>=7) {
|
|
||||||
if(HOD.free[++i])HOD.M_cen_max=a[++j]; }
|
|
||||||
else {
|
|
||||||
if(HOD.free[++i])HOD.MaxCen=a[++j]; }
|
|
||||||
}
|
|
||||||
if(HOD.free[++i])HOD.M_sat_break=a[++j];
|
|
||||||
if(HOD.free[++i])HOD.alpha1=a[++j];
|
|
||||||
|
|
||||||
|
|
||||||
if(XCORR) {
|
|
||||||
i=0;
|
|
||||||
if(HOD.free[++i])HOD2.M_min=a[++j];
|
|
||||||
if(HOD.free[++i])HOD2.M1=a[++j];
|
|
||||||
if(HOD.free[++i])HOD2.alpha=a[++j];
|
|
||||||
if(HOD.free[++i])HOD2.M_cut=a[++j];
|
|
||||||
if(HOD.free[++i])HOD2.sigma_logM=a[++j];
|
|
||||||
|
|
||||||
if(HOD2.pdfc!=9) {
|
|
||||||
if(HOD.free[++i])CVIR_FAC=a[++j];
|
|
||||||
if(HOD2.pdfc>=7) {
|
|
||||||
if(HOD2.free[++i])HOD2.M_cen_max=a[++j]; }
|
|
||||||
else {
|
|
||||||
if(HOD2.free[++i])HOD2.MaxCen=a[++j]; }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
if(!ThisTask) {
|
|
||||||
printf("START %d ",niter);
|
|
||||||
for(i=1;i<=ncf_hod;++i)printf("%e ",a[i]);
|
|
||||||
printf("\n");
|
|
||||||
}
|
|
||||||
|
|
||||||
if(HOD.pdfs==2 && HOD.M_cut<1.0e7)return(1.0e7);
|
|
||||||
if(HOD.pdfs==2 && HOD.M_cut>1.0e15)return(1.0e7);
|
|
||||||
|
|
||||||
/* if(HOD.M_min>HOD.M_max)return(1.0e7); */
|
|
||||||
|
|
||||||
/* I've noticed some problems when sigma_logM gets to be
|
|
||||||
* unresonably high or low, so I've put some limits on the
|
|
||||||
* values they can have when doing mag-bin fitting.
|
|
||||||
*/
|
|
||||||
if(HOD.pdfc==6) {
|
|
||||||
if(HOD.sigma_logM<0.07)return(1.0e7);
|
|
||||||
if(HOD.sigma_logM>1.2)return(1.0e7);
|
|
||||||
}
|
|
||||||
if(HOD.pdfc==2 || HOD.pdfc==9) {
|
|
||||||
if(HOD.sigma_logM>1.8)return(1.0e7);
|
|
||||||
if(HOD.sigma_logM<0.05)return(1.0e7);
|
|
||||||
}
|
|
||||||
if(HOD.M1>1.0e17)return(1.0e7);
|
|
||||||
|
|
||||||
if(FIX_PARAM==2)
|
|
||||||
{
|
|
||||||
HOD.M1=HOD.M_low;
|
|
||||||
x1=qromo(func_galaxy_density,log(HOD.M_low),log(HOD.M_max),midpnt);
|
|
||||||
if(x1<GALAXY_DENSITY)return(1.0e7);
|
|
||||||
HOD.M1=pow(10.0,14.8);
|
|
||||||
x1=qromo(func_galaxy_density,log(HOD.M_low),log(HOD.M_max),midpnt);
|
|
||||||
if(x1>GALAXY_DENSITY)return(1.0e7);
|
|
||||||
HOD.M1=0;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* Check the make sure these are reasonable parameters
|
|
||||||
* (Assuming that M_min is NOT a FREE parameter but is
|
|
||||||
* calculated from the GALAXY_DENSITY.)
|
|
||||||
*/
|
|
||||||
if(FIX_PARAM==1 && !HOD.color)
|
|
||||||
{
|
|
||||||
HOD.M_min=pow(10.0,8.0);
|
|
||||||
HOD.M_low=set_low_mass();
|
|
||||||
if(HOD.M_low<1.0e8)HOD.M_low=1.0e8;
|
|
||||||
x1=qromo(func_galaxy_density,log(HOD.M_low),log(HOD.M_max),midpnt);
|
|
||||||
// fprintf(stderr,"PC1 %e %e\n",x1,GALAXY_DENSITY);
|
|
||||||
if(x1<GALAXY_DENSITY) {
|
|
||||||
fprintf(stdout,"PCHECK %e %e %e\n",x1,GALAXY_DENSITY,HOD.M_low);
|
|
||||||
return(1.0e7); }
|
|
||||||
HOD.M_min=pow(10.0,14.8);
|
|
||||||
if(HOD.pdfc==7 && HOD.pdfc==8)
|
|
||||||
HOD.M_min=HOD.M_cen_max*0.99;
|
|
||||||
HOD.M_low=set_low_mass();
|
|
||||||
x1=qromo(func_galaxy_density,log(HOD.M_low),log(HOD.M_max),midpnt);
|
|
||||||
/* fprintf(stderr,"PC2 %e %e %e %e\n",HOD.M_min,HOD.M_low,x1,GALAXY_DENSITY); */
|
|
||||||
if(x1>GALAXY_DENSITY) {
|
|
||||||
fprintf(stdout,"PCHECK %e %e\n",x1,GALAXY_DENSITY);
|
|
||||||
return(1.0e7); }
|
|
||||||
HOD.M_min=0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(ERROR_FLAG)
|
|
||||||
{
|
|
||||||
ERROR_FLAG=0;
|
|
||||||
return(1e7);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(HOD.free[0] || HOD.free[1])
|
|
||||||
GALAXY_DENSITY=0;
|
|
||||||
|
|
||||||
if(!HOD.color)
|
|
||||||
set_HOD_params();
|
|
||||||
|
|
||||||
/*
|
|
||||||
if(XCORR)
|
|
||||||
set_HOD2_params();
|
|
||||||
*/
|
|
||||||
|
|
||||||
if(HOD.free[0])
|
|
||||||
{
|
|
||||||
chi2ngal = (GALAXY_DENSITY-wp.ngal)*(GALAXY_DENSITY-wp.ngal)/wp.ngal_err/wp.ngal_err;
|
|
||||||
if(chi2ngal>1.0E3)return(chi2ngal);
|
|
||||||
}
|
|
||||||
if(ERROR_FLAG)
|
|
||||||
{
|
|
||||||
ERROR_FLAG=0;
|
|
||||||
return(1e7);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* if(HOD.pdfs==3 && HOD.M_cut<HOD.M_low)return(1.1e7); */
|
|
||||||
if(HOD.M_min>HOD.M1)return(1.0e7);
|
|
||||||
/* if(HOD.pdfs==3)if(HOD.M_cut<HOD.M_min*0.9)return(1.2e7); */
|
|
||||||
|
|
||||||
mmin_prev=HOD.M_min;
|
|
||||||
sig_prev=HOD.sigma_logM;
|
|
||||||
|
|
||||||
|
|
||||||
if(HOD.color>=niter)
|
|
||||||
flag = 1;
|
|
||||||
|
|
||||||
if(flag && COVAR)
|
|
||||||
{
|
|
||||||
// printf("INVERTING COVARIANCE MATRIX\n");
|
|
||||||
flag=0;
|
|
||||||
tmp=dmatrix(1,wp.np,1,1);
|
|
||||||
tmp2=dmatrix(1,wp.np,1,wp.np);
|
|
||||||
for(i=1;i<=wp.np;++i)
|
|
||||||
for(j=1;j<=wp.np;++j)
|
|
||||||
tmp2[i][j]=wp.covar[i][j];
|
|
||||||
gaussj(tmp2,wp.np,tmp,1);
|
|
||||||
for(i=1;i<=wp.np;++i)
|
|
||||||
for(j=1;j<=wp.np;++j)
|
|
||||||
wp.covar[i][j]=tmp2[i][j];
|
|
||||||
free_dmatrix(tmp,1,wp.np,1,1);
|
|
||||||
free_dmatrix(tmp2,1,wp.np,1,wp.np);
|
|
||||||
x=dvector(1,wp.np);
|
|
||||||
|
|
||||||
}
|
|
||||||
if(!COVAR)
|
|
||||||
x=dvector(1,wp.np);
|
|
||||||
|
|
||||||
rmax = wp.r[wp.np];
|
|
||||||
rmin = wp.r[1];
|
|
||||||
dlogr = (log(rmax)-log(rmin))/(wp.np-1);
|
|
||||||
BETA = pow(OMEGA_M,0.6)/qromo(func_galaxy_bias,log(HOD.M_low),log(HOD.M_max),midpnt)*
|
|
||||||
GALAXY_DENSITY;
|
|
||||||
if(OUTPUT)
|
|
||||||
printf("BETA = %f\n",BETA);
|
|
||||||
|
|
||||||
rlo = exp(log(rmin) - 0.5*dlogr);
|
|
||||||
for(i=1;i<=wp.np;++i)
|
|
||||||
{
|
|
||||||
rhi = exp(dlogr)*rlo;
|
|
||||||
if(DEPROJECTED)
|
|
||||||
x[i]=one_halo_real_space(wp.r[i])+two_halo_real_space(wp.r[i]);
|
|
||||||
else
|
|
||||||
{
|
|
||||||
x[i]=projected_xi(wp.r[i]);
|
|
||||||
if(wp.format==3)
|
|
||||||
x[i]/=wp.r[i];
|
|
||||||
}
|
|
||||||
if(OUTPUT && !ThisTask)
|
|
||||||
printf("WP%d %f %e %e %e %e\n",niter+1,wp.r[i],wp.x[i],x[i],rlo,rhi);
|
|
||||||
rlo=rhi;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
if(ERROR_FLAG)
|
|
||||||
{
|
|
||||||
ERROR_FLAG=0;
|
|
||||||
return(1e7);
|
|
||||||
}
|
|
||||||
|
|
||||||
chi2=0;
|
|
||||||
|
|
||||||
if(COVAR)
|
|
||||||
{
|
|
||||||
for(i=1;i<=wp.np;++i)
|
|
||||||
for(j=1;j<=wp.np;++j)
|
|
||||||
{
|
|
||||||
x1=(x[i]-wp.x[i])*(x[j]-wp.x[j])*wp.covar[i][j];
|
|
||||||
chi2+=x1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if(!PCA)
|
|
||||||
{
|
|
||||||
for(i=1;i<=wp.np;++i)
|
|
||||||
{
|
|
||||||
x1=(x[i]-wp.x[i])*(x[i]-wp.x[i])/
|
|
||||||
(wp.e[i]*wp.e[i] + wp.esys*wp.esys*x[i]*x[i]);
|
|
||||||
chi2+=x1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
chi2=0;
|
|
||||||
for(i=1;i<=wp.npca;++i)
|
|
||||||
{
|
|
||||||
par_chi=0;
|
|
||||||
for(j=1;j<=wp.np;++j)
|
|
||||||
par_chi+=wp.covar[j][i]*(x[j]-wp.x[j])/wp.e[j];
|
|
||||||
chi2+=par_chi*par_chi/wp.eigen[i];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* From Peder Norberg's instructions for use of PCA:
|
|
||||||
|
|
||||||
do i=1,npca
|
|
||||||
par_chi=0.d0
|
|
||||||
do j=1,npoints
|
|
||||||
par_chi=par_chi+pca(j,i)*(xi_teo(j)-xi_data(j))/err_data(j)
|
|
||||||
enddo
|
|
||||||
chi2=chi2+(par_chi**2)/ev(i) ! (****)
|
|
||||||
enddo
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Add in the error on the galaxy density
|
|
||||||
*/
|
|
||||||
if(HOD.free[0])
|
|
||||||
chi2+=chi2ngal;
|
|
||||||
|
|
||||||
t1 = clock();
|
|
||||||
t0 = difftime(t1,t0)/CLOCKS_PER_SEC;
|
|
||||||
niter++;
|
|
||||||
if(!ThisTask){
|
|
||||||
printf("ITER %7d %e ",niter,chi2);
|
|
||||||
for(i=1;i<=ncf_hod;++i)printf("%e ",a[i]);
|
|
||||||
printf(" %.2f\n",t0);
|
|
||||||
fflush(stdout);
|
|
||||||
if(HOD.free[0])
|
|
||||||
printf("NGAL %e %e %e\n",chi2ngal,
|
|
||||||
GALAXY_DENSITY,wp.ngal);
|
|
||||||
}
|
|
||||||
chi2_prev=chi2;
|
|
||||||
chi2_array[ichi]=chi2;
|
|
||||||
ichi++;
|
|
||||||
if(ichi==10)ichi=0;
|
|
||||||
fflush(stdout);
|
|
||||||
return(chi2);
|
|
||||||
}
|
|
||||||
|
|
||||||
void initial_wp_values(double *a, double **pp, double *yy)
|
|
||||||
{
|
|
||||||
static int flag=1;
|
|
||||||
int i,j;
|
|
||||||
double d[100];
|
|
||||||
|
|
||||||
|
|
||||||
if(flag) {
|
|
||||||
i=0;j=0;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.M_min;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.M1;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.alpha;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.M_cut;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.sigma_logM;
|
|
||||||
if(HOD.free[++i])a[++j]=CVIR_FAC;
|
|
||||||
if(HOD.pdfc>=7){
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.M_cen_max; }
|
|
||||||
else {
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.MaxCen; }
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.M_sat_break;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD.alpha1;
|
|
||||||
|
|
||||||
if(XCORR){
|
|
||||||
i=0;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD2.M_min;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD2.M1;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD2.alpha;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD2.M_cut;
|
|
||||||
if(HOD.free[++i])a[++j]=HOD2.sigma_logM;
|
|
||||||
if(HOD.free[++i])a[++j]=CVIR_FAC;
|
|
||||||
if(HOD2.pdfc>=7){
|
|
||||||
if(HOD.free[++i])a[++j]=HOD2.M_cen_max; }
|
|
||||||
else {
|
|
||||||
if(HOD.free[++i])a[++j]=HOD2.MaxCen; }
|
|
||||||
}
|
|
||||||
printf("INITIAL VALUES: ");
|
|
||||||
for(i=1;i<=wp.ncf;++i)printf("%e ",a[i]);
|
|
||||||
printf("\n");
|
|
||||||
}
|
|
||||||
//flag++;
|
|
||||||
|
|
||||||
/* Make the starting stepsize 10% of the initial values.
|
|
||||||
*/
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
d[i]=a[i]*0.25/flag;
|
|
||||||
|
|
||||||
|
|
||||||
if(POWELL)
|
|
||||||
{
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
{
|
|
||||||
for(j=1;j<=wp.ncf;++j)
|
|
||||||
{
|
|
||||||
pp[i][j]=0;
|
|
||||||
if(i==j)pp[i][j]+=d[j];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
for(j=1;j<=wp.ncf;++j)
|
|
||||||
pp[1][j]=a[j];
|
|
||||||
yy[1]=chi2_wp(a);
|
|
||||||
|
|
||||||
for(i=1;i<=wp.ncf;++i)
|
|
||||||
{
|
|
||||||
a[i]+=d[i];
|
|
||||||
if(i>1)a[i-1]-=d[i-1];
|
|
||||||
yy[i+1]=chi2_wp(a);
|
|
||||||
for(j=1;j<=wp.ncf;++j)
|
|
||||||
pp[i+1][j]=a[j];
|
|
||||||
}
|
|
||||||
a[wp.ncf]-=d[wp.ncf];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* This routine reads in the wp data and covariance matrix from
|
|
||||||
* the filenames specified.
|
|
||||||
*
|
|
||||||
* FILE FORMATS:
|
|
||||||
*
|
|
||||||
* - fname_wp -> r xi e_xi
|
|
||||||
* - fname_covar -> (i=1,np)(j=1,np) read(covar[i][j])
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
void wp_input()
|
|
||||||
{
|
|
||||||
float x1,x2,x3;
|
|
||||||
FILE *fp;
|
|
||||||
int i,j,n;
|
|
||||||
char a[1000];
|
|
||||||
|
|
||||||
if(!(fp=fopen(wp.fname_wp,"r")))
|
|
||||||
{
|
|
||||||
fprintf(stdout,"ERROR opening [%s]\n",wp.fname_wp);
|
|
||||||
endrun("error in wp_input");
|
|
||||||
}
|
|
||||||
wp.np=filesize(fp);
|
|
||||||
|
|
||||||
/* [wp.format==2] means that there are two header lines at
|
|
||||||
* the top of the file.
|
|
||||||
*/
|
|
||||||
if(wp.format==2)
|
|
||||||
{
|
|
||||||
wp.np-=2;
|
|
||||||
fgets(a,1000,fp);
|
|
||||||
fgets(a,1000,fp);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* [wp.format==3] means that there is one header lines at
|
|
||||||
* the top of the file.
|
|
||||||
*/
|
|
||||||
if(wp.format==3)
|
|
||||||
{
|
|
||||||
wp.np-=1;
|
|
||||||
fgets(a,1000,fp);
|
|
||||||
}
|
|
||||||
|
|
||||||
wp.r=dvector(1,wp.np);
|
|
||||||
wp.x=dvector(1,wp.np);
|
|
||||||
wp.e=dvector(1,wp.np);
|
|
||||||
if(PCA)
|
|
||||||
{
|
|
||||||
wp.eigen=dvector(1,wp.np);
|
|
||||||
wp.covar=dmatrix(1,wp.np,1,wp.np);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Read in the projected correlation function data.
|
|
||||||
* Standard format [wp.format==1] is linear r, linear wp, linear err.
|
|
||||||
* [wp.format==2] is log10 r, log10 wp, linear err.
|
|
||||||
* NB! Peder's format is to list the inner edge of the bin, so we're adding 0.1 to each number.
|
|
||||||
*/
|
|
||||||
for(i=1;i<=wp.np;++i)
|
|
||||||
{
|
|
||||||
fscanf(fp,"%f %f %f",&x1,&x2,&x3);
|
|
||||||
wp.r[i]=x1;
|
|
||||||
wp.x[i]=x2;
|
|
||||||
wp.e[i]=x3;
|
|
||||||
if(wp.format==2){
|
|
||||||
wp.r[i] = pow(10.0,wp.r[i]+0.1);
|
|
||||||
wp.x[i] = pow(10.0,wp.x[i])*wp.r[i];
|
|
||||||
wp.e[i] = wp.e[i]*wp.r[i];
|
|
||||||
}
|
|
||||||
if(wp.format==3){
|
|
||||||
fscanf(fp,"%f",&x3);
|
|
||||||
wp.e[i]=x3;
|
|
||||||
wp.r[i] = pow(10.0,wp.r[i]+0.1);
|
|
||||||
// wp.x[i] = wp.x[i]*wp.r[i];
|
|
||||||
// wp.e[i] = wp.e[i]*wp.r[i];
|
|
||||||
}
|
|
||||||
if(wp.format==3 && PCA) {
|
|
||||||
fscanf(fp,"%lf",&wp.eigen[i]);
|
|
||||||
for(j=1;j<=wp.np;++j)
|
|
||||||
fscanf(fp,"%lf",&wp.covar[j][i]);
|
|
||||||
if(wp.npca==0)
|
|
||||||
wp.npca = wp.np;
|
|
||||||
}
|
|
||||||
// if(wp.format==3 && !PCA)
|
|
||||||
fgets(a,1000,fp);
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
fprintf(stderr,"Done reading %d lines from [%s]\n",wp.np,wp.fname_wp);
|
|
||||||
|
|
||||||
if(!COVAR || PCA)
|
|
||||||
return;
|
|
||||||
/*
|
|
||||||
if(wp.format==1)
|
|
||||||
{
|
|
||||||
Work.SDSS_bins=1;
|
|
||||||
for(i=1;i<=40;++i)
|
|
||||||
Work.rad[i] = i-0.5;
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
if(!(fp=fopen(wp.fname_covar,"r")))
|
|
||||||
{
|
|
||||||
fprintf(stdout,"ERROR opening [%s]\n",wp.fname_covar);
|
|
||||||
endrun("error in wp_input");
|
|
||||||
}
|
|
||||||
wp.covar=dmatrix(1,wp.np,1,wp.np);
|
|
||||||
for(i=1;i<=wp.np;++i)
|
|
||||||
for(j=1;j<=wp.np;++j)
|
|
||||||
{
|
|
||||||
fscanf(fp,"%lf",&(wp.covar[i][j]));
|
|
||||||
/* printf("COVAR %d %d %e\n",i,j,wp.covar[i][j]); */
|
|
||||||
}
|
|
||||||
fclose(fp);
|
|
||||||
if(!ThisTask)
|
|
||||||
fprintf(stdout,"Done reading %d lines from [%s]\n",wp.np,wp.fname_covar);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,180 +0,0 @@
|
||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#include "header.h"
|
|
||||||
|
|
||||||
/* This calculates and tabulates both the linear and non-linear
|
|
||||||
* matter correlation function.
|
|
||||||
*
|
|
||||||
* If the parameter BOX_SIZE is set, then the lower limits of the
|
|
||||||
* Fourier transform in 1/BOX_SIZE, else it starts at k=0.
|
|
||||||
*
|
|
||||||
* The integral (Smith etal 2003 MNRAS.341.1311S Eq [4]) to transform:
|
|
||||||
*
|
|
||||||
* Int_0^\infty Delta(k) sin(rk)/rk/k dk
|
|
||||||
*
|
|
||||||
* This integral sometimes gives qromo problems when calculating xi(r) at large r.
|
|
||||||
* Therefore, we cut off the integral at k = 10^3, which has negligible effect on the
|
|
||||||
* correlation function at the relevent scales.
|
|
||||||
*/
|
|
||||||
|
|
||||||
double r_g4;
|
|
||||||
double xi_int(double xk);
|
|
||||||
|
|
||||||
/* Calculates and tabulates the non-linear matter correlation function.
|
|
||||||
* Since this is only really needed for the scale-dependence of the bias,
|
|
||||||
* which is basically 1 at scales r>~8 Mpc/h, I won't calculate this much
|
|
||||||
* past that value.
|
|
||||||
*/
|
|
||||||
double xi_interp(double r)
|
|
||||||
{
|
|
||||||
static int flag=0,prev_cosmo=0;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int n=30,i,j;
|
|
||||||
double a,xi_int(),rhi=95,rlo=0.1,dlogr,klo,s1,s2,tolerance=1.0e-6;
|
|
||||||
|
|
||||||
if(!flag || RESET_COSMOLOGY!=prev_cosmo)
|
|
||||||
{
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
dlogr = (log(rhi)-log(rlo))/(n-1);
|
|
||||||
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
klo = 0;
|
|
||||||
if(BOX_SIZE>0)klo = 1/BOX_SIZE;
|
|
||||||
r_g4 = x[i] = exp((i-1)*dlogr)*rlo;
|
|
||||||
|
|
||||||
j=1;
|
|
||||||
s1 = qromo(xi_int,klo,j/r_g4,midpnt);
|
|
||||||
s2 = s1;
|
|
||||||
klo = j/r_g4;
|
|
||||||
while(mabs(s1)>tolerance*mabs(s2)) {
|
|
||||||
j+=16;
|
|
||||||
s1 = qromo(xi_int,klo,j/r_g4,midpnt);
|
|
||||||
s2 += s1;
|
|
||||||
klo = j/r_g4;
|
|
||||||
}
|
|
||||||
y[i]=s2;
|
|
||||||
}
|
|
||||||
check_for_smoothness(x,y,n,0);
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
}
|
|
||||||
|
|
||||||
splint(x,y,y2,n,r,&a);
|
|
||||||
return(a);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* This is the integrand of Smith et al Eq. [4]
|
|
||||||
*/
|
|
||||||
double xi_int(double xk)
|
|
||||||
{
|
|
||||||
double xk1,xk2,psp;
|
|
||||||
|
|
||||||
if(xk==0)return(0);
|
|
||||||
|
|
||||||
/* power spectrum at xk
|
|
||||||
*/
|
|
||||||
psp=nonlinear_power_spectrum(xk);
|
|
||||||
|
|
||||||
/* Integrand of Fourier transform
|
|
||||||
*/
|
|
||||||
xk1=r_g4*xk;
|
|
||||||
psp*=sin(xk1)/xk1/xk;
|
|
||||||
return psp;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
double xi_linear_interp(double r)
|
|
||||||
{
|
|
||||||
static int flag=0,prev_cosmo=0;
|
|
||||||
static double *x,*y,*y2;
|
|
||||||
int n=100,i;
|
|
||||||
double a,rlo=0.1,rhi=150,dlogr,klo;
|
|
||||||
double xi_linear_int();
|
|
||||||
|
|
||||||
if(!flag || RESET_COSMOLOGY!=prev_cosmo)
|
|
||||||
{
|
|
||||||
if(!flag)
|
|
||||||
{
|
|
||||||
x=dvector(1,n);
|
|
||||||
y=dvector(1,n);
|
|
||||||
y2=dvector(1,n);
|
|
||||||
}
|
|
||||||
flag=1;
|
|
||||||
|
|
||||||
dlogr = (log(rhi)-log(rlo))/(n-1);
|
|
||||||
klo = 0;
|
|
||||||
if(BOX_SIZE>0)klo = 1/BOX_SIZE;
|
|
||||||
for(i=1;i<=n;++i)
|
|
||||||
{
|
|
||||||
r_g4 = x[i] = exp((i-1)*dlogr)*rlo;
|
|
||||||
y[i] = qromo(xi_linear_int,klo,1.0/r_g4,midpnt)+
|
|
||||||
qromo(xi_linear_int,1.0/r_g4,1.0E+3,midpnt);
|
|
||||||
}
|
|
||||||
check_for_smoothness(x,y,n,0);
|
|
||||||
spline(x,y,n,2.0E+30,2.0E+30,y2);
|
|
||||||
prev_cosmo=RESET_COSMOLOGY;
|
|
||||||
}
|
|
||||||
|
|
||||||
splint(x,y,y2,n,r,&a);
|
|
||||||
return(a);
|
|
||||||
}
|
|
||||||
|
|
||||||
double xi_linear_int(xk)
|
|
||||||
double xk;
|
|
||||||
{
|
|
||||||
double psp;
|
|
||||||
double xk1,xk2;
|
|
||||||
|
|
||||||
/* power spectrum at xk
|
|
||||||
*/
|
|
||||||
psp=linear_power_spectrum(xk);
|
|
||||||
|
|
||||||
/* Now take Fourier transform
|
|
||||||
*/
|
|
||||||
xk1=r_g4*xk;
|
|
||||||
psp*=sin(xk1)/xk1/xk;
|
|
||||||
|
|
||||||
return psp;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Sometimes one or two of the correlation function values will
|
|
||||||
* totally crap out, [a side-effect of qromo] so here we check for that and if
|
|
||||||
* we find it then we interpolate the values in log-space.
|
|
||||||
*/
|
|
||||||
void check_for_smoothness(double *x, double *y, int n, double r)
|
|
||||||
{
|
|
||||||
int i,flag,flag2=0;
|
|
||||||
double m,b,new;
|
|
||||||
|
|
||||||
for(i=2;i<n;++i)
|
|
||||||
{
|
|
||||||
flag=0;
|
|
||||||
if(y[i]>0)flag2=1;
|
|
||||||
if(y[i]<0 && !flag2)continue;
|
|
||||||
if(x[i]<r)continue;
|
|
||||||
if(fabs(y[i]/y[i-1])>3.0 && fabs(y[i]/y[i+1])>3.0)flag=1;
|
|
||||||
if(fabs(y[i]/y[i-1])<0.2 && fabs(y[i]/y[i+1])<0.2)flag=1;
|
|
||||||
if(y[i]<0 && (y[i-1]>=0 && y[i+1]>=0))flag=1;
|
|
||||||
if(y[i+1]<0)flag=0;
|
|
||||||
if(!flag)continue;
|
|
||||||
|
|
||||||
m=(log(y[i+1])-log(y[i-1]))/(log(x[i+1])-log(x[i-1]));
|
|
||||||
b=log(y[i+1])-m*log(x[i+1]);
|
|
||||||
new=m*log(x[i])+b;
|
|
||||||
|
|
||||||
fprintf(stderr,"SMOOTHING: %e %e %e r= %f new=%e\n",y[i-1],y[i],y[i+1],x[i],exp(new));
|
|
||||||
y[i]=exp(new);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
417
python_tools/fit_hod/HOD_library.py
Normal file
417
python_tools/fit_hod/HOD_library.py
Normal file
|
@ -0,0 +1,417 @@
|
||||||
|
import numpy as np
|
||||||
|
import readsnap
|
||||||
|
import readsubf
|
||||||
|
import sys
|
||||||
|
import time
|
||||||
|
import random
|
||||||
|
|
||||||
|
###############################################################################
|
||||||
|
#this function returns an array containing the positions of the galaxies (kpc/h)
|
||||||
|
#in the catalogue according to the fiducial density, M1 and alpha
|
||||||
|
#CDM halos with masses within [min_mass,max_mass], are populated
|
||||||
|
#with galaxies. The IDs and positions of the CDM particles belonging to the
|
||||||
|
#different groups are read from the snapshots
|
||||||
|
#If one needs to creates many catalogues, this function is not appropiate,
|
||||||
|
#since it wastes a lot of time reading the snapshots and sorting the IDs
|
||||||
|
#min_mass and max_mass are in units of Msun/h, not 1e10 Msun/h
|
||||||
|
#mass_criteria: definition of the halo virial radius -- 't200' 'm200' 'c200'
|
||||||
|
#fiducial_density: galaxy number density to be reproduced, in (h/Mpc)^3
|
||||||
|
def hod(snapshot_fname,groups_fname,groups_number,min_mass,max_mass,
|
||||||
|
fiducial_density,M1,alpha,mass_criteria,verbose=False):
|
||||||
|
|
||||||
|
thres=1e-3 #controls the max relative error to accept a galaxy density
|
||||||
|
|
||||||
|
#read the header and obtain the boxsize
|
||||||
|
head=readsnap.snapshot_header(snapshot_fname)
|
||||||
|
BoxSize=head.boxsize #BoxSize in kpc/h
|
||||||
|
|
||||||
|
#read positions and IDs of DM particles: sort the IDs array
|
||||||
|
DM_pos=readsnap.read_block(snapshot_fname,"POS ",parttype=-1) #kpc/h
|
||||||
|
DM_ids=readsnap.read_block(snapshot_fname,"ID ",parttype=-1)-1
|
||||||
|
sorted_ids=DM_ids.argsort(axis=0)
|
||||||
|
#the particle whose ID is N is located in the position sorted_ids[N]
|
||||||
|
#i.e. DM_ids[sorted_ids[N]]=N
|
||||||
|
#the position of the particle whose ID is N would be:
|
||||||
|
#DM_pos[sorted_ids[N]]
|
||||||
|
|
||||||
|
#read the IDs of the particles belonging to the CDM halos
|
||||||
|
halos_ID=readsubf.subf_ids(groups_fname,groups_number,0,0,
|
||||||
|
long_ids=True,read_all=True)
|
||||||
|
IDs=halos_ID.SubIDs-1
|
||||||
|
del halos_ID
|
||||||
|
|
||||||
|
#read CDM halos information
|
||||||
|
halos=readsubf.subfind_catalog(groups_fname,groups_number,
|
||||||
|
group_veldisp=True,masstab=True,
|
||||||
|
long_ids=True,swap=False)
|
||||||
|
if mass_criteria=='t200':
|
||||||
|
halos_mass=halos.group_m_tophat200*1e10 #masses in Msun/h
|
||||||
|
halos_radius=halos.group_r_tophat200 #radius in kpc/h
|
||||||
|
elif mass_criteria=='m200':
|
||||||
|
halos_mass=halos.group_m_mean200*1e10 #masses in Msun/h
|
||||||
|
halos_radius=halos.group_r_mean200 #radius in kpc/h
|
||||||
|
elif mass_criteria=='c200':
|
||||||
|
halos_mass=halos.group_m_crit200*1e10 #masses in Msun/h
|
||||||
|
halos_radius=halos.group_r_crit200 #radius in kpc/h
|
||||||
|
else:
|
||||||
|
print 'bad mass_criteria'
|
||||||
|
sys.exit()
|
||||||
|
halos_pos=halos.group_pos #positions in kpc/h
|
||||||
|
halos_len=halos.group_len
|
||||||
|
halos_offset=halos.group_offset
|
||||||
|
halos_indexes=np.where((halos_mass>min_mass) & (halos_mass<max_mass))[0]
|
||||||
|
del halos
|
||||||
|
|
||||||
|
if verbose:
|
||||||
|
print ' '
|
||||||
|
print 'total halos found=',halos_pos.shape[0]
|
||||||
|
print 'halos number density=',len(halos_pos)/(BoxSize*1e-3)**3
|
||||||
|
|
||||||
|
#keep only the halos in the given mass range
|
||||||
|
halo_mass=halos_mass[halos_indexes]
|
||||||
|
halo_pos=halos_pos[halos_indexes]
|
||||||
|
halo_radius=halos_radius[halos_indexes]
|
||||||
|
halo_len=halos_len[halos_indexes]
|
||||||
|
halo_offset=halos_offset[halos_indexes]
|
||||||
|
del halos_indexes
|
||||||
|
|
||||||
|
##### COMPUTE Mmin GIVEN M1 & alpha #####
|
||||||
|
i=0; max_iterations=20 #maximum number of iterations
|
||||||
|
Mmin1=min_mass; Mmin2=max_mass
|
||||||
|
while (i<max_iterations):
|
||||||
|
Mmin=0.5*(Mmin1+Mmin2) #estimation of the HOD parameter Mmin
|
||||||
|
|
||||||
|
total_galaxies=0
|
||||||
|
inside=np.where(halo_mass>Mmin)[0] #take all galaxies with M>Mmin
|
||||||
|
mass=halo_mass[inside] #only halos with M>Mmin have central/satellites
|
||||||
|
|
||||||
|
total_galaxies=mass.shape[0]+np.sum((mass/M1)**alpha)
|
||||||
|
mean_density=total_galaxies*1.0/(BoxSize*1e-3)**3 #galaxies/(Mpc/h)^3
|
||||||
|
|
||||||
|
if (np.absolute((mean_density-fiducial_density)/fiducial_density)<thres):
|
||||||
|
i=max_iterations
|
||||||
|
elif (mean_density>fiducial_density):
|
||||||
|
Mmin1=Mmin
|
||||||
|
else:
|
||||||
|
Mmin2=Mmin
|
||||||
|
i+=1
|
||||||
|
|
||||||
|
if verbose:
|
||||||
|
print ' '
|
||||||
|
print 'Mmin=',Mmin
|
||||||
|
print 'average number of galaxies=',total_galaxies
|
||||||
|
print 'average galaxy density=',mean_density
|
||||||
|
#########################################
|
||||||
|
|
||||||
|
#just halos with M>Mmin; the rest do not host central/satellite galaxies
|
||||||
|
inside=np.where(halo_mass>Mmin)[0]
|
||||||
|
halo_mass=halo_mass[inside]
|
||||||
|
halo_pos=halo_pos[inside]
|
||||||
|
halo_radius=halo_radius[inside]
|
||||||
|
halo_len=halo_len[inside]
|
||||||
|
halo_offset=halo_offset[inside]
|
||||||
|
del inside
|
||||||
|
|
||||||
|
#compute number of satellites in each halo using the Poisson distribution
|
||||||
|
N_mean_sat=(halo_mass/M1)**alpha #mean number of satellites
|
||||||
|
N_sat=np.empty(len(N_mean_sat),dtype=np.int32)
|
||||||
|
for i in range(len(N_sat)):
|
||||||
|
N_sat[i]=np.random.poisson(N_mean_sat[i])
|
||||||
|
N_tot=np.sum(N_sat)+len(halo_mass) #total number of galaxies in the catalogue
|
||||||
|
|
||||||
|
if verbose:
|
||||||
|
print ' '
|
||||||
|
print np.min(halo_mass),'< M_halo <',np.max(halo_mass)
|
||||||
|
print 'total number of galaxies=',N_tot
|
||||||
|
print 'galaxy number density=',N_tot/(BoxSize*1e-3)**3
|
||||||
|
|
||||||
|
#put satellites following the distribution of dark matter in groups
|
||||||
|
if verbose:
|
||||||
|
print ' '
|
||||||
|
print 'Creating mock catalogue ...',
|
||||||
|
|
||||||
|
pos_galaxies=np.empty((N_tot,3),dtype=np.float32)
|
||||||
|
#index: variable that go through halos (may be several galaxies in a halo)
|
||||||
|
#i: variable that go through all (central/satellites) galaxies
|
||||||
|
#count: find number of galaxies that lie beyond its host halo virial radius
|
||||||
|
index=0; count=0; i=0
|
||||||
|
while (index<halo_mass.shape[0]):
|
||||||
|
|
||||||
|
position=halo_pos[index] #position of the DM halo
|
||||||
|
radius=halo_radius[index] #radius of the DM halo
|
||||||
|
|
||||||
|
#save the position of the central galaxy
|
||||||
|
pos_galaxies[i]=position; i+=1
|
||||||
|
|
||||||
|
#if halo contains satellites, save their positions
|
||||||
|
Nsat=N_sat[index]
|
||||||
|
if Nsat>0:
|
||||||
|
offset=halo_offset[index]
|
||||||
|
length=halo_len[index]
|
||||||
|
idss=sorted_ids[IDs[offset:offset+length]]
|
||||||
|
|
||||||
|
#compute the distances to the halo center keeping those with R<Rvir
|
||||||
|
pos=DM_pos[idss] #positions of the particles belonging to the halo
|
||||||
|
posc=pos-position
|
||||||
|
|
||||||
|
#this is to populate correctly halos closer to box boundaries
|
||||||
|
if np.any((position+radius>BoxSize) + (position-radius<0.0)):
|
||||||
|
|
||||||
|
inside=np.where(posc[:,0]>BoxSize/2.0)[0]
|
||||||
|
posc[inside,0]-=BoxSize
|
||||||
|
inside=np.where(posc[:,0]<-BoxSize/2.0)[0]
|
||||||
|
posc[inside,0]+=BoxSize
|
||||||
|
|
||||||
|
inside=np.where(posc[:,1]>BoxSize/2.0)[0]
|
||||||
|
posc[inside,1]-=BoxSize
|
||||||
|
inside=np.where(posc[:,1]<-BoxSize/2.0)[0]
|
||||||
|
posc[inside,1]+=BoxSize
|
||||||
|
|
||||||
|
inside=np.where(posc[:,2]>BoxSize/2.0)[0]
|
||||||
|
posc[inside,2]-=BoxSize
|
||||||
|
inside=np.where(posc[:,2]<-BoxSize/2.0)[0]
|
||||||
|
posc[inside,2]+=BoxSize
|
||||||
|
|
||||||
|
radii=np.sqrt(posc[:,0]**2+posc[:,1]**2+posc[:,2]**2)
|
||||||
|
inside=np.where(radii<radius)[0]
|
||||||
|
selected=random.sample(inside,Nsat)
|
||||||
|
pos=pos[selected]
|
||||||
|
|
||||||
|
#aditional, not esential check. Can be comment out
|
||||||
|
posc=pos-position
|
||||||
|
if np.any((posc>BoxSize/2.0) + (posc<-BoxSize/2.0)):
|
||||||
|
inside=np.where(posc[:,0]>BoxSize/2.0)[0]
|
||||||
|
posc[inside,0]-=BoxSize
|
||||||
|
inside=np.where(posc[:,0]<-BoxSize/2.0)[0]
|
||||||
|
posc[inside,0]+=BoxSize
|
||||||
|
|
||||||
|
inside=np.where(posc[:,1]>BoxSize/2.0)[0]
|
||||||
|
posc[inside,1]-=BoxSize
|
||||||
|
inside=np.where(posc[:,1]<-BoxSize/2.0)[0]
|
||||||
|
posc[inside,1]+=BoxSize
|
||||||
|
|
||||||
|
inside=np.where(posc[:,2]>BoxSize/2.0)[0]
|
||||||
|
posc[inside,2]-=BoxSize
|
||||||
|
inside=np.where(posc[:,2]<-BoxSize/2.0)[0]
|
||||||
|
posc[inside,2]+=BoxSize
|
||||||
|
r_max=np.max(np.sqrt(posc[:,0]**2+posc[:,1]**2+posc[:,2]**2))
|
||||||
|
if r_max>radius: #check no particles beyond Rv selected
|
||||||
|
print position
|
||||||
|
print radius
|
||||||
|
print pos
|
||||||
|
count+=1
|
||||||
|
|
||||||
|
for j in range(Nsat):
|
||||||
|
pos_galaxies[i]=pos[j]; i+=1
|
||||||
|
index+=1
|
||||||
|
|
||||||
|
if verbose:
|
||||||
|
print 'done'
|
||||||
|
#some final checks
|
||||||
|
if i!=N_tot:
|
||||||
|
print 'some galaxies missing:'
|
||||||
|
print 'register',i,'galaxies out of',N_tot
|
||||||
|
if count>0:
|
||||||
|
print 'error:',count,'particles beyond the virial radius selected'
|
||||||
|
|
||||||
|
return pos_galaxies
|
||||||
|
###############################################################################
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#This function is equal to the above one, except that the snapshot read, halos
|
||||||
|
#read and ID sorting it is not performing here. It is best suited when many
|
||||||
|
#galaxy catalogues need to be created: for example, when iterating among M1 and
|
||||||
|
#alpha trying to find the best combination that reproduces the measured wp(r)
|
||||||
|
#VARIABLES:
|
||||||
|
#DM_pos: array containing the positions of the CDM particles
|
||||||
|
#sorted_ids: array containing the positions of the IDs in the snapshots.
|
||||||
|
#sorted_ids[N] gives the position where the particle whose ID is N is located
|
||||||
|
#IDs:IDs array as read from the subfind ID file
|
||||||
|
#halo_mass: array containing the masses of the CDM halos in the mass interval
|
||||||
|
#halo_pos: array containing the positions of the CDM halos in the mass interval
|
||||||
|
#halo_radius: array containing the radii of the CDM halos in the mass interval
|
||||||
|
#halo_len: array containing the len of the CDM halos in the mass interval
|
||||||
|
#halo_offset: array containing the offset of the CDM halos in the mass interval
|
||||||
|
#BoxSize: Size of the simulation Box. In Mpc/h
|
||||||
|
#fiducial_density: galaxy number density to be reproduced, in (h/Mpc)^3
|
||||||
|
def hod_fast(DM_pos,sorted_ids,IDs,halo_mass,halo_pos,halo_radius,halo_len,
|
||||||
|
halo_offset,BoxSize,min_mass,max_mass,fiducial_density,
|
||||||
|
M1,alpha,seed,verbose=False):
|
||||||
|
|
||||||
|
problematic_cases=0 #number of problematic cases (e.g. halos with Rvir=0.0)
|
||||||
|
thres=1e-3 #controls the max relative error to accept a galaxy density
|
||||||
|
|
||||||
|
##### COMPUTE Mmin GIVEN M1 & alpha #####
|
||||||
|
i=0; max_iterations=20 #maximum number of iterations
|
||||||
|
Mmin1=min_mass; Mmin2=max_mass
|
||||||
|
while (i<max_iterations):
|
||||||
|
Mmin=0.5*(Mmin1+Mmin2) #estimation of the HOD parameter Mmin
|
||||||
|
|
||||||
|
total_galaxies=0
|
||||||
|
inside=np.where(halo_mass>Mmin)[0]
|
||||||
|
mass=halo_mass[inside] #only halos with M>Mmin have central/satellites
|
||||||
|
|
||||||
|
total_galaxies=mass.shape[0]+np.sum((mass/M1)**alpha)
|
||||||
|
mean_density=total_galaxies*1.0/BoxSize**3
|
||||||
|
|
||||||
|
if (np.absolute((mean_density-fiducial_density)/fiducial_density)<thres):
|
||||||
|
i=max_iterations
|
||||||
|
elif (mean_density>fiducial_density):
|
||||||
|
Mmin1=Mmin
|
||||||
|
else:
|
||||||
|
Mmin2=Mmin
|
||||||
|
i+=1
|
||||||
|
|
||||||
|
if verbose:
|
||||||
|
print ' '
|
||||||
|
print 'Mmin=',Mmin
|
||||||
|
print 'average number of galaxies=',total_galaxies
|
||||||
|
print 'average galaxy density=',mean_density
|
||||||
|
#########################################
|
||||||
|
|
||||||
|
#just halos with M>Mmin; the rest do not host central/satellite galaxies
|
||||||
|
inside=np.where(halo_mass>Mmin)[0]
|
||||||
|
halo_mass=halo_mass[inside]
|
||||||
|
halo_pos=halo_pos[inside]
|
||||||
|
halo_radius=halo_radius[inside]
|
||||||
|
halo_len=halo_len[inside]
|
||||||
|
halo_offset=halo_offset[inside]
|
||||||
|
del inside
|
||||||
|
|
||||||
|
#compute number of satellites in each halo using the Poisson distribution
|
||||||
|
np.random.seed(seed) #this is just to check convergence on w_p(r_p)
|
||||||
|
N_mean_sat=(halo_mass/M1)**alpha #mean number of satellites
|
||||||
|
N_sat=np.empty(len(N_mean_sat),dtype=np.int32)
|
||||||
|
for i in range(len(N_sat)):
|
||||||
|
N_sat[i]=np.random.poisson(N_mean_sat[i])
|
||||||
|
N_tot=np.sum(N_sat)+len(halo_mass) #total number of galaxies in the catalogue
|
||||||
|
|
||||||
|
if verbose:
|
||||||
|
print ' '
|
||||||
|
print np.min(halo_mass),'< M_halo <',np.max(halo_mass)
|
||||||
|
print 'total number of galaxies=',N_tot
|
||||||
|
print 'galaxy number density=',N_tot/BoxSize**3
|
||||||
|
|
||||||
|
#put satellites following the distribution of dark matter in groups
|
||||||
|
if verbose:
|
||||||
|
print ' '
|
||||||
|
print 'Creating mock catalogue ...',
|
||||||
|
|
||||||
|
pos_galaxies=np.empty((N_tot,3),dtype=np.float32)
|
||||||
|
#index: variable that go through halos (may be several galaxies in a halo)
|
||||||
|
#i: variable that go through galaxies
|
||||||
|
#count: find number of galaxies that lie beyond its host halo virial radius
|
||||||
|
random.seed(seed) #this is just to check convergence on w_p(r_p)
|
||||||
|
index=0; count=0; i=0
|
||||||
|
while (index<halo_mass.size):
|
||||||
|
|
||||||
|
position=halo_pos[index] #position of the DM halo
|
||||||
|
radius=halo_radius[index] #radius of the DM halo
|
||||||
|
|
||||||
|
#save the position of the central galaxy
|
||||||
|
pos_galaxies[i]=position; i+=1
|
||||||
|
|
||||||
|
#if halo contains satellites, save their positions
|
||||||
|
Nsat=N_sat[index]
|
||||||
|
if Nsat>0:
|
||||||
|
offset=halo_offset[index]
|
||||||
|
length=halo_len[index]
|
||||||
|
idss=sorted_ids[IDs[offset:offset+length]]
|
||||||
|
|
||||||
|
#compute the radius of those particles and keep those with R<Rvir
|
||||||
|
pos=DM_pos[idss]
|
||||||
|
posc=pos-position
|
||||||
|
|
||||||
|
#this is to populate correctly halos closer to box boundaries
|
||||||
|
if np.any((position+radius>BoxSize) + (position-radius<0.0)):
|
||||||
|
|
||||||
|
inside=np.where(posc[:,0]>BoxSize/2.0)[0]
|
||||||
|
posc[inside,0]-=BoxSize
|
||||||
|
inside=np.where(posc[:,0]<-BoxSize/2.0)[0]
|
||||||
|
posc[inside,0]+=BoxSize
|
||||||
|
|
||||||
|
inside=np.where(posc[:,1]>BoxSize/2.0)[0]
|
||||||
|
posc[inside,1]-=BoxSize
|
||||||
|
inside=np.where(posc[:,1]<-BoxSize/2.0)[0]
|
||||||
|
posc[inside,1]+=BoxSize
|
||||||
|
|
||||||
|
inside=np.where(posc[:,2]>BoxSize/2.0)[0]
|
||||||
|
posc[inside,2]-=BoxSize
|
||||||
|
inside=np.where(posc[:,2]<-BoxSize/2.0)[0]
|
||||||
|
posc[inside,2]+=BoxSize
|
||||||
|
|
||||||
|
radii=np.sqrt(posc[:,0]**2+posc[:,1]**2+posc[:,2]**2)
|
||||||
|
inside=np.where(radii<radius)[0]
|
||||||
|
if len(inside)<Nsat:
|
||||||
|
problematic_cases+=1
|
||||||
|
print 'problematic case',len(inside),Nsat
|
||||||
|
else:
|
||||||
|
selected=random.sample(inside,Nsat)
|
||||||
|
pos=pos[selected]
|
||||||
|
|
||||||
|
#aditional, not esential check. Can be comment out
|
||||||
|
#posc=pos-position
|
||||||
|
#if np.any((posc>BoxSize/2.0) + (posc<-BoxSize/2.0)):
|
||||||
|
# inside=np.where(posc[:,0]>BoxSize/2.0)[0]
|
||||||
|
# posc[inside,0]-=BoxSize
|
||||||
|
# inside=np.where(posc[:,0]<-BoxSize/2.0)[0]
|
||||||
|
# posc[inside,0]+=BoxSize
|
||||||
|
|
||||||
|
# inside=np.where(posc[:,1]>BoxSize/2.0)[0]
|
||||||
|
# posc[inside,1]-=BoxSize
|
||||||
|
# inside=np.where(posc[:,1]<-BoxSize/2.0)[0]
|
||||||
|
# posc[inside,1]+=BoxSize
|
||||||
|
|
||||||
|
# inside=np.where(posc[:,2]>BoxSize/2.0)[0]
|
||||||
|
# posc[inside,2]-=BoxSize
|
||||||
|
# inside=np.where(posc[:,2]<-BoxSize/2.0)[0]
|
||||||
|
# posc[inside,2]+=BoxSize
|
||||||
|
#r_max=np.max(np.sqrt(posc[:,0]**2+posc[:,1]**2+posc[:,2]**2))
|
||||||
|
#if r_max>radius: #check no particles beyond Rv selected
|
||||||
|
# print position
|
||||||
|
# print radius
|
||||||
|
# print pos
|
||||||
|
# count+=1
|
||||||
|
|
||||||
|
for j in range(Nsat):
|
||||||
|
pos_galaxies[i]=pos[j]; i+=1
|
||||||
|
index+=1
|
||||||
|
|
||||||
|
if verbose:
|
||||||
|
print 'done'
|
||||||
|
#some final checks
|
||||||
|
if i!=N_tot:
|
||||||
|
print 'some galaxies missing:'
|
||||||
|
print 'register',i,'galaxies out of',N_tot
|
||||||
|
if count>0:
|
||||||
|
print 'error:',count,'particles beyond the virial radius selected'
|
||||||
|
|
||||||
|
return pos_galaxies
|
||||||
|
###############################################################################
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
##### example of use #####
|
||||||
|
"""
|
||||||
|
snapshot_fname='/data1/villa/b500p512nu0.6z99np1024tree/snapdir_017/snap_017'
|
||||||
|
groups_fname='/home/villa/data1/b500p512nu0.6z99np1024tree'
|
||||||
|
groups_number=17
|
||||||
|
|
||||||
|
### HALO CATALOGUE PARAMETERS ###
|
||||||
|
mass_criteria='t200'
|
||||||
|
min_mass=2e12 #Msun/h
|
||||||
|
max_mass=2e15 #Msun/h
|
||||||
|
|
||||||
|
### HOD PARAMETERS ###
|
||||||
|
fiducial_density=0.00111 #mean number density for galaxies with Mr<-21
|
||||||
|
M1=8e13
|
||||||
|
alpha=1.4
|
||||||
|
|
||||||
|
pos=hod(snapshot_fname,groups_fname,groups_number,min_mass,max_mass,fiducial_density,M1,alpha,mass_criteria,verbose=True)
|
||||||
|
|
||||||
|
print pos
|
||||||
|
"""
|
276
python_tools/fit_hod/HOD_parameters.py
Normal file
276
python_tools/fit_hod/HOD_parameters.py
Normal file
|
@ -0,0 +1,276 @@
|
||||||
|
#LATEST MODIFICATION: 10/11/2013
|
||||||
|
#This code computes the Xi^2 for a set of different HOD parameters
|
||||||
|
|
||||||
|
#to generate always the same results for a particular value of M1 & alpha
|
||||||
|
#edit the HOD_library.py code and comment out the lines with the seeds
|
||||||
|
|
||||||
|
#the range over which M1 and alpha wants to be varied has to be specified
|
||||||
|
#below: not in the INPUT
|
||||||
|
|
||||||
|
#Be careful with the IDs. In Gadget the IDs start from 1 whereas when we sort
|
||||||
|
#them the first one will be 0, for instance:
|
||||||
|
#import numpy as np
|
||||||
|
#a=np.array([1,2,8,5,4,9,6,3,7])
|
||||||
|
#b=a.argsort(axis=0)
|
||||||
|
#b
|
||||||
|
#array([0, 1, 7, 4, 3, 6, 8, 2, 5])
|
||||||
|
#i.e. b[1] will return 1, whereas it should be 0
|
||||||
|
|
||||||
|
from mpi4py import MPI
|
||||||
|
import numpy as np
|
||||||
|
import scipy.integrate as si
|
||||||
|
import snap_chooser as SC
|
||||||
|
import readsnap
|
||||||
|
import readsubf
|
||||||
|
import HOD_library as HOD
|
||||||
|
import correlation_function_library as CF
|
||||||
|
import sys
|
||||||
|
import os
|
||||||
|
import random
|
||||||
|
|
||||||
|
#function used to compute wp(rp): d(wp) / dr = 2r*xi(r) / sqrt(r^2-rp^2)
|
||||||
|
def deriv(y,x,r,xi,rp):
|
||||||
|
value=2.0*x*np.interp(x,r,xi)/np.sqrt(x**2-rp**2)
|
||||||
|
return np.array([value])
|
||||||
|
|
||||||
|
|
||||||
|
###### MPI DEFINITIONS ######
|
||||||
|
comm=MPI.COMM_WORLD
|
||||||
|
nprocs=comm.Get_size()
|
||||||
|
myrank=comm.Get_rank()
|
||||||
|
|
||||||
|
########################### INPUT ###############################
|
||||||
|
if len(sys.argv)>1:
|
||||||
|
sa=sys.argv
|
||||||
|
|
||||||
|
snapshot_fname=sa[1]; groups_fname=sa[2]; groups_number=sa[3]
|
||||||
|
|
||||||
|
mass_criteria=sa[4]; min_mass=float(sa[5]); max_mass=float(sa[6])
|
||||||
|
|
||||||
|
fiducial_density=float(sa[7])
|
||||||
|
M1_min=float(sa[8]); M1_max=float(sa[9]); M1_bins=int(sa[10]);
|
||||||
|
alpha_min=float(sa[11]); alpha_max=float(sa[12]); alpha_bins=int(sa[13])
|
||||||
|
|
||||||
|
random_file=sa[14]
|
||||||
|
|
||||||
|
BoxSize=float(sa[15])
|
||||||
|
Rmin=float(sa[16]); Rmax=float(sa[17]); bins=int(sa[18])
|
||||||
|
|
||||||
|
DD_name=sa[19]; RR_name=sa[20]; DR_name=sa[21]
|
||||||
|
DD_action=sa[22]; RR_action=sa[23]; DR_action=sa[24]
|
||||||
|
|
||||||
|
wp_file=sa[25]; results_file=sa[26]
|
||||||
|
|
||||||
|
else:
|
||||||
|
#### SNAPSHOTS TO SELECT GALAXIES WITHIN CDM HALOS ####
|
||||||
|
snapshot_fname='../../snapdir_003/snap_003'
|
||||||
|
groups_fname='../../'
|
||||||
|
groups_number=3
|
||||||
|
|
||||||
|
#### HALO CATALOGUE PARAMETERS ####
|
||||||
|
mass_criteria='m200' #'t200' 'm200' or 'c200'
|
||||||
|
min_mass=3e10 #Msun/h
|
||||||
|
max_mass=2e15 #Msun/h
|
||||||
|
|
||||||
|
### HOD PARAMETERS ###
|
||||||
|
fiducial_density=0.00111 #mean number density for galaxies with Mr<-21
|
||||||
|
#M1_min=6.0e13; M1_max=1.0e14; M1_bins=20
|
||||||
|
#alpha_min=1.05; alpha_max=1.60; alpha_bins=20
|
||||||
|
|
||||||
|
M1_min=6.9e+13; M1_max= 6.9e+13; M1_bins=100
|
||||||
|
alpha_min=1.20; alpha_max=1.20; alpha_bins=100
|
||||||
|
|
||||||
|
#### RANDOM CATALOG ####
|
||||||
|
random_file='/home/villa/disksom2/Correlation_function/Random_catalogue/random_catalogue_4e5.dat'
|
||||||
|
|
||||||
|
#### PARAMETERS ####
|
||||||
|
BoxSize=500.0 #Mpc/h
|
||||||
|
Rmin=0.1 #Mpc/h
|
||||||
|
Rmax=75.0 #Mpc/h
|
||||||
|
bins=60
|
||||||
|
|
||||||
|
#### PARTIAL RESULTS NAMES ####
|
||||||
|
DD_name='DD.dat' #name for the file containing DD results
|
||||||
|
RR_name='../RR_0.1_75_60_4e5.dat' #name for the file containing RR results
|
||||||
|
DR_name='DR.dat' #name for the file containing DR results
|
||||||
|
|
||||||
|
#### ACTIONS ####
|
||||||
|
DD_action='compute' #'compute' or 'read' (from DD_name file)
|
||||||
|
RR_action='read' #'compute' or 'read' (from RR_name file)
|
||||||
|
DR_action='compute' #'compute' or 'read' (from DR_name file)
|
||||||
|
|
||||||
|
#### wp FILE ####
|
||||||
|
wp_file='../w_p_21.dat'
|
||||||
|
wp_covariance_file='../wp_covar_21.0.dat'
|
||||||
|
|
||||||
|
#### OUTPUT ####
|
||||||
|
results_file='borrar.dat'
|
||||||
|
######################################################
|
||||||
|
|
||||||
|
if myrank==0:
|
||||||
|
|
||||||
|
#read positions and IDs of DM particles: sort the IDs array
|
||||||
|
DM_pos=readsnap.read_block(snapshot_fname,"POS ",parttype=-1)
|
||||||
|
#IDs should go from 0 to N-1, instead from 1 to N
|
||||||
|
DM_ids=readsnap.read_block(snapshot_fname,"ID ",parttype=-1)-1
|
||||||
|
if np.min(DM_ids)!=0 or np.max(DM_ids)!=(len(DM_pos)-1):
|
||||||
|
print 'Error!!!!'
|
||||||
|
print 'IDs should go from 0 to N-1'
|
||||||
|
print len(DM_ids),np.min(DM_ids),np.max(DM_ids)
|
||||||
|
sorted_ids=DM_ids.argsort(axis=0)
|
||||||
|
del DM_ids
|
||||||
|
#the particle whose ID is N is located in the position sorted_ids[N]
|
||||||
|
#i.e. DM_ids[sorted_ids[N]]=N
|
||||||
|
#the position of the particle whose ID is N would be:
|
||||||
|
#DM_pos[sorted_ids[N]]
|
||||||
|
|
||||||
|
#read the IDs of the particles belonging to the CDM halos
|
||||||
|
#again the IDs should go from 0 to N-1
|
||||||
|
halos_ID=readsubf.subf_ids(groups_fname,groups_number,0,0,
|
||||||
|
long_ids=True,read_all=True)
|
||||||
|
IDs=halos_ID.SubIDs-1
|
||||||
|
del halos_ID
|
||||||
|
|
||||||
|
print 'subhalos IDs=',np.min(IDs),np.max(IDs)
|
||||||
|
|
||||||
|
#read CDM halos information
|
||||||
|
halos=readsubf.subfind_catalog(groups_fname,groups_number,
|
||||||
|
group_veldisp=True,masstab=True,
|
||||||
|
long_ids=True,swap=False)
|
||||||
|
if mass_criteria=='t200':
|
||||||
|
halos_mass=halos.group_m_tophat200*1e10 #masses in Msun/h
|
||||||
|
halos_radius=halos.group_r_tophat200 #radius in kpc/h
|
||||||
|
elif mass_criteria=='m200':
|
||||||
|
halos_mass=halos.group_m_mean200*1e10 #masses in Msun/h
|
||||||
|
halos_radius=halos.group_r_mean200 #radius in kpc/h
|
||||||
|
elif mass_criteria=='c200':
|
||||||
|
halos_mass=halos.group_m_crit200*1e10 #masses in Msun/h
|
||||||
|
halos_radius=halos.group_r_crit200 #radius in kpc/h
|
||||||
|
else:
|
||||||
|
print 'bad mass_criteria'
|
||||||
|
sys.exit()
|
||||||
|
halos_pos=halos.group_pos
|
||||||
|
halos_len=halos.group_len
|
||||||
|
halos_offset=halos.group_offset
|
||||||
|
halos_indexes=np.where((halos_mass>min_mass) & (halos_mass<max_mass))[0]
|
||||||
|
del halos
|
||||||
|
|
||||||
|
print ' '
|
||||||
|
print 'total halos found=',len(halos_pos)
|
||||||
|
print 'halos number density=',len(halos_pos)/BoxSize**3
|
||||||
|
|
||||||
|
#keep only the halos in the given mass range
|
||||||
|
halo_mass=halos_mass[halos_indexes]
|
||||||
|
halo_pos=halos_pos[halos_indexes]
|
||||||
|
halo_radius=halos_radius[halos_indexes]
|
||||||
|
halo_len=halos_len[halos_indexes]
|
||||||
|
halo_offset=halos_offset[halos_indexes]
|
||||||
|
del halos_indexes
|
||||||
|
|
||||||
|
if np.any(halo_len==[]):
|
||||||
|
print 'something bad'
|
||||||
|
|
||||||
|
#read the random catalogue (new version)
|
||||||
|
dt=np.dtype((np.float32,3))
|
||||||
|
pos_r=np.fromfile(random_file,dtype=dt)*BoxSize #Mpc/h
|
||||||
|
|
||||||
|
#read the wp file
|
||||||
|
f=open(wp_file,'r'); wp=[]
|
||||||
|
for line in f.readlines():
|
||||||
|
a=line.split()
|
||||||
|
wp.append([float(a[0]),float(a[1]),float(a[2])])
|
||||||
|
f.close(); wp=np.array(wp)
|
||||||
|
|
||||||
|
#read covariance matrix file
|
||||||
|
f=open(wp_covariance_file,'r')
|
||||||
|
Cov=[]
|
||||||
|
for line in f.readlines():
|
||||||
|
a=line.split()
|
||||||
|
for value in a:
|
||||||
|
Cov.append(float(value))
|
||||||
|
f.close(); Cov=np.array(Cov)
|
||||||
|
if len(Cov)!=len(wp)**2:
|
||||||
|
print 'problem with point numbers in the covariance file'
|
||||||
|
sys.exit()
|
||||||
|
Cov=np.reshape(Cov,(len(wp),len(wp)))
|
||||||
|
Cov=np.matrix(Cov)
|
||||||
|
|
||||||
|
for g in range(100):
|
||||||
|
|
||||||
|
##### MASTER #####
|
||||||
|
if myrank==0:
|
||||||
|
|
||||||
|
#set here the range of M1, alpha to vary
|
||||||
|
#print 'M1='; M1=float(raw_input())
|
||||||
|
#print 'alpha='; alpha=float(raw_input())
|
||||||
|
|
||||||
|
#M1=1.0e14+0.4e14*np.random.random()
|
||||||
|
#alpha=1.10+0.3*np.random.random()
|
||||||
|
#seed=np.random.randint(0,3000,1)[0]
|
||||||
|
|
||||||
|
M1=1.15e14
|
||||||
|
alpha=1.27
|
||||||
|
seed=955
|
||||||
|
|
||||||
|
#create the galaxy catalogue through the HOD parameters
|
||||||
|
pos_g=HOD.hod_fast(DM_pos,sorted_ids,IDs,halo_mass,halo_pos,
|
||||||
|
halo_radius,halo_len,halo_offset,BoxSize,
|
||||||
|
min_mass,max_mass,fiducial_density,M1,
|
||||||
|
alpha,seed,verbose=True)/1e3
|
||||||
|
|
||||||
|
#compute the 2pt correlation function
|
||||||
|
r,xi_r,error_xi=CF.TPCF(pos_g,pos_r,BoxSize,DD_action,
|
||||||
|
RR_action,DR_action,DD_name,RR_name,
|
||||||
|
DR_name,bins,Rmin,Rmax)
|
||||||
|
|
||||||
|
f=open('correlation_function.dat','w')
|
||||||
|
for i in range(len(r)):
|
||||||
|
f.write(str(r[i])+' '+str(xi_r[i])+' '+str(error_xi[i])+'\n')
|
||||||
|
f.close()
|
||||||
|
|
||||||
|
r_max=np.max(r)
|
||||||
|
h=1e-13 #discontinuity at r=rp. We integrate from r=rp+h to r_max
|
||||||
|
yinit=np.array([0.0])
|
||||||
|
|
||||||
|
f=open('projected_correlation_function.dat','w')
|
||||||
|
wp_HOD=[]
|
||||||
|
for rp in wp[:,0]:
|
||||||
|
x=np.array([rp+h,r_max])
|
||||||
|
y=si.odeint(deriv,yinit,x,args=(r,xi_r,rp),mxstep=100000)
|
||||||
|
wp_HOD.append(y[1][0])
|
||||||
|
f.write(str(rp)+' '+str(y[1][0])+'\n')
|
||||||
|
wp_HOD=np.array(wp_HOD)
|
||||||
|
f.close()
|
||||||
|
|
||||||
|
print 'M1=',M1
|
||||||
|
print 'alpha=',alpha
|
||||||
|
|
||||||
|
chi2_bins=(wp_HOD-wp[:,1])**2/wp[:,2]**2
|
||||||
|
|
||||||
|
for min_bin in [2]:
|
||||||
|
for max_bin in [12]:
|
||||||
|
elements=np.arange(min_bin,max_bin)
|
||||||
|
|
||||||
|
#X^2 without covariance matrix
|
||||||
|
chi2_nocov=np.sum(chi2_bins[elements])
|
||||||
|
|
||||||
|
#X^2 with covariance matrix
|
||||||
|
wp_aux=wp[elements,1]; wp_HOD_aux=wp_HOD[elements]
|
||||||
|
Cov_aux=Cov[elements,:][:,elements]
|
||||||
|
diff=np.matrix(wp_HOD_aux-wp_aux)
|
||||||
|
chi2=diff*Cov_aux.I*diff.T
|
||||||
|
|
||||||
|
print 'X2('+str(min_bin)+'-'+str(max_bin)+')=',chi2_nocov,chi2
|
||||||
|
g=open(results_file,'a')
|
||||||
|
g.write(str(M1)+ ' '+str(alpha)+' '+str(seed)+' '+str(chi2)+'\n')
|
||||||
|
g.close()
|
||||||
|
|
||||||
|
|
||||||
|
##### SLAVES #####
|
||||||
|
else:
|
||||||
|
pos_g=None; pos_r=None
|
||||||
|
CF.TPCF(pos_g,pos_r,BoxSize,DD_action,RR_action,DR_action,
|
||||||
|
DD_name,RR_name,DR_name,bins,Rmin,Rmax)
|
||||||
|
|
||||||
|
|
||||||
|
|
773
python_tools/fit_hod/correlation_function_library.py
Normal file
773
python_tools/fit_hod/correlation_function_library.py
Normal file
|
@ -0,0 +1,773 @@
|
||||||
|
#Version 1.1
|
||||||
|
#LATEST MODIFICATION: 15/05/2013
|
||||||
|
#This file contains the functions needed to compute:
|
||||||
|
#1)-the 2pt correlation function
|
||||||
|
#2)-the 2pt cross-correlation function
|
||||||
|
from mpi4py import MPI
|
||||||
|
import numpy as np
|
||||||
|
import scipy.weave as wv
|
||||||
|
import sys,os
|
||||||
|
import time
|
||||||
|
|
||||||
|
###### MPI DEFINITIONS ######
|
||||||
|
comm=MPI.COMM_WORLD
|
||||||
|
nprocs=comm.Get_size()
|
||||||
|
myrank=comm.Get_rank()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
################################################################################
|
||||||
|
#This functions computes the TPCF (2pt correlation function)
|
||||||
|
#from an N-body simulation. It takes into account boundary conditions
|
||||||
|
#VARIABLES:
|
||||||
|
#pos_g: array containing the positions of the galaxies
|
||||||
|
#pos_r: array containing the positions of the random particles catalogue
|
||||||
|
#BoxSize: Size of the Box. Units must be equal to those of pos_r/pos_g
|
||||||
|
#DD_action: compute number of galaxy pairs from data or read them---compute/read
|
||||||
|
#RR_action: compute number of random pairs from data or read them---compute/read
|
||||||
|
#DR_action: compute number of galaxy-random pairs or read them---compute/read
|
||||||
|
#DD_name: file name to write/read galaxy-galaxy pairs results
|
||||||
|
#RR_name: file name to write/read random-random pairs results
|
||||||
|
#DR_name: file name to write/read galaxy-random pairs results
|
||||||
|
#bins: number of bins to compute the 2pt correlation function
|
||||||
|
#Rmin: minimum radius to compute the 2pt correlation function
|
||||||
|
#Rmax: maximum radius to compute the 2pt correlation function
|
||||||
|
#USAGE: at the end of the file there is a example of how to use this function
|
||||||
|
def TPCF(pos_g,pos_r,BoxSize,DD_action,RR_action,DR_action,
|
||||||
|
DD_name,RR_name,DR_name,bins,Rmin,Rmax,verbose=False):
|
||||||
|
|
||||||
|
#dims determined requiring that no more 8 adyacent subboxes will be taken
|
||||||
|
dims=int(BoxSize/Rmax)
|
||||||
|
dims2=dims**2; dims3=dims**3
|
||||||
|
|
||||||
|
##### MASTER #####
|
||||||
|
if myrank==0:
|
||||||
|
|
||||||
|
#compute the indexes of the halo/subhalo/galaxy catalogue
|
||||||
|
Ng=len(pos_g)*1.0; indexes_g=[]
|
||||||
|
coord=np.floor(dims*pos_g/BoxSize).astype(np.int32)
|
||||||
|
index=dims2*coord[:,0]+dims*coord[:,1]+coord[:,2]
|
||||||
|
for i in range(dims3):
|
||||||
|
ids=np.where(index==i)[0]
|
||||||
|
indexes_g.append(ids)
|
||||||
|
indexes_g=np.array(indexes_g)
|
||||||
|
|
||||||
|
#compute the indexes of the random catalogue
|
||||||
|
Nr=len(pos_r)*1.0; indexes_r=[]
|
||||||
|
coord=np.floor(dims*pos_r/BoxSize).astype(np.int32)
|
||||||
|
index=dims2*coord[:,0]+dims*coord[:,1]+coord[:,2]
|
||||||
|
for i in range(dims3):
|
||||||
|
ids=np.where(index==i)[0]
|
||||||
|
indexes_r.append(ids)
|
||||||
|
indexes_r=np.array(indexes_r)
|
||||||
|
|
||||||
|
|
||||||
|
#compute galaxy-galaxy pairs: DD
|
||||||
|
if DD_action=='compute':
|
||||||
|
DD=DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,indexes1=indexes_g,
|
||||||
|
indexes2=None,pos1=pos_g,pos2=None)
|
||||||
|
if verbose:
|
||||||
|
print DD
|
||||||
|
print np.sum(DD)
|
||||||
|
#write results to a file
|
||||||
|
write_results(DD_name,DD,bins,'radial')
|
||||||
|
else:
|
||||||
|
#read results from a file
|
||||||
|
DD,bins_aux=read_results(DD_name,'radial')
|
||||||
|
if bins_aux!=bins:
|
||||||
|
print 'Sizes are different!'
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
#compute random-random pairs: RR
|
||||||
|
if RR_action=='compute':
|
||||||
|
RR=DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,indexes1=indexes_r,
|
||||||
|
indexes2=None,pos1=pos_r,pos2=None)
|
||||||
|
if verbose:
|
||||||
|
print RR
|
||||||
|
print np.sum(RR)
|
||||||
|
#write results to a file
|
||||||
|
write_results(RR_name,RR,bins,'radial')
|
||||||
|
else:
|
||||||
|
#read results from a file
|
||||||
|
RR,bins_aux=read_results(RR_name,'radial')
|
||||||
|
if bins_aux!=bins:
|
||||||
|
print 'Sizes are different!'
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
#compute galaxy-random pairs: DR
|
||||||
|
if DR_action=='compute':
|
||||||
|
DR=DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,indexes1=indexes_g,
|
||||||
|
indexes2=indexes_r,pos1=pos_g,pos2=pos_r)
|
||||||
|
if verbose:
|
||||||
|
print DR
|
||||||
|
print np.sum(DR)
|
||||||
|
#write results to a file
|
||||||
|
write_results(DR_name,DR,bins,'radial')
|
||||||
|
else:
|
||||||
|
#read results from a file
|
||||||
|
DR,bins_aux=read_results(DR_name,'radial')
|
||||||
|
if bins_aux!=bins:
|
||||||
|
print 'Sizes are different!'
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
|
||||||
|
#final procesing
|
||||||
|
bins_histo=np.logspace(np.log10(Rmin),np.log10(Rmax),bins+1)
|
||||||
|
middle=0.5*(bins_histo[:-1]+bins_histo[1:])
|
||||||
|
DD*=1.0; RR*=1.0; DR*=1.0
|
||||||
|
|
||||||
|
r,xi_r,error_xi_r=[],[],[]
|
||||||
|
for i in range(bins):
|
||||||
|
if (RR[i]>0.0): #avoid divisions by 0
|
||||||
|
xi_aux,error_xi_aux=xi(DD[i],RR[i],DR[i],Ng,Nr)
|
||||||
|
r.append(middle[i])
|
||||||
|
xi_r.append(xi_aux)
|
||||||
|
error_xi_r.append(error_xi_aux)
|
||||||
|
|
||||||
|
r=np.array(r)
|
||||||
|
xi_r=np.array(xi_r)
|
||||||
|
error_xi_r=np.array(error_xi_r)
|
||||||
|
|
||||||
|
return r,xi_r,error_xi_r
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
##### SLAVES #####
|
||||||
|
else:
|
||||||
|
if DD_action=='compute':
|
||||||
|
DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,
|
||||||
|
indexes1=None,indexes2=None,pos1=None,pos2=None)
|
||||||
|
if RR_action=='compute':
|
||||||
|
DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,
|
||||||
|
indexes1=None,indexes2=None,pos1=None,pos2=None)
|
||||||
|
if DR_action=='compute':
|
||||||
|
DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,
|
||||||
|
indexes1=None,indexes2=None,pos1=None,pos2=None)
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
################################################################################
|
||||||
|
#This functions computes the TPCCF (2pt cross-correlation function)
|
||||||
|
#from an N-body simulation. It takes into account boundary conditions
|
||||||
|
#VARIABLES:
|
||||||
|
#pos_g1: array containing the positions of the galaxies1
|
||||||
|
#pos_g2: array containing the positions of the galaxies2
|
||||||
|
#pos_r: array containing the positions of the random particles catalogue
|
||||||
|
#BoxSize: Size of the Box. Units must be equal to those of pos_r/pos_g1/pos_g2
|
||||||
|
#DD_action: compute number of galaxy pairs from data or read them---compute/read
|
||||||
|
#RR_action: compute number of random pairs from data or read them---compute/read
|
||||||
|
#DR_action: compute number of galaxy-random pairs or read them---compute/read
|
||||||
|
#DD_name: file name to write/read galaxy-galaxy pairs results
|
||||||
|
#RR_name: file name to write/read random-random pairs results
|
||||||
|
#DR_name: file name to write/read galaxy-random pairs results
|
||||||
|
#bins: number of bins to compute the 2pt correlation function
|
||||||
|
#Rmin: minimum radius to compute the 2pt correlation function
|
||||||
|
#Rmax: maximum radius to compute the 2pt correlation function
|
||||||
|
#USAGE: at the end of the file there is a example of how to use this function
|
||||||
|
def TPCCF(pos_g1,pos_g2,pos_r,BoxSize,
|
||||||
|
D1D2_action,D1R_action,D2R_action,RR_action,
|
||||||
|
D1D2_name,D1R_name,D2R_name,RR_name,
|
||||||
|
bins,Rmin,Rmax,verbose=False):
|
||||||
|
|
||||||
|
|
||||||
|
#dims determined requiring that no more 8 adyacent subboxes will be taken
|
||||||
|
dims=int(BoxSize/Rmax)
|
||||||
|
dims2=dims**2; dims3=dims**3
|
||||||
|
|
||||||
|
##### MASTER #####
|
||||||
|
if myrank==0:
|
||||||
|
|
||||||
|
#compute the indexes of the halo1/subhalo1/galaxy1 catalogue
|
||||||
|
Ng1=len(pos_g1)*1.0; indexes_g1=[]
|
||||||
|
coord=np.floor(dims*pos_g1/BoxSize).astype(np.int32)
|
||||||
|
index=dims2*coord[:,0]+dims*coord[:,1]+coord[:,2]
|
||||||
|
for i in range(dims3):
|
||||||
|
ids=np.where(index==i)[0]
|
||||||
|
indexes_g1.append(ids)
|
||||||
|
indexes_g1=np.array(indexes_g1)
|
||||||
|
|
||||||
|
#compute the indexes of the halo2/subhalo2/galaxy2 catalogue
|
||||||
|
Ng2=len(pos_g2)*1.0; indexes_g2=[]
|
||||||
|
coord=np.floor(dims*pos_g2/BoxSize).astype(np.int32)
|
||||||
|
index=dims2*coord[:,0]+dims*coord[:,1]+coord[:,2]
|
||||||
|
for i in range(dims3):
|
||||||
|
ids=np.where(index==i)[0]
|
||||||
|
indexes_g2.append(ids)
|
||||||
|
indexes_g2=np.array(indexes_g2)
|
||||||
|
|
||||||
|
#compute the indexes of the random catalogue
|
||||||
|
Nr=len(pos_r)*1.0; indexes_r=[]
|
||||||
|
coord=np.floor(dims*pos_r/BoxSize).astype(np.int32)
|
||||||
|
index=dims2*coord[:,0]+dims*coord[:,1]+coord[:,2]
|
||||||
|
for i in range(dims3):
|
||||||
|
ids=np.where(index==i)[0]
|
||||||
|
indexes_r.append(ids)
|
||||||
|
indexes_r=np.array(indexes_r)
|
||||||
|
|
||||||
|
|
||||||
|
#compute galaxy1-galaxy2 pairs: D1D2
|
||||||
|
if D1D2_action=='compute':
|
||||||
|
D1D2=DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,indexes1=indexes_g1,
|
||||||
|
indexes2=indexes_g2,pos1=pos_g1,pos2=pos_g2)
|
||||||
|
if verbose:
|
||||||
|
print D1D2
|
||||||
|
print np.sum(D1D2)
|
||||||
|
#write results to a file
|
||||||
|
write_results(D1D2_name,D1D2,bins,'radial')
|
||||||
|
else:
|
||||||
|
#read results from a file
|
||||||
|
D1D2,bins_aux=read_results(D1D2_name,'radial')
|
||||||
|
if bins_aux!=bins:
|
||||||
|
print 'Sizes are different!'
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
#compute galaxy1-random pairs: D1R
|
||||||
|
if D1R_action=='compute':
|
||||||
|
D1R=DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,indexes1=indexes_g1,
|
||||||
|
indexes2=indexes_r,pos1=pos_g1,pos2=pos_r)
|
||||||
|
if verbose:
|
||||||
|
print D1R
|
||||||
|
print np.sum(D1R)
|
||||||
|
#write results to a file
|
||||||
|
write_results(D1R_name,D1R,bins,'radial')
|
||||||
|
else:
|
||||||
|
#read results from a file
|
||||||
|
D1R,bins_aux=read_results(D1R_name,'radial')
|
||||||
|
if bins_aux!=bins:
|
||||||
|
print 'Sizes are different!'
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
#compute galaxy2-random pairs: D2R
|
||||||
|
if D2R_action=='compute':
|
||||||
|
D2R=DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,indexes1=indexes_g2,
|
||||||
|
indexes2=indexes_r,pos1=pos_g2,pos2=pos_r)
|
||||||
|
if verbose:
|
||||||
|
print D2R
|
||||||
|
print np.sum(D2R)
|
||||||
|
#write results to a file
|
||||||
|
write_results(D2R_name,D2R,bins,'radial')
|
||||||
|
else:
|
||||||
|
#read results from a file
|
||||||
|
D2R,bins_aux=read_results(D2R_name,'radial')
|
||||||
|
if bins_aux!=bins:
|
||||||
|
print 'Sizes are different!'
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
#compute random-random pairs: RR
|
||||||
|
if RR_action=='compute':
|
||||||
|
RR=DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,indexes1=indexes_r,
|
||||||
|
indexes2=None,pos1=pos_r,pos2=None)
|
||||||
|
if verbose:
|
||||||
|
print RR
|
||||||
|
print np.sum(RR)
|
||||||
|
#write results to a file
|
||||||
|
write_results(RR_name,RR,bins,'radial')
|
||||||
|
else:
|
||||||
|
#read results from a file
|
||||||
|
RR,bins_aux=read_results(RR_name,'radial')
|
||||||
|
if bins_aux!=bins:
|
||||||
|
print 'Sizes are different!'
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
|
||||||
|
#final procesing
|
||||||
|
bins_histo=np.logspace(np.log10(Rmin),np.log10(Rmax),bins+1)
|
||||||
|
middle=0.5*(bins_histo[:-1]+bins_histo[1:])
|
||||||
|
|
||||||
|
inside=np.where(RR>0)[0]
|
||||||
|
D1D2=D1D2[inside]; D1R=D1R[inside]; D2R=D2R[inside]; RR=RR[inside]
|
||||||
|
middle=middle[inside]
|
||||||
|
|
||||||
|
D1D2n=D1D2*1.0/(Ng1*Ng2)
|
||||||
|
D1Rn=D1R*1.0/(Ng1*Nr)
|
||||||
|
D2Rn=D2R*1.0/(Ng2*Nr)
|
||||||
|
RRn=RR*2.0/(Nr*(Nr-1.0))
|
||||||
|
|
||||||
|
xi_r=D1D2n/RRn-D1Rn/RRn-D2Rn/RRn+1.0
|
||||||
|
|
||||||
|
return middle,xi_r
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
##### SLAVES #####
|
||||||
|
else:
|
||||||
|
if D1D2_action=='compute':
|
||||||
|
DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,
|
||||||
|
indexes1=None,indexes2=None,pos1=None,pos2=None)
|
||||||
|
if D1R_action=='compute':
|
||||||
|
DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,
|
||||||
|
indexes1=None,indexes2=None,pos1=None,pos2=None)
|
||||||
|
if D2R_action=='compute':
|
||||||
|
DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,
|
||||||
|
indexes1=None,indexes2=None,pos1=None,pos2=None)
|
||||||
|
if RR_action=='compute':
|
||||||
|
DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,
|
||||||
|
indexes1=None,indexes2=None,pos1=None,pos2=None)
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
|
||||||
|
################################################################################
|
||||||
|
#This function is used to compute the DD file (the number of random pairs in a
|
||||||
|
#random catalogue) that it is need for massive computation of the 2pt
|
||||||
|
#correlation function
|
||||||
|
#from an N-body simulation. It takes into account boundary conditions
|
||||||
|
#VARIABLES:
|
||||||
|
#pos_r: array containing the positions of the random particles catalogue
|
||||||
|
#BoxSize: Size of the Box. Units must be equal to those of pos_r/pos_g
|
||||||
|
#RR_name: file name to write/read random-random pairs results
|
||||||
|
#bins: number of bins to compute the 2pt correlation function
|
||||||
|
#Rmin: minimum radius to compute the 2pt correlation function
|
||||||
|
#Rmax: maximum radius to compute the 2pt correlation function
|
||||||
|
#USAGE: at the end of the file there is a example of how to use this function
|
||||||
|
def DD_file(pos_r,BoxSize,RR_name,bins,Rmin,Rmax):
|
||||||
|
|
||||||
|
#dims determined requiring that no more 8 adyacent subboxes will be taken
|
||||||
|
dims=int(BoxSize/Rmax)
|
||||||
|
dims2=dims**2; dims3=dims**3
|
||||||
|
|
||||||
|
##### MASTER #####
|
||||||
|
if myrank==0:
|
||||||
|
|
||||||
|
#compute the indexes of the random catalogue
|
||||||
|
Nr=len(pos_r)*1.0; indexes_r=[]
|
||||||
|
coord=np.floor(dims*pos_r/BoxSize).astype(np.int32)
|
||||||
|
index=dims2*coord[:,0]+dims*coord[:,1]+coord[:,2]
|
||||||
|
for i in range(dims3):
|
||||||
|
ids=np.where(index==i)[0]
|
||||||
|
indexes_r.append(ids)
|
||||||
|
indexes_r=np.array(indexes_r)
|
||||||
|
|
||||||
|
#compute random-random pairs: RR
|
||||||
|
RR=DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,indexes1=indexes_r,
|
||||||
|
indexes2=None,pos1=pos_r,pos2=None)
|
||||||
|
print RR
|
||||||
|
print np.sum(RR)
|
||||||
|
#write results to a file
|
||||||
|
write_results(RR_name,RR,bins,'radial')
|
||||||
|
|
||||||
|
##### SLAVES #####
|
||||||
|
else:
|
||||||
|
DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,
|
||||||
|
indexes1=None,indexes2=None,pos1=None,pos2=None)
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
################################################################################
|
||||||
|
####### COMPUTE THE NUMBER OF PAIRS IN A CATALOG ####### (x,y,z) very fast
|
||||||
|
################################################################################
|
||||||
|
def DDR_pairs(bins,Rmin,Rmax,BoxSize,dims,indexes1,indexes2,pos1,pos2):
|
||||||
|
|
||||||
|
dims2=dims**2; dims3=dims**3
|
||||||
|
|
||||||
|
#we put bins+1. The last bin is only for pairs separated by r=Rmax
|
||||||
|
pairs=np.zeros(bins+1,dtype=np.int64)
|
||||||
|
|
||||||
|
##### MASTER #####
|
||||||
|
if myrank==0:
|
||||||
|
#Master sends the indexes and particle positions to the slaves
|
||||||
|
for i in range(1,nprocs):
|
||||||
|
comm.send(pos1,dest=i,tag=6)
|
||||||
|
comm.send(pos2,dest=i,tag=7)
|
||||||
|
comm.send(indexes1,dest=i,tag=8)
|
||||||
|
comm.send(indexes2,dest=i,tag=9)
|
||||||
|
|
||||||
|
#Masters distributes the calculation among slaves
|
||||||
|
for subbox in range(dims3):
|
||||||
|
b=comm.recv(source=MPI.ANY_SOURCE,tag=1)
|
||||||
|
comm.send(False,dest=b,tag=2)
|
||||||
|
comm.send(subbox,dest=b,tag=3)
|
||||||
|
|
||||||
|
#Master gathers partial results from slaves and returns the final result
|
||||||
|
for j in range(1,nprocs):
|
||||||
|
b=comm.recv(source=MPI.ANY_SOURCE,tag=1)
|
||||||
|
comm.send(True,dest=b,tag=2)
|
||||||
|
pairs_aux=comm.recv(source=b,tag=10)
|
||||||
|
pairs+=pairs_aux
|
||||||
|
|
||||||
|
#the last element is just for situations in which r=Rmax
|
||||||
|
pairs[bins-1]+=pairs[bins]
|
||||||
|
|
||||||
|
return pairs[:-1]
|
||||||
|
|
||||||
|
|
||||||
|
##### SLAVES #####
|
||||||
|
else:
|
||||||
|
#position of the center of each subbox
|
||||||
|
sub_c=np.empty(3,dtype=np.float32)
|
||||||
|
|
||||||
|
#slaves receive the positions and indexes
|
||||||
|
pos1=comm.recv(source=0,tag=6)
|
||||||
|
pos2=comm.recv(source=0,tag=7)
|
||||||
|
indexes1=comm.recv(source=0,tag=8)
|
||||||
|
indexes2=comm.recv(source=0,tag=9)
|
||||||
|
|
||||||
|
comm.send(myrank,dest=0,tag=1)
|
||||||
|
final=comm.recv(source=0,tag=2)
|
||||||
|
while not(final):
|
||||||
|
|
||||||
|
subbox=comm.recv(source=0,tag=3)
|
||||||
|
core_ids=indexes1[subbox] #ids of the particles in the subbox
|
||||||
|
pos0=pos1[core_ids]
|
||||||
|
|
||||||
|
sub_c[0]=(subbox/dims2+0.5)*BoxSize/dims
|
||||||
|
sub_c[1]=((subbox%dims2)/dims+0.5)*BoxSize/dims
|
||||||
|
sub_c[2]=((subbox%dims2)%dims+0.5)*BoxSize/dims
|
||||||
|
|
||||||
|
#galaxy-galaxy or random-random case
|
||||||
|
if pos2==None:
|
||||||
|
#first: distances between particles in the same subbox
|
||||||
|
distances_core(pos0,BoxSize,bins,Rmin,Rmax,pairs)
|
||||||
|
|
||||||
|
#second: distances between particles in the subbox and particles around
|
||||||
|
ids=indexes_subbox_neigh(sub_c,Rmax,dims,BoxSize,indexes1,subbox)
|
||||||
|
if ids!=[]:
|
||||||
|
posN=pos1[ids]
|
||||||
|
DR_distances(pos0,posN,BoxSize,bins,Rmin,Rmax,pairs)
|
||||||
|
|
||||||
|
#galaxy-random case
|
||||||
|
else:
|
||||||
|
ids=indexes_subbox(sub_c,Rmax,dims,BoxSize,indexes2)
|
||||||
|
posN=pos2[ids]
|
||||||
|
DR_distances(pos0,posN,BoxSize,bins,Rmin,Rmax,pairs)
|
||||||
|
|
||||||
|
comm.send(myrank,dest=0,tag=1)
|
||||||
|
final=comm.recv(source=0,tag=2)
|
||||||
|
|
||||||
|
print 'cpu ',myrank,' finished: transfering data to master'
|
||||||
|
comm.send(pairs,dest=0,tag=10)
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
|
||||||
|
################################################################################
|
||||||
|
#this function computes the distances between all the particles-pairs and
|
||||||
|
#return the number of pairs found in each distance bin
|
||||||
|
def distances_core(pos,BoxSize,bins,Rmin,Rmax,pairs):
|
||||||
|
|
||||||
|
l=pos.shape[0]
|
||||||
|
|
||||||
|
support = """
|
||||||
|
#include <iostream>
|
||||||
|
using namespace std;
|
||||||
|
"""
|
||||||
|
code = """
|
||||||
|
float middle=BoxSize/2.0;
|
||||||
|
float dx,dy,dz,r;
|
||||||
|
float x1,y1,z1,x2,y2,z2;
|
||||||
|
float delta=log10(Rmax/Rmin)/bins;
|
||||||
|
int bin,i,j;
|
||||||
|
|
||||||
|
for (i=0;i<l;i++){
|
||||||
|
x1=pos(i,0);
|
||||||
|
y1=pos(i,1);
|
||||||
|
z1=pos(i,2);
|
||||||
|
for (j=i+1;j<l;j++){
|
||||||
|
x2=pos(j,0);
|
||||||
|
y2=pos(j,1);
|
||||||
|
z2=pos(j,2);
|
||||||
|
dx=(fabs(x1-x2)<middle) ? x1-x2 : BoxSize-fabs(x1-x2);
|
||||||
|
dy=(fabs(y1-y2)<middle) ? y1-y2 : BoxSize-fabs(y1-y2);
|
||||||
|
dz=(fabs(z1-z2)<middle) ? z1-z2 : BoxSize-fabs(z1-z2);
|
||||||
|
r=sqrt(dx*dx+dy*dy+dz*dz);
|
||||||
|
|
||||||
|
if (r>=Rmin && r<=Rmax){
|
||||||
|
bin=(int)(log10(r/Rmin)/delta);
|
||||||
|
pairs(bin)+=1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"""
|
||||||
|
wv.inline(code,['pos','l','BoxSize','Rmin','Rmax','bins','pairs'],
|
||||||
|
type_converters = wv.converters.blitz,
|
||||||
|
support_code = support,libraries = ['m'])
|
||||||
|
|
||||||
|
return pairs
|
||||||
|
################################################################################
|
||||||
|
#pos1---an array of positions
|
||||||
|
#pos2---an array of positions
|
||||||
|
#the function returns the number of pairs in distance bins between pos1 and pos2
|
||||||
|
def DR_distances(p1,p2,BoxSize,bins,Rmin,Rmax,pairs):
|
||||||
|
|
||||||
|
l1=p1.shape[0]
|
||||||
|
l2=p2.shape[0]
|
||||||
|
|
||||||
|
support = """
|
||||||
|
#include <iostream>
|
||||||
|
using namespace std;
|
||||||
|
"""
|
||||||
|
code = """
|
||||||
|
float middle=BoxSize/2.0;
|
||||||
|
float dx,dy,dz,r;
|
||||||
|
float x1,y1,z1,x2,y2,z2;
|
||||||
|
float delta=log10(Rmax/Rmin)/bins;
|
||||||
|
int bin,i,j;
|
||||||
|
|
||||||
|
for (i=0;i<l1;i++){
|
||||||
|
x1=p1(i,0);
|
||||||
|
y1=p1(i,1);
|
||||||
|
z1=p1(i,2);
|
||||||
|
for (j=0;j<l2;j++){
|
||||||
|
x2=p2(j,0);
|
||||||
|
y2=p2(j,1);
|
||||||
|
z2=p2(j,2);
|
||||||
|
dx=(fabs(x1-x2)<middle) ? x1-x2 : BoxSize-fabs(x1-x2);
|
||||||
|
dy=(fabs(y1-y2)<middle) ? y1-y2 : BoxSize-fabs(y1-y2);
|
||||||
|
dz=(fabs(z1-z2)<middle) ? z1-z2 : BoxSize-fabs(z1-z2);
|
||||||
|
r=sqrt(dx*dx+dy*dy+dz*dz);
|
||||||
|
|
||||||
|
if (r>=Rmin && r<=Rmax){
|
||||||
|
bin=(int)(log10(r/Rmin)/delta);
|
||||||
|
pairs(bin)+=1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"""
|
||||||
|
wv.inline(code,['p1','p2','l1','l2','BoxSize','Rmin','Rmax','bins','pairs'],
|
||||||
|
type_converters = wv.converters.blitz,
|
||||||
|
support_code = support)
|
||||||
|
|
||||||
|
return pairs
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
|
||||||
|
################################################################################
|
||||||
|
#this routine computes the IDs of all the particles within the neighboord cells
|
||||||
|
#that which can lie within the radius Rmax
|
||||||
|
def indexes_subbox(pos,Rmax,dims,BoxSize,indexes):
|
||||||
|
|
||||||
|
#we add dims to avoid negative numbers. For example
|
||||||
|
#if something hold between -1 and 5, the array to be
|
||||||
|
#constructed should have indexes -1 0 1 2 3 4 5.
|
||||||
|
#To achieve this in a clever way we add dims
|
||||||
|
i_min=int(np.floor((pos[0]-Rmax)*dims/BoxSize))+dims
|
||||||
|
i_max=int(np.floor((pos[0]+Rmax)*dims/BoxSize))+dims
|
||||||
|
j_min=int(np.floor((pos[1]-Rmax)*dims/BoxSize))+dims
|
||||||
|
j_max=int(np.floor((pos[1]+Rmax)*dims/BoxSize))+dims
|
||||||
|
k_min=int(np.floor((pos[2]-Rmax)*dims/BoxSize))+dims
|
||||||
|
k_max=int(np.floor((pos[2]+Rmax)*dims/BoxSize))+dims
|
||||||
|
|
||||||
|
i_array=np.arange(i_min,i_max+1)%dims
|
||||||
|
j_array=np.arange(j_min,j_max+1)%dims
|
||||||
|
k_array=np.arange(k_min,k_max+1)%dims
|
||||||
|
|
||||||
|
PAR_indexes=np.array([])
|
||||||
|
for i in i_array:
|
||||||
|
for j in j_array:
|
||||||
|
for k in k_array:
|
||||||
|
num=dims**2*i+dims*j+k
|
||||||
|
ids=indexes[num]
|
||||||
|
PAR_indexes=np.concatenate((PAR_indexes,ids)).astype(np.int32)
|
||||||
|
|
||||||
|
return PAR_indexes
|
||||||
|
################################################################################
|
||||||
|
#this routine returns the ids of the particles in the neighboord cells
|
||||||
|
#that havent been already selected
|
||||||
|
def indexes_subbox_neigh(pos,Rmax,dims,BoxSize,indexes,subbox):
|
||||||
|
|
||||||
|
#we add dims to avoid negative numbers. For example
|
||||||
|
#if something hold between -1 and 5, the array to be
|
||||||
|
#constructed should have indexes -1 0 1 2 3 4 5.
|
||||||
|
#To achieve this in a clever way we add dims
|
||||||
|
i_min=int(np.floor((pos[0]-Rmax)*dims/BoxSize))+dims
|
||||||
|
i_max=int(np.floor((pos[0]+Rmax)*dims/BoxSize))+dims
|
||||||
|
j_min=int(np.floor((pos[1]-Rmax)*dims/BoxSize))+dims
|
||||||
|
j_max=int(np.floor((pos[1]+Rmax)*dims/BoxSize))+dims
|
||||||
|
k_min=int(np.floor((pos[2]-Rmax)*dims/BoxSize))+dims
|
||||||
|
k_max=int(np.floor((pos[2]+Rmax)*dims/BoxSize))+dims
|
||||||
|
|
||||||
|
i_array=np.arange(i_min,i_max+1)%dims
|
||||||
|
j_array=np.arange(j_min,j_max+1)%dims
|
||||||
|
k_array=np.arange(k_min,k_max+1)%dims
|
||||||
|
|
||||||
|
ids=np.array([])
|
||||||
|
for i in i_array:
|
||||||
|
for j in j_array:
|
||||||
|
for k in k_array:
|
||||||
|
num=dims**2*i+dims*j+k
|
||||||
|
if num>subbox:
|
||||||
|
ids_subbox=indexes[num]
|
||||||
|
ids=np.concatenate((ids,ids_subbox)).astype(np.int32)
|
||||||
|
return ids
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
|
||||||
|
################################################################################
|
||||||
|
#This function computes the correlation function and its error once the number
|
||||||
|
#of galaxy-galaxy, random-random & galaxy-random pairs are given together
|
||||||
|
#with the total number of galaxies and random points
|
||||||
|
def xi(GG,RR,GR,Ng,Nr):
|
||||||
|
|
||||||
|
normGG=2.0/(Ng*(Ng-1.0))
|
||||||
|
normRR=2.0/(Nr*(Nr-1.0))
|
||||||
|
normGR=1.0/(Ng*Nr)
|
||||||
|
|
||||||
|
GGn=GG*normGG
|
||||||
|
RRn=RR*normRR
|
||||||
|
GRn=GR*normGR
|
||||||
|
|
||||||
|
xi=GGn/RRn-2.0*GRn/RRn+1.0
|
||||||
|
|
||||||
|
fact=normRR/normGG*RR*(1.0+xi)+4.0/Ng*(normRR*RR/normGG*(1.0+xi))**2
|
||||||
|
err=normGG/(normRR*RR)*np.sqrt(fact)
|
||||||
|
err=err*np.sqrt(3.0)
|
||||||
|
|
||||||
|
return xi,err
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
################################################################################
|
||||||
|
#This function writes partial results to a file
|
||||||
|
def write_results(fname,histogram,bins,case):
|
||||||
|
f=open(fname,'w')
|
||||||
|
if case=='par-perp':
|
||||||
|
for i in range(len(histogram)):
|
||||||
|
coord_perp=i/bins
|
||||||
|
coord_par=i%bins
|
||||||
|
f.write(str(coord_par)+' '+str(coord_perp)+' '+str(histogram[i])+'\n')
|
||||||
|
elif case=='radial':
|
||||||
|
for i in range(len(histogram)):
|
||||||
|
f.write(str(i)+' '+str(histogram[i])+'\n')
|
||||||
|
else:
|
||||||
|
print 'Error in the description of case:'
|
||||||
|
print 'Choose between: par-perp or radial'
|
||||||
|
f.close()
|
||||||
|
################################################################################
|
||||||
|
#This functions reads partial results of a file
|
||||||
|
def read_results(fname,case):
|
||||||
|
|
||||||
|
histogram=[]
|
||||||
|
|
||||||
|
if case=='par-perp':
|
||||||
|
bins=np.around(np.sqrt(size)).astype(np.int64)
|
||||||
|
|
||||||
|
if bins*bins!=size:
|
||||||
|
print 'Error finding the size of the matrix'
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
f=open(fname,'r')
|
||||||
|
for line in f.readlines():
|
||||||
|
a=line.split()
|
||||||
|
histogram.append(int(a[2]))
|
||||||
|
f.close()
|
||||||
|
histogram=np.array(histogram)
|
||||||
|
return histogram,bins
|
||||||
|
elif case=='radial':
|
||||||
|
f=open(fname,'r')
|
||||||
|
for line in f.readlines():
|
||||||
|
a=line.split()
|
||||||
|
histogram.append(int(a[1]))
|
||||||
|
f.close()
|
||||||
|
histogram=np.array(histogram)
|
||||||
|
return histogram,histogram.shape[0]
|
||||||
|
else:
|
||||||
|
print 'Error in the description of case:'
|
||||||
|
print 'Choose between: par-perp or radial'
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
############ EXAMPLE OF USAGE: TPCF ############
|
||||||
|
"""
|
||||||
|
points_g=150000
|
||||||
|
points_r=200000
|
||||||
|
|
||||||
|
BoxSize=500.0 #Mpc/h
|
||||||
|
Rmin=1.0 #Mpc/h
|
||||||
|
Rmax=50.0 #Mpc/h
|
||||||
|
bins=30
|
||||||
|
|
||||||
|
DD_action='compute'
|
||||||
|
RR_action='compute'
|
||||||
|
DR_action='compute'
|
||||||
|
DD_name='DD.dat'
|
||||||
|
RR_name='RR.dat'
|
||||||
|
DR_name='DR.dat'
|
||||||
|
|
||||||
|
if myrank==0:
|
||||||
|
pos_g=np.random.random((points_g,3))*BoxSize
|
||||||
|
pos_r=np.random.random((points_r,3))*BoxSize
|
||||||
|
|
||||||
|
start=time.clock()
|
||||||
|
r,xi_r,error_xi=TPCF(pos_g,pos_r,BoxSize,DD_action,RR_action,DR_action,
|
||||||
|
DD_name,RR_name,DR_name,bins,Rmin,Rmax,verbose=True)
|
||||||
|
|
||||||
|
print r
|
||||||
|
print xi_r
|
||||||
|
print error_xi
|
||||||
|
end=time.clock()
|
||||||
|
print 'time:',end-start
|
||||||
|
else:
|
||||||
|
pos_g=None; pos_r=None
|
||||||
|
TPCF(pos_g,pos_r,BoxSize,DD_action,RR_action,DR_action,
|
||||||
|
DD_name,RR_name,DR_name,bins,Rmin,Rmax,verbose=True)
|
||||||
|
"""
|
||||||
|
|
||||||
|
|
||||||
|
############ EXAMPLE OF USAGE: TPCCF ############
|
||||||
|
"""
|
||||||
|
points_g1=150000
|
||||||
|
points_g2=150000
|
||||||
|
points_r=200000
|
||||||
|
|
||||||
|
BoxSize=500.0 #Mpc/h
|
||||||
|
Rmin=1.0 #Mpc/h
|
||||||
|
Rmax=50.0 #Mpc/h
|
||||||
|
bins=30
|
||||||
|
|
||||||
|
D1D2_action='compute'; D1D2_name='D1D2.dat'
|
||||||
|
D1R_action='compute'; D1R_name='D1R.dat'
|
||||||
|
D2R_action='compute'; D2R_name='D2R.dat'
|
||||||
|
RR_action='compute'; RR_name='RR.dat'
|
||||||
|
|
||||||
|
|
||||||
|
if myrank==0:
|
||||||
|
pos_g1=np.random.random((points_g1,3))*BoxSize
|
||||||
|
pos_g2=np.random.random((points_g2,3))*BoxSize
|
||||||
|
pos_r=np.random.random((points_r,3))*BoxSize
|
||||||
|
|
||||||
|
r,xi_r=TPCCF(pos_g1,pos_g2,pos_r,BoxSize,
|
||||||
|
D1D2_action,D1R_action,D2R_action,RR_action,
|
||||||
|
D1D2_name,D1R_name,D2R_name,RR_name,
|
||||||
|
bins,Rmin,Rmax,verbose=True)
|
||||||
|
|
||||||
|
print r
|
||||||
|
print xi_r
|
||||||
|
else:
|
||||||
|
pos_g1=None; pos_g2=None; pos_r=None
|
||||||
|
TPCCF(pos_g1,pos_g2,pos_r,BoxSize,D1D2_action,D1R_action,D2R_action,
|
||||||
|
RR_action,D1D2_name,D1R_name,D2R_name,RR_name,bins,Rmin,Rmax,
|
||||||
|
verbose=True)
|
||||||
|
"""
|
||||||
|
|
||||||
|
############ EXAMPLE OF USAGE: DD_file ############
|
||||||
|
"""
|
||||||
|
points_r=200000
|
||||||
|
|
||||||
|
BoxSize=500.0 #Mpc/h
|
||||||
|
Rmin=1.0 #Mpc/h
|
||||||
|
Rmax=50.0 #Mpc/h
|
||||||
|
bins=30
|
||||||
|
|
||||||
|
RR_name='RR.dat'
|
||||||
|
|
||||||
|
if myrank==0:
|
||||||
|
pos_r=np.random.random((points_r,3))*BoxSize
|
||||||
|
DD_file(pos_r,BoxSize,RR_name,bins,Rmin,Rmax)
|
||||||
|
else:
|
||||||
|
pos_r=None
|
||||||
|
DD_file(pos_r,BoxSize,RR_name,bins,Rmin,Rmax)
|
||||||
|
"""
|
431
python_tools/fit_hod/readsnap.py
Normal file
431
python_tools/fit_hod/readsnap.py
Normal file
|
@ -0,0 +1,431 @@
|
||||||
|
# routines for reading headers and data blocks from Gadget snapshot files
|
||||||
|
# usage e.g.:
|
||||||
|
#
|
||||||
|
# import readsnap as rs
|
||||||
|
# header = rs.snapshot_header("snap_063.0") # reads snapshot header
|
||||||
|
# print header.massarr
|
||||||
|
# mass = rs.read_block("snap_063","MASS",parttype=5) # reads mass for particles of type 5, using block names should work for both format 1 and 2 snapshots
|
||||||
|
# print "mass for", mass.size, "particles read"
|
||||||
|
# print mass[0:10]
|
||||||
|
#
|
||||||
|
# before using read_block, make sure that the description (and order if using format 1 snapshot files) of the data blocks
|
||||||
|
# is correct for your configuration of Gadget
|
||||||
|
#
|
||||||
|
# for mutliple file snapshots give e.g. the filename "snap_063" rather than "snap_063.0" to read_block
|
||||||
|
# for snapshot_header the file number should be included, e.g."snap_063.0", as the headers of the files differ
|
||||||
|
#
|
||||||
|
# the returned data block is ordered by particle species even when read from a multiple file snapshot
|
||||||
|
|
||||||
|
import numpy as np
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
import math
|
||||||
|
|
||||||
|
# ----- class for snapshot header -----
|
||||||
|
|
||||||
|
class snapshot_header:
|
||||||
|
def __init__(self, filename):
|
||||||
|
|
||||||
|
if os.path.exists(filename):
|
||||||
|
curfilename = filename
|
||||||
|
elif os.path.exists(filename+".0"):
|
||||||
|
curfilename = filename+".0"
|
||||||
|
else:
|
||||||
|
print "file not found:", filename
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
self.filename = filename
|
||||||
|
f = open(curfilename,'rb')
|
||||||
|
blocksize = np.fromfile(f,dtype=np.int32,count=1)
|
||||||
|
if blocksize[0] == 8:
|
||||||
|
swap = 0
|
||||||
|
format = 2
|
||||||
|
elif blocksize[0] == 256:
|
||||||
|
swap = 0
|
||||||
|
format = 1
|
||||||
|
else:
|
||||||
|
blocksize.byteswap(True)
|
||||||
|
if blocksize[0] == 8:
|
||||||
|
swap = 1
|
||||||
|
format = 2
|
||||||
|
elif blocksize[0] == 256:
|
||||||
|
swap = 1
|
||||||
|
format = 1
|
||||||
|
else:
|
||||||
|
print "incorrect file format encountered when reading header of", filename
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
self.format = format
|
||||||
|
self.swap = swap
|
||||||
|
|
||||||
|
if format==2:
|
||||||
|
f.seek(16, os.SEEK_CUR)
|
||||||
|
|
||||||
|
self.npart = np.fromfile(f,dtype=np.int32,count=6)
|
||||||
|
self.massarr = np.fromfile(f,dtype=np.float64,count=6)
|
||||||
|
self.time = (np.fromfile(f,dtype=np.float64,count=1))[0]
|
||||||
|
self.redshift = (np.fromfile(f,dtype=np.float64,count=1))[0]
|
||||||
|
self.sfr = (np.fromfile(f,dtype=np.int32,count=1))[0]
|
||||||
|
self.feedback = (np.fromfile(f,dtype=np.int32,count=1))[0]
|
||||||
|
self.nall = np.fromfile(f,dtype=np.int32,count=6)
|
||||||
|
self.cooling = (np.fromfile(f,dtype=np.int32,count=1))[0]
|
||||||
|
self.filenum = (np.fromfile(f,dtype=np.int32,count=1))[0]
|
||||||
|
self.boxsize = (np.fromfile(f,dtype=np.float64,count=1))[0]
|
||||||
|
self.omega_m = (np.fromfile(f,dtype=np.float64,count=1))[0]
|
||||||
|
self.omega_l = (np.fromfile(f,dtype=np.float64,count=1))[0]
|
||||||
|
self.hubble = (np.fromfile(f,dtype=np.float64,count=1))[0]
|
||||||
|
|
||||||
|
if swap:
|
||||||
|
self.npart.byteswap(True)
|
||||||
|
self.massarr.byteswap(True)
|
||||||
|
self.time = self.time.byteswap()
|
||||||
|
self.redshift = self.redshift.byteswap()
|
||||||
|
self.sfr = self.sfr.byteswap()
|
||||||
|
self.feedback = self.feedback.byteswap()
|
||||||
|
self.nall.byteswap(True)
|
||||||
|
self.cooling = self.cooling.byteswap()
|
||||||
|
self.filenum = self.filenum.byteswap()
|
||||||
|
self.boxsize = self.boxsize.byteswap()
|
||||||
|
self.omega_m = self.omega_m.byteswap()
|
||||||
|
self.omega_l = self.omega_l.byteswap()
|
||||||
|
self.hubble = self.hubble.byteswap()
|
||||||
|
|
||||||
|
f.close()
|
||||||
|
|
||||||
|
# ----- find offset and size of data block -----
|
||||||
|
|
||||||
|
def find_block(filename, format, swap, block, block_num, only_list_blocks=False):
|
||||||
|
if (not os.path.exists(filename)):
|
||||||
|
print "file not found:", filename
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
f = open(filename,'rb')
|
||||||
|
f.seek(0, os.SEEK_END)
|
||||||
|
filesize = f.tell()
|
||||||
|
f.seek(0, os.SEEK_SET)
|
||||||
|
|
||||||
|
found = False
|
||||||
|
curblock_num = 1
|
||||||
|
while ((not found) and (f.tell()<filesize)):
|
||||||
|
if format==2:
|
||||||
|
f.seek(4, os.SEEK_CUR)
|
||||||
|
curblock = f.read(4)
|
||||||
|
if (block == curblock):
|
||||||
|
found = True
|
||||||
|
f.seek(8, os.SEEK_CUR)
|
||||||
|
else:
|
||||||
|
if curblock_num==block_num:
|
||||||
|
found = True
|
||||||
|
|
||||||
|
curblocksize = (np.fromfile(f,dtype=np.uint32,count=1))[0]
|
||||||
|
if swap:
|
||||||
|
curblocksize = curblocksize.byteswap()
|
||||||
|
|
||||||
|
# - print some debug info about found data blocks -
|
||||||
|
#if format==2:
|
||||||
|
# print curblock, curblock_num, curblocksize
|
||||||
|
#else:
|
||||||
|
# print curblock_num, curblocksize
|
||||||
|
|
||||||
|
if only_list_blocks:
|
||||||
|
if format==2:
|
||||||
|
print curblock_num,curblock,f.tell(),curblocksize
|
||||||
|
else:
|
||||||
|
print curblock_num,f.tell(),curblocksize
|
||||||
|
found = False
|
||||||
|
|
||||||
|
|
||||||
|
if found:
|
||||||
|
blocksize = curblocksize
|
||||||
|
offset = f.tell()
|
||||||
|
else:
|
||||||
|
f.seek(curblocksize, os.SEEK_CUR)
|
||||||
|
blocksize_check = (np.fromfile(f,dtype=np.uint32,count=1))[0]
|
||||||
|
if swap: blocksize_check = blocksize_check.byteswap()
|
||||||
|
if (curblocksize != blocksize_check):
|
||||||
|
print "something wrong"
|
||||||
|
sys.exit()
|
||||||
|
curblock_num += 1
|
||||||
|
f.close()
|
||||||
|
|
||||||
|
if ((not found) and (not only_list_blocks)):
|
||||||
|
print "Error: block not found"
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
if (not only_list_blocks):
|
||||||
|
return offset,blocksize
|
||||||
|
|
||||||
|
# ----- read data block -----
|
||||||
|
#for snapshots with very very large number of particles set nall manually
|
||||||
|
#for instance nall=np.array([0,2048**3,0,0,0,0])
|
||||||
|
def read_block(filename, block, parttype=-1, physical_velocities=True, arepo=0, no_masses=False, verbose=False, nall=[0,0,0,0,0,0]):
|
||||||
|
if (verbose):
|
||||||
|
print "reading block", block
|
||||||
|
|
||||||
|
blockadd=0
|
||||||
|
blocksub=0
|
||||||
|
|
||||||
|
if arepo==0:
|
||||||
|
if (verbose):
|
||||||
|
print "Gadget format"
|
||||||
|
blockadd=0
|
||||||
|
if arepo==1:
|
||||||
|
if (verbose):
|
||||||
|
print "Arepo format"
|
||||||
|
blockadd=1
|
||||||
|
if arepo==2:
|
||||||
|
if (verbose):
|
||||||
|
print "Arepo extended format"
|
||||||
|
blockadd=4
|
||||||
|
if no_masses==True:
|
||||||
|
if (verbose):
|
||||||
|
print "No mass block present"
|
||||||
|
blocksub=1
|
||||||
|
|
||||||
|
if parttype not in [-1,0,1,2,3,4,5]:
|
||||||
|
print "wrong parttype given"
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
if os.path.exists(filename):
|
||||||
|
curfilename = filename
|
||||||
|
elif os.path.exists(filename+".0"):
|
||||||
|
curfilename = filename+".0"
|
||||||
|
else:
|
||||||
|
print "file not found:", filename
|
||||||
|
print "and:", curfilename
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
head = snapshot_header(curfilename)
|
||||||
|
format = head.format
|
||||||
|
|
||||||
|
print "FORMAT=", format
|
||||||
|
swap = head.swap
|
||||||
|
npart = head.npart
|
||||||
|
massarr = head.massarr
|
||||||
|
if np.all(nall==[0,0,0,0,0,0]):
|
||||||
|
nall = head.nall
|
||||||
|
filenum = head.filenum
|
||||||
|
redshift = head.redshift
|
||||||
|
time = head.time
|
||||||
|
del head
|
||||||
|
|
||||||
|
# - description of data blocks -
|
||||||
|
# add or change blocks as needed for your Gadget version
|
||||||
|
data_for_type = np.zeros(6,bool) # should be set to "True" below for the species for which data is stored in the data block #by doing this, the default value is False data_for_type=[False,False,False,False,False,False]
|
||||||
|
dt = np.float32 # data type of the data in the block
|
||||||
|
if block=="POS ":
|
||||||
|
data_for_type[:] = True
|
||||||
|
dt = np.dtype((np.float32,3))
|
||||||
|
block_num = 2
|
||||||
|
elif block=="VEL ":
|
||||||
|
data_for_type[:] = True
|
||||||
|
dt = np.dtype((np.float32,3))
|
||||||
|
block_num = 3
|
||||||
|
elif block=="ID ":
|
||||||
|
data_for_type[:] = True
|
||||||
|
dt = np.uint32
|
||||||
|
block_num = 4
|
||||||
|
#only used for format I, when file structure is HEAD,POS,VEL,ID,ACCE
|
||||||
|
elif block=="ACCE": #This is only for the PIETRONI project
|
||||||
|
data_for_type[:] = True #This is only for the PIETRONI project
|
||||||
|
dt = np.dtype((np.float32,3)) #This is only for the PIETRONI project
|
||||||
|
block_num = 5 #This is only for the PIETRONI project
|
||||||
|
elif block=="MASS":
|
||||||
|
data_for_type[np.where(massarr==0)] = True
|
||||||
|
block_num = 5
|
||||||
|
if parttype>=0 and massarr[parttype]>0:
|
||||||
|
if (verbose):
|
||||||
|
print "filling masses according to massarr"
|
||||||
|
return np.ones(nall[parttype],dtype=dt)*massarr[parttype]
|
||||||
|
elif block=="U ":
|
||||||
|
data_for_type[0] = True
|
||||||
|
block_num = 6-blocksub
|
||||||
|
elif block=="RHO ":
|
||||||
|
data_for_type[0] = True
|
||||||
|
block_num = 7-blocksub
|
||||||
|
elif block=="VOL ":
|
||||||
|
data_for_type[0] = True
|
||||||
|
block_num = 8-blocksub
|
||||||
|
elif block=="CMCE":
|
||||||
|
data_for_type[0] = True
|
||||||
|
dt = np.dtype((np.float32,3))
|
||||||
|
block_num = 9-blocksub
|
||||||
|
elif block=="AREA":
|
||||||
|
data_for_type[0] = True
|
||||||
|
block_num = 10-blocksub
|
||||||
|
elif block=="NFAC":
|
||||||
|
data_for_type[0] = True
|
||||||
|
dt = np.dtype(np.int64) #depends on code version, most recent hast int32, old MyIDType
|
||||||
|
block_num = 11-blocksub
|
||||||
|
elif block=="NE ":
|
||||||
|
data_for_type[0] = True
|
||||||
|
block_num = 8+blockadd-blocksub
|
||||||
|
elif block=="NH ":
|
||||||
|
data_for_type[0] = True
|
||||||
|
block_num = 9+blockadd-blocksub
|
||||||
|
elif block=="HSML":
|
||||||
|
data_for_type[0] = True
|
||||||
|
block_num = 10+blockadd-blocksub
|
||||||
|
elif block=="SFR ":
|
||||||
|
data_for_type[0] = True
|
||||||
|
block_num = 11+blockadd-blocksub
|
||||||
|
elif block=="MHI ": #This is only for the bias_HI project
|
||||||
|
data_for_type[0] = True #This is only for the bias_HI project
|
||||||
|
block_num = 12+blockadd-blocksub #This is only for the bias_HI project
|
||||||
|
elif block=="TEMP": #This is only for the bias_HI project
|
||||||
|
data_for_type[0] = True #This is only for the bias_HI project
|
||||||
|
block_num = 13+blockadd-blocksub #This is only for the bias_HI project
|
||||||
|
elif block=="AGE ":
|
||||||
|
data_for_type[4] = True
|
||||||
|
block_num = 12+blockadd-blocksub
|
||||||
|
elif block=="Z ":
|
||||||
|
data_for_type[0] = True
|
||||||
|
data_for_type[4] = True
|
||||||
|
block_num = 13+blockadd-blocksub
|
||||||
|
elif block=="BHMA":
|
||||||
|
data_for_type[5] = True
|
||||||
|
block_num = 14+blockadd-blocksub
|
||||||
|
elif block=="BHMD":
|
||||||
|
data_for_type[5] = True
|
||||||
|
block_num = 15+blockadd-blocksub
|
||||||
|
else:
|
||||||
|
print "Sorry! Block type", block, "not known!"
|
||||||
|
sys.exit()
|
||||||
|
# - end of block description -
|
||||||
|
|
||||||
|
actual_data_for_type = np.copy(data_for_type)
|
||||||
|
if parttype >= 0:
|
||||||
|
actual_data_for_type[:] = False
|
||||||
|
actual_data_for_type[parttype] = True
|
||||||
|
if data_for_type[parttype]==False:
|
||||||
|
print "Error: no data for specified particle type", parttype, "in the block", block
|
||||||
|
sys.exit()
|
||||||
|
elif block=="MASS":
|
||||||
|
actual_data_for_type[:] = True
|
||||||
|
|
||||||
|
allpartnum = np.int64(0)
|
||||||
|
species_offset = np.zeros(6,np.int64)
|
||||||
|
for j in range(6):
|
||||||
|
species_offset[j] = allpartnum
|
||||||
|
if actual_data_for_type[j]:
|
||||||
|
allpartnum += nall[j]
|
||||||
|
|
||||||
|
for i in range(filenum): # main loop over files
|
||||||
|
if filenum>1:
|
||||||
|
curfilename = filename+"."+str(i)
|
||||||
|
|
||||||
|
if i>0:
|
||||||
|
head = snapshot_header(curfilename)
|
||||||
|
npart = head.npart
|
||||||
|
del head
|
||||||
|
|
||||||
|
curpartnum = np.int32(0)
|
||||||
|
cur_species_offset = np.zeros(6,np.int64)
|
||||||
|
for j in range(6):
|
||||||
|
cur_species_offset[j] = curpartnum
|
||||||
|
if data_for_type[j]:
|
||||||
|
curpartnum += npart[j]
|
||||||
|
|
||||||
|
if parttype>=0:
|
||||||
|
actual_curpartnum = npart[parttype]
|
||||||
|
add_offset = cur_species_offset[parttype]
|
||||||
|
else:
|
||||||
|
actual_curpartnum = curpartnum
|
||||||
|
add_offset = np.int32(0)
|
||||||
|
|
||||||
|
offset,blocksize = find_block(curfilename,format,swap,block,block_num)
|
||||||
|
|
||||||
|
if i==0: # fix data type for ID if long IDs are used
|
||||||
|
if block=="ID ":
|
||||||
|
if blocksize == np.dtype(dt).itemsize*curpartnum * 2:
|
||||||
|
dt = np.uint64
|
||||||
|
|
||||||
|
if np.dtype(dt).itemsize*curpartnum != blocksize:
|
||||||
|
print "something wrong with blocksize! expected =",np.dtype(dt).itemsize*curpartnum,"actual =",blocksize
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
f = open(curfilename,'rb')
|
||||||
|
f.seek(offset + add_offset*np.dtype(dt).itemsize, os.SEEK_CUR)
|
||||||
|
curdat = np.fromfile(f,dtype=dt,count=actual_curpartnum) # read data
|
||||||
|
f.close()
|
||||||
|
if swap:
|
||||||
|
curdat.byteswap(True)
|
||||||
|
|
||||||
|
if i==0:
|
||||||
|
data = np.empty(allpartnum,dt)
|
||||||
|
|
||||||
|
for j in range(6):
|
||||||
|
if actual_data_for_type[j]:
|
||||||
|
if block=="MASS" and massarr[j]>0: # add mass block for particles for which the mass is specified in the snapshot header
|
||||||
|
data[species_offset[j]:species_offset[j]+npart[j]] = massarr[j]
|
||||||
|
else:
|
||||||
|
if parttype>=0:
|
||||||
|
data[species_offset[j]:species_offset[j]+npart[j]] = curdat
|
||||||
|
else:
|
||||||
|
data[species_offset[j]:species_offset[j]+npart[j]] = curdat[cur_species_offset[j]:cur_species_offset[j]+npart[j]]
|
||||||
|
species_offset[j] += npart[j]
|
||||||
|
|
||||||
|
del curdat
|
||||||
|
|
||||||
|
if physical_velocities and block=="VEL " and redshift!=0:
|
||||||
|
data *= math.sqrt(time)
|
||||||
|
|
||||||
|
return data
|
||||||
|
|
||||||
|
# ----- list all data blocks in a format 2 snapshot file -----
|
||||||
|
|
||||||
|
def list_format2_blocks(filename):
|
||||||
|
if os.path.exists(filename):
|
||||||
|
curfilename = filename
|
||||||
|
elif os.path.exists(filename+".0"):
|
||||||
|
curfilename = filename+".0"
|
||||||
|
else:
|
||||||
|
print "file not found:", filename
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
head = snapshot_header(curfilename)
|
||||||
|
format = head.format
|
||||||
|
swap = head.swap
|
||||||
|
del head
|
||||||
|
|
||||||
|
print 'GADGET FORMAT ',format
|
||||||
|
if (format != 2):
|
||||||
|
print "# OFFSET SIZE"
|
||||||
|
else:
|
||||||
|
print "# BLOCK OFFSET SIZE"
|
||||||
|
print "-------------------------"
|
||||||
|
|
||||||
|
find_block(curfilename, format, swap, "XXXX", 0, only_list_blocks=True)
|
||||||
|
|
||||||
|
print "-------------------------"
|
||||||
|
|
||||||
|
def read_gadget_header(filename):
|
||||||
|
if os.path.exists(filename):
|
||||||
|
curfilename = filename
|
||||||
|
elif os.path.exists(filename+".0"):
|
||||||
|
curfilename = filename+".0"
|
||||||
|
else:
|
||||||
|
print "file not found:", filename
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
head=snapshot_header(curfilename)
|
||||||
|
print 'npar=',head.npart
|
||||||
|
print 'nall=',head.nall
|
||||||
|
print 'a=',head.time
|
||||||
|
print 'z=',head.redshift
|
||||||
|
print 'masses=',head.massarr*1e10,'Msun/h'
|
||||||
|
print 'boxsize=',head.boxsize,'kpc/h'
|
||||||
|
print 'filenum=',head.filenum
|
||||||
|
print 'cooling=',head.cooling
|
||||||
|
print 'Omega_m,Omega_l=',head.omega_m,head.omega_l
|
||||||
|
print 'h=',head.hubble,'\n'
|
||||||
|
|
||||||
|
rhocrit=2.77536627e11 #h**2 M_sun/Mpc**3
|
||||||
|
rhocrit=rhocrit/1e9 #h**2M_sun/kpc**3
|
||||||
|
|
||||||
|
Omega_DM=head.nall[1]*head.massarr[1]*1e10/(head.boxsize**3*rhocrit)
|
||||||
|
print 'DM mass=',head.massarr[1]*1e10,'Omega_DM=',Omega_DM
|
||||||
|
if head.nall[2]>0 and head.massarr[2]>0:
|
||||||
|
Omega_NU=head.nall[2]*head.massarr[2]*1e10/(head.boxsize**3*rhocrit)
|
||||||
|
print 'NU mass=',head.massarr[2]*1e10,'Omega_NU=',Omega_NU
|
||||||
|
print 'Sum of neutrino masses=',Omega_NU*head.hubble**2*94.1745,'eV'
|
290
python_tools/fit_hod/readsubf.py
Normal file
290
python_tools/fit_hod/readsubf.py
Normal file
|
@ -0,0 +1,290 @@
|
||||||
|
|
||||||
|
# code for reading Subfind's subhalo_tab files
|
||||||
|
# usage e.g.:
|
||||||
|
#
|
||||||
|
# import readsubf
|
||||||
|
# cat = readsubf.subfind_catalog("./m_10002_h_94_501_z3_csf/",63,masstab=True)
|
||||||
|
# print cat.nsubs
|
||||||
|
# print "largest halo x position = ",cat.sub_pos[0][0]
|
||||||
|
|
||||||
|
import numpy as np
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
|
||||||
|
class subfind_catalog:
|
||||||
|
def __init__(self, basedir, snapnum, group_veldisp = False, masstab = False, long_ids = False, swap = False):
|
||||||
|
self.filebase = basedir + "/groups_" + str(snapnum).zfill(3) + "/subhalo_tab_" + str(snapnum).zfill(3) + "."
|
||||||
|
|
||||||
|
#print
|
||||||
|
#print "reading subfind catalog for snapshot",snapnum,"of",basedir
|
||||||
|
|
||||||
|
if long_ids: self.id_type = np.uint64
|
||||||
|
else: self.id_type = np.uint32
|
||||||
|
|
||||||
|
self.group_veldisp = group_veldisp
|
||||||
|
self.masstab = masstab
|
||||||
|
|
||||||
|
filenum = 0
|
||||||
|
doneflag = False
|
||||||
|
skip_gr = 0
|
||||||
|
skip_sub = 0
|
||||||
|
while not doneflag:
|
||||||
|
curfile = self.filebase + str(filenum)
|
||||||
|
|
||||||
|
if (not os.path.exists(curfile)):
|
||||||
|
print "file not found:", curfile
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
f = open(curfile,'rb')
|
||||||
|
|
||||||
|
ngroups = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
totngroups = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
nids = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
totnids = np.fromfile(f, dtype=np.uint64, count=1)[0]
|
||||||
|
ntask = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
nsubs = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
totnsubs = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
|
||||||
|
if swap:
|
||||||
|
ngroups = ngroups.byteswap()
|
||||||
|
totngroups = totngroups.byteswap()
|
||||||
|
nids = nids.byteswap()
|
||||||
|
totnids = totnids.byteswap()
|
||||||
|
ntask = ntask.byteswap()
|
||||||
|
nsubs = nsubs.byteswap()
|
||||||
|
totnsubs = totnsubs.byteswap()
|
||||||
|
|
||||||
|
if filenum == 0:
|
||||||
|
self.ngroups = totngroups
|
||||||
|
self.nids = totnids
|
||||||
|
self.nfiles = ntask
|
||||||
|
self.nsubs = totnsubs
|
||||||
|
|
||||||
|
self.group_len = np.empty(totngroups, dtype=np.uint32)
|
||||||
|
self.group_offset = np.empty(totngroups, dtype=np.uint32)
|
||||||
|
self.group_mass = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_pos = np.empty(totngroups, dtype=np.dtype((np.float32,3)))
|
||||||
|
self.group_m_mean200 = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_r_mean200 = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_m_crit200 = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_r_crit200 = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_m_tophat200 = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_r_tophat200 = np.empty(totngroups, dtype=np.float32)
|
||||||
|
if group_veldisp:
|
||||||
|
self.group_veldisp_mean200 = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_veldisp_crit200 = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_veldisp_tophat200 = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_contamination_count = np.empty(totngroups, dtype=np.uint32)
|
||||||
|
self.group_contamination_mass = np.empty(totngroups, dtype=np.float32)
|
||||||
|
self.group_nsubs = np.empty(totngroups, dtype=np.uint32)
|
||||||
|
self.group_firstsub = np.empty(totngroups, dtype=np.uint32)
|
||||||
|
|
||||||
|
self.sub_len = np.empty(totnsubs, dtype=np.uint32)
|
||||||
|
self.sub_offset = np.empty(totnsubs, dtype=np.uint32)
|
||||||
|
self.sub_parent = np.empty(totnsubs, dtype=np.uint32)
|
||||||
|
self.sub_mass = np.empty(totnsubs, dtype=np.float32)
|
||||||
|
self.sub_pos = np.empty(totnsubs, dtype=np.dtype((np.float32,3)))
|
||||||
|
self.sub_vel = np.empty(totnsubs, dtype=np.dtype((np.float32,3)))
|
||||||
|
self.sub_cm = np.empty(totnsubs, dtype=np.dtype((np.float32,3)))
|
||||||
|
self.sub_spin = np.empty(totnsubs, dtype=np.dtype((np.float32,3)))
|
||||||
|
self.sub_veldisp = np.empty(totnsubs, dtype=np.float32)
|
||||||
|
self.sub_vmax = np.empty(totnsubs, dtype=np.float32)
|
||||||
|
self.sub_vmaxrad = np.empty(totnsubs, dtype=np.float32)
|
||||||
|
self.sub_halfmassrad = np.empty(totnsubs, dtype=np.float32)
|
||||||
|
self.sub_id_mostbound = np.empty(totnsubs, dtype=self.id_type)
|
||||||
|
self.sub_grnr = np.empty(totnsubs, dtype=np.uint32)
|
||||||
|
if masstab:
|
||||||
|
self.sub_masstab = np.empty(totnsubs, dtype=np.dtype((np.float32,6)))
|
||||||
|
|
||||||
|
if ngroups > 0:
|
||||||
|
locs = slice(skip_gr, skip_gr + ngroups)
|
||||||
|
self.group_len[locs] = np.fromfile(f, dtype=np.uint32, count=ngroups)
|
||||||
|
self.group_offset[locs] = np.fromfile(f, dtype=np.uint32, count=ngroups)
|
||||||
|
self.group_mass[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_pos[locs] = np.fromfile(f, dtype=np.dtype((np.float32,3)), count=ngroups)
|
||||||
|
self.group_m_mean200[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_r_mean200[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_m_crit200[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_r_crit200[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_m_tophat200[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_r_tophat200[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
if group_veldisp:
|
||||||
|
self.group_veldisp_mean200[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_veldisp_crit200[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_veldisp_tophat200[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_contamination_count[locs] = np.fromfile(f, dtype=np.uint32, count=ngroups)
|
||||||
|
self.group_contamination_mass[locs] = np.fromfile(f, dtype=np.float32, count=ngroups)
|
||||||
|
self.group_nsubs[locs] = np.fromfile(f, dtype=np.uint32, count=ngroups)
|
||||||
|
self.group_firstsub[locs] = np.fromfile(f, dtype=np.uint32, count=ngroups)
|
||||||
|
skip_gr += ngroups
|
||||||
|
|
||||||
|
if nsubs > 0:
|
||||||
|
locs = slice(skip_sub, skip_sub + nsubs)
|
||||||
|
self.sub_len[locs] = np.fromfile(f, dtype=np.uint32, count=nsubs)
|
||||||
|
self.sub_offset[locs] = np.fromfile(f, dtype=np.uint32, count=nsubs)
|
||||||
|
self.sub_parent[locs] = np.fromfile(f, dtype=np.uint32, count=nsubs)
|
||||||
|
self.sub_mass[locs] = np.fromfile(f, dtype=np.float32, count=nsubs)
|
||||||
|
self.sub_pos[locs] = np.fromfile(f, dtype=np.dtype((np.float32,3)), count=nsubs)
|
||||||
|
self.sub_vel[locs] = np.fromfile(f, dtype=np.dtype((np.float32,3)), count=nsubs)
|
||||||
|
self.sub_cm[locs] = np.fromfile(f, dtype=np.dtype((np.float32,3)), count=nsubs)
|
||||||
|
self.sub_spin[locs] = np.fromfile(f, dtype=np.dtype((np.float32,3)), count=nsubs)
|
||||||
|
self.sub_veldisp[locs] = np.fromfile(f, dtype=np.float32, count=nsubs)
|
||||||
|
self.sub_vmax[locs] = np.fromfile(f, dtype=np.float32, count=nsubs)
|
||||||
|
self.sub_vmaxrad[locs] = np.fromfile(f, dtype=np.float32, count=nsubs)
|
||||||
|
self.sub_halfmassrad[locs] = np.fromfile(f, dtype=np.float32, count=nsubs)
|
||||||
|
self.sub_id_mostbound[locs] = np.fromfile(f, dtype=self.id_type, count=nsubs)
|
||||||
|
self.sub_grnr[locs] = np.fromfile(f, dtype=np.uint32, count=nsubs)
|
||||||
|
if masstab:
|
||||||
|
self.sub_masstab[locs] = np.fromfile(f, dtype=np.dtype((np.float32,6)), count=nsubs)
|
||||||
|
skip_sub += nsubs
|
||||||
|
|
||||||
|
curpos = f.tell()
|
||||||
|
f.seek(0,os.SEEK_END)
|
||||||
|
if curpos != f.tell(): print "Warning: finished reading before EOF for file",filenum
|
||||||
|
f.close()
|
||||||
|
#print 'finished with file number',filenum,"of",ntask
|
||||||
|
filenum += 1
|
||||||
|
if filenum == self.nfiles: doneflag = True
|
||||||
|
|
||||||
|
if swap:
|
||||||
|
self.group_len.byteswap(True)
|
||||||
|
self.group_offset.byteswap(True)
|
||||||
|
self.group_mass.byteswap(True)
|
||||||
|
self.group_pos.byteswap(True)
|
||||||
|
self.group_m_mean200.byteswap(True)
|
||||||
|
self.group_r_mean200.byteswap(True)
|
||||||
|
self.group_m_crit200.byteswap(True)
|
||||||
|
self.group_r_crit200.byteswap(True)
|
||||||
|
self.group_m_tophat200.byteswap(True)
|
||||||
|
self.group_r_tophat200.byteswap(True)
|
||||||
|
if group_veldisp:
|
||||||
|
self.group_veldisp_mean200.byteswap(True)
|
||||||
|
self.group_veldisp_crit200.byteswap(True)
|
||||||
|
self.group_veldisp_tophat200.byteswap(True)
|
||||||
|
self.group_contamination_count.byteswap(True)
|
||||||
|
self.group_contamination_mass.byteswap(True)
|
||||||
|
self.group_nsubs.byteswap(True)
|
||||||
|
self.group_firstsub.byteswap(True)
|
||||||
|
|
||||||
|
self.sub_len.byteswap(True)
|
||||||
|
self.sub_offset.byteswap(True)
|
||||||
|
self.sub_parent.byteswap(True)
|
||||||
|
self.sub_mass.byteswap(True)
|
||||||
|
self.sub_pos.byteswap(True)
|
||||||
|
self.sub_vel.byteswap(True)
|
||||||
|
self.sub_cm.byteswap(True)
|
||||||
|
self.sub_spin.byteswap(True)
|
||||||
|
self.sub_veldisp.byteswap(True)
|
||||||
|
self.sub_vmax.byteswap(True)
|
||||||
|
self.sub_vmaxrad.byteswap(True)
|
||||||
|
self.sub_halfmassrad.byteswap(True)
|
||||||
|
self.sub_id_mostbound.byteswap(True)
|
||||||
|
self.sub_grnr.byteswap(True)
|
||||||
|
if masstab:
|
||||||
|
self.sub_masstab.byteswap(True)
|
||||||
|
|
||||||
|
#print
|
||||||
|
#print "number of groups =", self.ngroups
|
||||||
|
#print "number of subgroups =", self.nsubs
|
||||||
|
#if self.nsubs > 0:
|
||||||
|
# print "largest group of length",self.group_len[0],"has",self.group_nsubs[0],"subhalos"
|
||||||
|
# print
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# code for reading Subfind's ID files
|
||||||
|
# usage e.g.:
|
||||||
|
#
|
||||||
|
# import readsubf
|
||||||
|
# ids = readsubf.subf_ids("./m_10002_h_94_501_z3_csf/", 0, 100)
|
||||||
|
|
||||||
|
|
||||||
|
class subf_ids:
|
||||||
|
def __init__(self, basedir, snapnum, substart, sublen, swap = False, verbose = False, long_ids = False, read_all = False):
|
||||||
|
self.filebase = basedir + "/groups_" + str(snapnum).zfill(3) + "/subhalo_ids_" + str(snapnum).zfill(3) + "."
|
||||||
|
|
||||||
|
if (verbose):
|
||||||
|
print
|
||||||
|
print "reading subhalo IDs for snapshot",snapnum,"of",basedir
|
||||||
|
|
||||||
|
if long_ids: self.id_type = np.uint64
|
||||||
|
else: self.id_type = np.uint32
|
||||||
|
|
||||||
|
|
||||||
|
filenum = 0
|
||||||
|
doneflag = False
|
||||||
|
count=substart
|
||||||
|
found=0
|
||||||
|
|
||||||
|
|
||||||
|
while not doneflag:
|
||||||
|
curfile = self.filebase + str(filenum)
|
||||||
|
|
||||||
|
if (not os.path.exists(curfile)):
|
||||||
|
print "file not found:", curfile
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
f = open(curfile,'rb')
|
||||||
|
|
||||||
|
Ngroups = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
TotNgroups = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
NIds = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
TotNids = np.fromfile(f, dtype=np.uint64, count=1)[0]
|
||||||
|
NTask = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
Offset = np.fromfile(f, dtype=np.uint32, count=1)[0]
|
||||||
|
|
||||||
|
|
||||||
|
if read_all:
|
||||||
|
substart=0
|
||||||
|
sublen=TotNids
|
||||||
|
if swap:
|
||||||
|
Ngroups = Ngroups.byteswap()
|
||||||
|
TotNgroups = TotNgroups.byteswap()
|
||||||
|
NIds = NIds.byteswap()
|
||||||
|
TotNids = TotNids.byteswap()
|
||||||
|
NTask = NTask.byteswap()
|
||||||
|
Offset = Offset.byteswap()
|
||||||
|
if filenum == 0:
|
||||||
|
if (verbose):
|
||||||
|
print "Ngroups = ", Ngroups
|
||||||
|
print "TotNgroups = ", Ngroups
|
||||||
|
print "NIds = ", NIds
|
||||||
|
print "TotNids = ", TotNids
|
||||||
|
print "NTask = ", NTask
|
||||||
|
print "Offset = ", Offset
|
||||||
|
self.nfiles = NTask
|
||||||
|
self.SubLen=sublen
|
||||||
|
self.SubIDs = np.empty(sublen, dtype=self.id_type)
|
||||||
|
|
||||||
|
|
||||||
|
if count <= Offset+NIds:
|
||||||
|
nskip = count - Offset
|
||||||
|
nrem = Offset + NIds - count
|
||||||
|
if sublen > nrem:
|
||||||
|
n_to_read = nrem
|
||||||
|
else:
|
||||||
|
n_to_read = sublen
|
||||||
|
if n_to_read > 0:
|
||||||
|
if (verbose):
|
||||||
|
print filenum, n_to_read
|
||||||
|
if nskip > 0:
|
||||||
|
dummy=np.fromfile(f, dtype=self.id_type, count=nskip)
|
||||||
|
if (verbose):
|
||||||
|
print dummy
|
||||||
|
locs = slice(found, found + n_to_read)
|
||||||
|
dummy2 = np.fromfile(f, dtype=self.id_type, count=n_to_read)
|
||||||
|
if (verbose):
|
||||||
|
print dummy2
|
||||||
|
self.SubIDs[locs]=dummy2
|
||||||
|
found += n_to_read
|
||||||
|
count += n_to_read
|
||||||
|
sublen -= n_to_read
|
||||||
|
|
||||||
|
f.close()
|
||||||
|
filenum += 1
|
||||||
|
if filenum == self.nfiles: doneflag = True
|
||||||
|
|
||||||
|
if swap:
|
||||||
|
self.SubIDs.byteswap(True)
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue