CosmoBolognaLib
Free Software C++/Python libraries for cosmological calculations
HODCatalogue.cpp
1 /********************************************************************
2  * Copyright (C) 2020 by Federico Zangrandi, Luca Stabellini and *
3  * Sofia Contarini, Federico Marulli *
4  * *
5  * This program is free software; you can redistribute it and/or *
6  * modify it under the terms of the GNU General Public License as *
7  * published by the Free Software Foundation; either version 2 of *
8  * the License, or (at your option) any later version. *
9  * *
10  * This program is distributed in the hope that it will be useful, *
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13  * GNU General Public License for more details. *
14  * *
15  * You should have received a copy of the GNU General Public *
16  * License along with this program; if not, write to the Free *
17  * Software Foundation, Inc., *
18  * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19  ********************************************************************/
20 
37 #include "Catalogue.h"
38 #include <chrono>
39 
40 using namespace std;
41 using namespace cbl;
42 using namespace glob;
43 
44 
45 // ============================================================================
46 
47 
48 double cbl::catalogue::Average_c_Zehavi_2011 (const double x, const double logMmin, const double logsigma_c)
49 {
50  return 0.5*(1.+erf((log10(x)-logMmin)/logsigma_c));
51 }
52 
53 
54 // ============================================================================
55 
56 
57 double cbl::catalogue::Average_s_Zehavi_2011 (const double x, const double M0, const double M1, const double alpha)
58 {
59  return 0.5*pow((x-M0)/M1, alpha);
60 }
61 
62 
63 // ============================================================================
64 
65 
66 double cbl::catalogue::Average_c_Zehavi_2005 (const double M_h, const double M_min)
67 {
68  return (M_h>M_min) ? 1. : 0.;
69 }
70 
71 
72 // ============================================================================
73 
74 
75 double cbl::catalogue::Average_s_Zehavi_2005 (const double x, const double M1, const double alpha)
76 {
77  return pow(x/M1, alpha);
78 }
79 
80 
81 // ============================================================================
82 
83 
84 cbl::catalogue::Catalogue::Catalogue (const Catalogue halo_catalogue, const cosmology::Cosmology &cosm, const HODType HOD_Type, const double threshold, const bool substructures, std::vector<double> parameter)
85 {
86  // MOSTER 10 model:
87 
88  // Compute sigma_c scatter for lognormal distribution Moster2010 for central galaxies, eq. 4.3.7
89  auto fsigma_c = [](double x)
90  {
91  // All the parameters below depend on Halo Mass
92  const double sigma_infinity = 0.1592; // 0.0569;
93  const double sigma_1 = 0.0460; // 0.1204;
94  const double chsi = 4.2503; // 6.3020;
95  const double M_2 = pow(10, 11.8045); // pow(10.,11.9652);
96  //sigma_c SHMR:
97  return sigma_infinity + sigma_1 * (1. - (2. / cbl::par::pi) * atan(chsi * log10(x / M_2)));
98  };
99 
100  // Phi_s normalization of modified Schechter for satellite galaxies, Moster2010
101  auto fPhi_s = [](double x)
102  {
103  const double lamda = 0.8032; //0.8285;
104  const double phi_0 = pow(10., -10.8924); //pow(10.,-11.1622);
105 
106  return phi_0 * pow(x, lamda);
107  };
108 
109  // compute alpha index for the modified Schechter
110  auto falpha_s = [](double x)
111  {
112  const double alpha_infinity = -1.3676; //-1.3740;
113  const double alpha_1 = -0.0524; //-0.0309;
114  const double zeta = 9.5727; //4.3629;
115  const double M_3 = pow(10, 12.3646); //pow(10,12.5730);
116 
117  return alpha_infinity + alpha_1 * (1. - (2. / cbl::par::pi) * atan(zeta * log10(x / M_3)));
118  };
119 
120  // compute minumum stellar mass, in h unit i.e. the minimum stellar
121  // mass of the galaxy sample eq.5.1.6
122  auto mag_mstar = [&cosm](double x)
123  {
124  const double MoverL = 1.;
125  return MoverL*pow(10., (4.77-x)/2.5);
126  };
127 
128  auto startTimer = chrono::steady_clock::now();
129 
130  // threshold of stellar masses
131  double starMass_threshold = 0;
132 
133  // ZEHAVI PARAMETERS INITIALIZATION:
134  // Zehavi11
135  double logMmin = 0.;
136  double logsigma_c = 0.;
137  double M0 = 0.;
138  double M1 = 0.;
139  double alpha = 0.;
140 
141  // Zehavi05
142  double M_min = 0.;
143 
144  // MOSTER10 PARAMETERS INITIALIZATION, CENTRAL:
145  //Moster central
146  double k_c = 0.;
147  double M1_c = 0.;
148  double beta_c = 0.;
149  double gamma_c = 0.;
150  double sigma_c = 0.;
151 
152  // MOSTER10 PARAMETERS INITIALIZATION, SATELLITE:
153  double k_s = 0.;
154  double M1_s = 0.;
155  double beta_s = 0.;
156  double gamma_s = 0.;
157  double Phi_s = 0.;
158  double alpha_s = 0.;
159 
160  // ----- ZEHAVI 05-11 -----
161 
162  // Paramters settings:
163  /*
164  threshold -> input parameter in r-band Magnitude M_{r}.
165  p.[0] = Log M_min: minimum halo mass for hosting central galaxy.
166  p.[1] = Sigma_{log_M}: scatter applied to the smoothed step-function (used in mean occupation number of central galaxies).
167  p.[2] and [3] = Log(M_{0}) and log(M'_{1}): relative to satellite galaxies.
168  p.[3] = alpha: slope of the power-law used to obtain the mean occupation number of satellite galaxies.
169  */
170  if (parameter.size() < 1)
171  parameter = {-99., -99., -99., -99., -99., -99., -99., -99., -99., -99., -99., -99., -99., -99., -99., -99.};
172 
173  // Setting of first 4 parameters based on input threshold:
174  // Zheavi models have minimum stellar mass set by threshold
175  if (HOD_Type==HODType::_Zehavi11_) {
176  if (threshold == -22)
177  starMass_threshold = mag_mstar(-22.);
178  else if (threshold == -21.5)
179  starMass_threshold = mag_mstar(-21.5);
180  else if (threshold == -21.)
181  starMass_threshold = mag_mstar(-21.);
182  else if (threshold == -20.5)
183  starMass_threshold = mag_mstar(-20.5);
184  else if (threshold == -20.)
185  starMass_threshold = mag_mstar(-20.);
186  else if (threshold == -19.5)
187  starMass_threshold = mag_mstar(-19.5);
188  else if (threshold == -19.)
189  starMass_threshold = mag_mstar(-19.);
190  else if (threshold == -18.5)
191  starMass_threshold = mag_mstar(-18.5);
192  else if (threshold == -18.)
193  starMass_threshold = mag_mstar(-18.);
194  else
195  ErrorCBL("Not default parameters available for this threshold", "Catalogue", "HODCatalogue.cpp");
196 
197  for (int ii = 0; ii < 5; ii++) {
198  if (parameter[ii] == -99) {
199  if (ii == 0) {
200  if (threshold == -22)
201  parameter[0] = 14.06;
202  else if (threshold == -21.5)
203  parameter[0] = 13.38;
204  else if (threshold == -21.)
205  parameter[0] = 12.78;
206  else if (threshold == -20.5)
207  parameter[0] = 12.14;
208  else if (threshold == -20.)
209  parameter[0] = 11.83;
210  else if (threshold == -19.5)
211  parameter[0] = 11.57;
212  else if (threshold == -19.)
213  parameter[0] = 11.45;
214  else if (threshold == -18.5)
215  parameter[0] = 11.33;
216  else if (threshold == -18.)
217  parameter[0] = 11.18;
218  else
219  ErrorCBL("Not default parameters available for this threshold", "Catalogue", "HODCatalogue.cpp");
220  }
221  else if (ii == 1) {
222  if (threshold == -22)
223  parameter[1] = 0.71;
224  else if (threshold == -21.5)
225  parameter[1] = 0.69;
226  else if (threshold == -21.)
227  parameter[1] = 0.68;
228  else if (threshold == -20.5)
229  parameter[1] = 0.17;
230  else if (threshold == -20.)
231  parameter[1] = 0.25;
232  else if (threshold == -19.5)
233  parameter[1] = 0.17;
234  else if (threshold == -19.)
235  parameter[1] = 0.19;
236  else if (threshold == -18.5)
237  parameter[1] = 0.26;
238  else if (threshold == -18.)
239  parameter[1] = 0.19;
240  else
241  ErrorCBL("Not default parameters available for this threshold", "Catalogue", "HODCatalogue.cpp");
242  }
243  else if (ii == 2) {
244  if (threshold == -22)
245  parameter[2] = pow(10., 13.72);
246  else if (threshold == -21.5)
247  parameter[2] = pow(10., 13.35);
248  else if (threshold == -21.)
249  parameter[2] = pow(10., 12.71);
250  else if (threshold == -20.5)
251  parameter[2] = pow(10, 11.62);
252  else if (threshold == -20.)
253  parameter[2] = pow(10., 12.35);
254  else if (threshold == -19.5)
255  parameter[2] = pow(10., 12.33);
256  else if (threshold == -19.)
257  parameter[2] = pow(10., 9.77);
258  else if (threshold == -18.5)
259  parameter[2] = pow(10., 8.99);
260  else if (threshold == -18.)
261  parameter[2] = pow(10., 9.81);
262  else
263  ErrorCBL("Not default parameters available for this threshold", "Catalogue", "HODCatalogue.cpp");
264  }
265  else if (ii == 3) {
266  if (threshold == -22)
267  parameter[3] = pow(10, 14.80);
268  else if (threshold == -21.5)
269  parameter[3] = pow(10., 14.20);
270  else if (threshold == -21.)
271  parameter[3] = pow(10., 13.76);
272  else if (threshold == -20.5)
273  parameter[3] = pow(10., 13.43);
274  else if (threshold == -20.)
275  parameter[3] = pow(10., 12.98);
276  else if (threshold == -19.5)
277  parameter[3] = pow(10., 12.75);
278  else if (threshold == -19.)
279  parameter[3] = pow(10., 12.63);
280  else if (threshold == -18.5)
281  parameter[3] = pow(10., 12.50);
282  else if (threshold == -18.)
283  parameter[3] = pow(10., 12.42);
284  else
285  ErrorCBL("Not default parameters available for this threshold", "Catalogue", "HODCatalogue.cpp");
286  }
287  else {
288  if (threshold == -22)
289  parameter[4] = 1.35;
290  else if (threshold == -21.5)
291  parameter[4] = 1.09;
292  else if (threshold == -21.)
293  parameter[4] = 1.15;
294  else if (threshold == -20.5)
295  parameter[4] = 1.15;
296  else if (threshold == -20.)
297  parameter[4] = 1.00;
298  else if (threshold == -19.5)
299  parameter[4] = 0.99;
300  else if (threshold == -19.)
301  parameter[4] = 1.02;
302  else if (threshold == -18.5)
303  parameter[4] = 1.02;
304  else if (threshold == -18.)
305  parameter[4] = 1.04;
306  else
307  ErrorCBL("Not default parameters available for this threshold", "Catalogue", "HODCatalogue.cpp");
308  }
309  }
310  }// END of setting first 4 parameters based on input threshold.
311 
312  // Average naumbers Zehavi11 but stellar mass with Moster10
313 
314  // SETTING PARAMTERS [5] to [15]:
315  /*
316  p.[5] = (m_c / M)_0: normalization of SHMR for central galaxies (eq. 4.3.11).
317  p.[6] = logM_{1c}: log10 of characteristic mass at which the SHMR changes slope for central galaxies.
318  p.[7] and p[8] = beta and gamma coefficents for central galaxies (eq. 4.3.11).
319  p.[9] = sigma: scatter for the log-normal distribution of central galaxies.
320  p.[10] = same as [5] but for satellite galaxies
321  p.[11] = same as [6] but for satellite galaxies
322  p.[12] and [13]= same as [7] ans [8] but for satellite galaxies
323  p.[14] = Phi_s: parametrization by Moster10, eq.4.3.9
324  p.[15] = alpha_s: parametrization by Moster10, eq.4.3.10
325  */
326 
327  if (parameter[5] == -99)
328  parameter[5] = 0.0267; // norma SHMR_c
329  if (parameter[6] == -99)
330  parameter[6] = pow(10, 11.9347); //break SHMR_c
331  if (parameter[7] == -99)
332  parameter[7] = 1.0059; //beta_c SHMR_c
333  if (parameter[8] == -99)
334  parameter[8] = 0.5611; //gamma_c SHMR_c
335  if (parameter[9] == -99)
336  {
337  // sigma_c, default value setted from halo mass
338  //cout << par::col_green << "Using default sigma_c" << par::col_default << endl;
339  //parameter[ii]=sigma_c(;
340  }
341  if (parameter[10] == -99)
342  parameter[10] = 0.0186; // norma SHMR_s
343  if (parameter[11] == -99)
344  parameter[11] = pow(10, 12.1988); // break SHMR_s
345  if (parameter[12] == -99)
346  parameter[12] = 0.7817; // beta_s SHMR_s
347  if (parameter[13] == -99)
348  parameter[13] = 0.7334; // gamma_s SHMR_s
349  if (parameter[14] == -99)
350  { // PHI_s, default value setted from halo mass
351 
352  //cout << par::col_green << "Using default Phi_s" << par::col_default << endl;
353  //parameter[ii]=Phi_s;
354  }
355  if (parameter[15] == -99)
356  {
357  // alpha_s, default value setted from halo mass
358  //
359  //cout << par::col_green << "Using default alpha_s" << par::col_default << endl;
360  // parameter[ii]=alpha_s;
361  }
362 
363  //HOD parameter Zehavi11
364  logMmin = parameter[0];
365  logsigma_c = parameter[1];
366  M0 = parameter[2];
367  M1 = parameter[3];
368  alpha = parameter[4];
369 
370  //Moster central stellar masses
371  k_c = parameter[5];
372  M1_c = parameter[6];
373  beta_c = parameter[7];
374  gamma_c = parameter[8];
375  sigma_c = parameter[9];
376 
377  //Moster satallite
378  k_s = parameter[10];
379  M1_s = parameter[11];
380  beta_s = parameter[12];
381  gamma_s = parameter[13];
382  Phi_s = parameter[14];
383  alpha_s = parameter[15];
384 
385  cout << " Chosen parameters for HOD: " << endl;
386  cout << " LogMmin = " << logMmin << endl;
387  cout << " Logsigma_c = " << logsigma_c << endl;
388  cout << " M0 = " << M0 << " M_sun/h" << endl;
389  cout << " M1 = " << M1 << " M_sun/h" << endl;
390  cout << " alpha = " << alpha << endl;
391  cout << " Minimum stellar mass = " << starMass_threshold << " M_sun/h" << endl
392  << endl;
393 
394  cout << " Chosen parameters for stellar masses: " << endl;
395  cout << " k_c = " << k_c << endl;
396  cout << " M1_c = " << M1_c << " M_sun" << endl;
397  cout << " beta_c = " << beta_c << endl;
398  cout << " gamma_c = " << gamma_c << endl;
399  cout << " sigma_c = " << sigma_c << endl;
400 
401  cout << " k_s = " << k_s << endl;
402  cout << " M1_s = " << M1_s << " M_sun" << endl;
403  cout << " beta_s = " << beta_s << endl;
404  cout << " gamma_s = " << gamma_s << endl;
405  cout << " Phi_s = " << Phi_s << endl;
406  cout << " alpha_s = " << alpha_s << endl
407  << endl;
408  }
409 
410  else if (HOD_Type == HODType::_Zehavi05_) {
411  if (threshold == -22)
412  starMass_threshold = mag_mstar(-22.);
413  else if (threshold == -21.5)
414  starMass_threshold = mag_mstar(-21.5);
415  else if (threshold == -21.)
416  starMass_threshold = mag_mstar(-21.);
417  else if (threshold == -20.5)
418  starMass_threshold = mag_mstar(-20.5);
419  else if (threshold == -20.)
420  starMass_threshold = mag_mstar(-20.);
421  else if (threshold == -19.5)
422  starMass_threshold = mag_mstar(-19.5);
423  else if (threshold == -19.)
424  starMass_threshold = mag_mstar(-19.);
425  else if (threshold == -18.5)
426  starMass_threshold = mag_mstar(-18.5);
427  else if (threshold == -18.)
428  starMass_threshold = mag_mstar(-18.);
429  else
430  ErrorCBL("Not default parameters available for this threshold", "Catalogue", "HODCatalogue.cpp");
431 
432  for (int ii = 0; ii < 3; ii++) {
433  if (parameter[ii] == -99) {
434  if (ii == 0) {
435  if (threshold == -22)
436  parameter[0] = pow(10, 13.91);
437  else if (threshold == -21.5)
438  parameter[0] = pow(10, 13.27);
439  else if (threshold == -21.)
440  parameter[0] = pow(10, 12.72);
441  else if (threshold == -20.5)
442  parameter[0] = pow(10, 12.30);
443  else if (threshold == -20.)
444  parameter[0] = pow(10, 12.01);
445  else if (threshold == -19.5)
446  parameter[0] = pow(10, 11.76);
447  else if (threshold == -19.)
448  parameter[0] = pow(10, 11.59);
449  else if (threshold == -18.5)
450  parameter[0] = pow(10, 11.44);
451  else if (threshold == -18.)
452  parameter[0] = pow(10, 11.27);
453  else
454  ErrorCBL("Not default parameters available for this threshold", "Catalogue", "HODCatalogue.cpp");
455  }
456  else if (ii == 1) {
457  if (threshold == -22)
458  parameter[1] = pow(10, 14.92);
459  else if (threshold == -21.5)
460  parameter[1] = pow(10., 14.60);
461  else if (threshold == -21.)
462  parameter[1] = pow(10., 14.09);
463  else if (threshold == -20.5)
464  parameter[1] = pow(10., 13.67);
465  else if (threshold == -20.)
466  parameter[1] = pow(10., 13.42);
467  else if (threshold == -19.5)
468  parameter[1] = pow(10., 13.15);
469  else if (threshold == -19.)
470  parameter[1] = pow(10., 12.94);
471  else if (threshold == -18.5)
472  parameter[1] = pow(10., 12.77);
473  else if (threshold == -18.)
474  parameter[1] = pow(10., 12.57);
475  else
476  ErrorCBL("Not default parameter available for this threshold", "Catalogue", "HODCatalogue.cpp");
477  }
478  else {
479  if (threshold == -22)
480  parameter[2] = 1.43;
481  else if (threshold == -21.5)
482  parameter[2] = 1.94;
483  else if (threshold == -21.)
484  parameter[2] = 1.39;
485  else if (threshold == -20.5)
486  parameter[2] = 1.21;
487  else if (threshold == -20.)
488  parameter[2] = 1.16;
489  else if (threshold == -19.5)
490  parameter[2] = 1.13;
491  else if (threshold == -19.)
492  parameter[2] = 1.08;
493  else if (threshold == -18.5)
494  parameter[2] = 1.01;
495  else if (threshold == -18.)
496  parameter[2] = 0.92;
497  else
498  ErrorCBL("not default parameter available for this threshold", "Catalogue", "HODCatalogue.cpp");
499  }
500  }
501  }
502  //for (int ii=0; ii<10; ii++) {
503  if (parameter[3] == -99)
504  parameter[3] = 0.0267; //norm SHMR_c
505  if (parameter[4] == -99)
506  parameter[4] = pow(10, 11.9347); //break SHMR_c
507  if (parameter[5] == -99)
508  parameter[5] = 1.0059; //beta_c SHMR_c
509  if (parameter[6] == -99)
510  parameter[6] = 0.5611; //gamma_c SHMR_c
511  if (parameter[7] == -99)
512  {
513  //cout << par::col_green << "If sigma_c=-99 it will be setted using the halo mass..." << par::col_default << endl;
514  //parameter[ii]=sigma_c(;
515  }
516  if (parameter[8] == -99)
517  parameter[8] = 0.0186; // norma SHMR_s
518  if (parameter[9] == -99)
519  parameter[9] = pow(10, 12.1988); // break SHMR_s
520  if (parameter[10] == -99)
521  parameter[10] = 0.7817; // beta_s SHMR_s
522  if (parameter[11] == -99)
523  parameter[11] = 0.7334; // gamma_s SHMR_s
524  if (parameter[12] == -99)
525  {
526  // PHI_s, default value setted from halo mass
527  //cout << par::col_green << "Using default PHI_s" << par::col_default << endl;
528  //parameter[ii]=Phi_s;
529  }
530  if (parameter[13] == -99)
531  { // alpha_s
532  //cout << par::col_green << "If alpha_s=-99 it will be setted using the halo mass..." << par::col_default << endl;
533  // parameter[ii]=alpha_s;
534  }
535 
536  M_min = parameter[0];
537  M1 = parameter[1];
538  alpha = parameter[2];
539  //Moster stellar mass centra
540  k_c = parameter[3];
541  M1_c = parameter[4];
542  beta_c = parameter[5];
543  gamma_c = parameter[6];
544  sigma_c = parameter[7];
545  //Moster satallite
546  k_s = parameter[8];
547  M1_s = parameter[9];
548  beta_s = parameter[10];
549  gamma_s = parameter[11];
550  Phi_s = parameter[12];
551  alpha_s = parameter[13];
552 
553  coutCBL << " Chosen parameters for HOD: " << endl;
554  coutCBL << " M_min = " << M_min << " M_sun/h" << endl;
555  coutCBL << " M1 = " << M1 << " M_sun/h" << endl;
556  coutCBL << " alpha = " << alpha << endl;
557  coutCBL << " Minimum stellar mass = " << starMass_threshold << "M_sun/h" << endl
558  << endl;
559 
560  coutCBL << " Chosen parameters for stellar masses: " << endl;
561  coutCBL << " k_c = " << k_c << endl;
562  coutCBL << " M1_c = " << M1_c << " M_sun" << endl;
563  coutCBL << " beta_c = " << beta_c << endl;
564  coutCBL << " gamma_c = " << gamma_c << endl;
565  coutCBL << " sigma_c = " << sigma_c << endl;
566 
567  coutCBL << " k_s = " << k_s << endl;
568  coutCBL << " M1_s = " << M1_s << " M_sun" << endl;
569  coutCBL << " beta_s = " << beta_s << endl;
570  coutCBL << " gamma_s = " << gamma_s << endl;
571  coutCBL << " Phi_s = " << Phi_s << endl;
572  coutCBL << " alpha_s = " << alpha_s << endl << endl;
573  }
574 
575 
576  // ----- Moster et al. 2010 -----
577 
578  else if (HOD_Type == HODType::_Moster10_)
579  {
580  // cout<<"Warning: threshold in Moster is minimum stellar mass!"<<endl;
581  if (threshold < 0.)
582  ErrorCBL("Warning: threshold in Moster is minimum stellar mass!", "Catalogue", "HODCatalogue.cpp");
583 
584  //for (int ii=0; ii<10; ii++) {
585  // if(parameter[ii]==-99){
586  if (parameter[0] == -99)
587  parameter[0] = 0.0297; // 0.0267; //norm SHMR_c //
588  if (parameter[1] == -99)
589  parameter[1] = pow(10., 11.9008); // pow(10,11.9347);//break SHMR_c //
590  if (parameter[2] == -99)
591  parameter[2] = 1.0757; //← w scatter// 1.0059; //beta_c SHMR_c //
592  if (parameter[3] == -99)
593  parameter[3] = 0.6310; //← w scatter// 0.5611; //gamma_c SHMR_c //
594  if (parameter[4] == -99)
595  {
596  //cout << par::col_green << "If sigma_c=-99 it will be setted using the halo mass..." << par::col_default << endl;
597  //parameter[ii]=sigma_c;
598  }
599  if (parameter[5] == -99)
600  parameter[5] = 0.0198; // 0.0186; // norma SHMR_s //
601  if (parameter[6] == -99)
602  parameter[6] = pow(10., 12.0640); //pow(10,12.1988); // break SHMR_s //
603  if (parameter[7] == -99)
604  parameter[7] = 0.8097; //0.7817; // beta_s SHMR_s //
605  if (parameter[8] == -99)
606  parameter[8] = 0.6910; //← w scatter//0.7334; // gamma_s SHMR_s //
607  if (parameter[9] == -99)
608  { // PHI_s
609 
610  //cout << par::col_green << "If Phi_s= -99 it will be setted using the halo mass..." << par::col_default << endl;
611  //parameter[ii]=Phi_s;
612  }
613  if (parameter[10] == -99)
614  { // alpha_s
615  //cout << par::col_green << "If alpha_s=-99 it will be setted using the halo mass..." << par::col_default << endl;
616  // parameter[ii]=alpha_s;
617  }
618 
619  starMass_threshold = threshold;
620 
621  k_c = parameter[0];
622  M1_c = parameter[1];
623  beta_c = parameter[2];
624  gamma_c = parameter[3];
625  sigma_c = parameter[4];
626  //Moster satallite
627  k_s = parameter[5];
628  M1_s = parameter[6];
629  beta_s = parameter[7];
630  gamma_s = parameter[8];
631  Phi_s = parameter[9];
632  alpha_s = parameter[10];
633 
634  coutCBL << par::col_green << "Used parameters(-99->set default value from halo mass):" << par::col_default << endl;
635  coutCBL << " k_c = " << k_c << endl;
636  coutCBL << " M1_c = " << M1_c << " M_sun" << endl;
637  coutCBL << " beta_c = " << beta_c << endl;
638  coutCBL << " gamma_c = " << gamma_c << endl;
639  coutCBL << " sigma_c = " << sigma_c << endl;
640 
641  coutCBL << " k_s = " << k_s << endl;
642  coutCBL << " M1_s = " << M1_s << " M_sun" << endl;
643  coutCBL << " beta_s = " << beta_s << endl;
644  coutCBL << " gamma_s = " << gamma_s << endl;
645  coutCBL << " Phi_s = " << Phi_s << endl;
646  coutCBL << " alpha_s = " << alpha_s << endl << endl;
647  }
648 
649  else
650  ErrorCBL("HOD_type not available...", "Catalogue", "HODCatalogue.cpp");
651 
652 
653  // -----------------------------------------------------------
654  // --------------- populate the halo catalogue ---------------
655  // -----------------------------------------------------------
656 
657  coutCBL << par::col_green << "Creating HOD catalogue" << par::col_default << endl;
658  // Vector which contain parameters to extract the stellar mass for central galaxies
659  vector<double> par_stellar_c = {k_c, M1_c, beta_c, gamma_c, sigma_c};
660 
661  // Conditional mass function Moster2010 for central galaxies, eq:4.3.6
662  const cbl::distribution_func CMF_c = [&cosm, &fsigma_c, &starMass_threshold] (double x, const shared_ptr<void> modelInput, vector<double> par_stellar_c)
663  {
664  const vector<double> fix_par = *static_pointer_cast<std::vector<double>>(modelInput);
665  if (par_stellar_c[4] == -99)
666  par_stellar_c[4] = fsigma_c(fix_par[0]);
667  double m_c = 2. * fix_par[0] * par_stellar_c[0] * pow(pow(fix_par[0] / par_stellar_c[1], -par_stellar_c[2]) + pow(fix_par[0] / par_stellar_c[1], par_stellar_c[3]), -1);
668 
669  return (1. / (par_stellar_c[4] * sqrt(2. * cbl::par::pi) * x * log(10))) * exp(-pow(log10(x / m_c) / (sqrt(2) * par_stellar_c[4]), 2.));
670  };
671 
672  // Moster et al 2010 distribution probability of stellar mass for satellite galaxies, IMF: Kroupa
673 
674  vector<double> par_stellar_s = {k_s, M1_s, beta_s, gamma_s, Phi_s, alpha_s};
675 
676  //Conditional mass function Moster2010 for satellite galaxies
677  const cbl::distribution_func CMF_s = [&cosm, &fPhi_s, &falpha_s](double x, const shared_ptr<void> modelInput, vector<double> par_stellar_s)
678  {
679  const vector<double> fix_par = *static_pointer_cast<std::vector<double>>(modelInput);
680  if (par_stellar_s[4] == -99)
681  par_stellar_s[4] = fPhi_s(fix_par[0]);
682  if (par_stellar_s[5] == -99)
683  par_stellar_s[5] = falpha_s(fix_par[0]);
684  double m_s = 2. * fix_par[0] * par_stellar_s[0] * pow(pow(fix_par[0] / par_stellar_s[1], -par_stellar_s[2]) + pow(fix_par[0] / par_stellar_s[1], par_stellar_s[3]), -1.);
685 
686  return (par_stellar_s[4] / m_s) * pow(x / m_s, par_stellar_s[5]) * exp(-pow((x / m_s), 2.));
687  };
688 
689 
690  // -------------------------------------------------
691  // --------------- average functions ---------------
692  // -------------------------------------------------
693 
694  //Average numbers of galaxies from CMF for central and satellite galaxies Moster et. al 2010
695 
696  auto Average_c_Moster_2010 = [&cosm, &fsigma_c] (double x, double star_threshold, double k_c, double M1_c, double beta_c, double gamma_c, double sigma_c)
697  {
698  if (sigma_c == -99)
699  sigma_c = fsigma_c(x);
700  double m_c = 2. * x * k_c / (pow(x / M1_c, -beta_c) + pow(x / M1_c, gamma_c));
701 
702  return 0.5 * (1 - erf(log10(star_threshold / m_c) / (sqrt(2) * sigma_c))); //threshold
703  };
704 
705  auto Average_s_Moster_2010 = [&fPhi_s, &falpha_s](double x, double star_threshold, double k_s, double M1_s, double beta_s, double gamma_s, double Phi_s, double alpha_s)
706  {
707  if (Phi_s == -99)
708  Phi_s = fPhi_s(x);
709  if (alpha_s == -99)
710  alpha_s = falpha_s(x);
711  double m_s = 2. * x * k_s * pow(pow(x / M1_s, -beta_s) + pow(x / M1_s, gamma_s), -1.);
712  double lower = pow(star_threshold / m_s, 2.);
713 
714  return (Phi_s / 2.) * gsl_sf_gamma_inc(0.5 * alpha_s + 0.5, lower);
715  };
716 
717 
718  //-------------------------------------------------------
719  // --------------- sub-halo mass function ---------------
720  //-------------------------------------------------------
721 
722  const double z = 0.;
723  vector<double> parameter_NFW{z};
724 
725 
726  // Giocoli et al. 2010/2011
727 
728  const double A = 9.33 * 1e-4;
729  const double zres = sqrt(1 + z);
730  const double alpha_SubHalo = -0.9;
731  const double betha_SubHalo = -12.2715;
732 
733  vector<double> par_SubHalo{A, zres, alpha_SubHalo, betha_SubHalo};
734 
735  const cbl::distribution_func SubMass = [&] (double lx, const shared_ptr<void> modelInput, const vector<double> par_SubHalo)
736  {
737  const std::vector<double> fix_par_h = *static_pointer_cast<std::vector<double>>(modelInput);
738  double x = pow(10., lx);
739  return pow(x, par_SubHalo[2] + 1) * exp(par_SubHalo[3] * pow(x, 3));
740  };
741 
742 
743  //-------------------------------------------------
744  // --------------- galaxy positions ---------------
745  //-------------------------------------------------
746 
747  const cbl::distribution_func NFW_profile = [&cosm] (double x, const shared_ptr<void> modelInput, const vector<double> parameter_NFW)
748  {
749  const vector<double> fix_par_h = *static_pointer_cast<std::vector<double>>(modelInput);
750  double r_vir = cosm.r_vir(fix_par_h[0], parameter_NFW[0]);
751  double c_vir = cosm.concentration_NFW_Duffy(fix_par_h[0], parameter_NFW[0]);
752  double r_s = r_vir / c_vir;
753  double A = pow(r_s + r_vir, 2) / pow(r_s, 2);
754 
755  return A * x / (pow(1 + x * c_vir, 2));
756  };
757 
758 
759  // -------------------------------------------
760  // --------------- infall mass ---------------
761  // -------------------------------------------
762 
763  auto InfallMass = [&cosm] (double x, const shared_ptr<void> modelInput, const vector<double> par_infall)
764  {
765  const vector<double> fix_par_h = *static_pointer_cast<std::vector<double>>(modelInput);
766  const double z = 0;
767  double M_infall = par_infall[0] * pow(pow(x / cosm.r_vir(fix_par_h[0], z), 2. / 3.), -1); //0.65!!
768 
769  return M_infall;
770  };
771 
772 
773  //-------------------------------------------------------------------------------------------------------------------
774  //-------------------------------------------------------------------------------------------------------------------
775 
776 
777  const double M_stellarmax = pow(10., 12.);
778 
779  // default values (refer to the GSL documentation for different choiches)
780  const int limit_size = 1000;
781  const int rule = 6;
782  const double prec = 1.e-5;
783  // set h of the input cosmology
784  const double h = cosm.hh();
785 
786  const double x_NFW_min = 1.e-5; //r/r_vir
787  const double x_NFW_max = 1.; //r/r_vir
788  //const double v_sat_min = -1e10; //km/s
789  //const double v_sat_max = 1e10; //km/s
790 
791  const int N_halo = halo_catalogue.nObjects();
792 
793  vector<bool> occupied(N_halo, false);
794  std::default_random_engine generator; //for poisson number
795  std::vector<std::vector<std::shared_ptr<Object>>> support_tot(N_halo);
796 
797  // start the parallelization
798 #pragma omp parallel num_threads(omp_get_max_threads())
799 
800  {
801 #pragma omp for schedule(dynamic)
802 
803  for (int i = 0; i < N_halo; ++i) {
804 
805  if (i > N_halo)
806  ErrorCBL("number of iterations exeed number of halos, possible infinite loop", "Catalogue", "HODCatalogue.cpp");
807 
808 #pragma omp critical // <--means: only a thread EXECUTE ONLY the NEXT LINE:
809  coutCBL << "..." << int(double(i) / double(N_halo) * 100) << "% completed\r"; cout.flush();
810 
811  // Parallelization continue here:
812 
813  // vector used to support the parallelization
814 
815  std::vector<std::shared_ptr<Object>> support;
816  const int seedtheta = 333 + i;
817  const int seedphi = 8782 + i;
818  const int seed = 34562 + i;
819 
820  // properties of halos
821  double halo_mass = halo_catalogue.mass(i);
822  const double halo_catalogue_x = halo_catalogue.xx(i);
823  const double halo_catalogue_y = halo_catalogue.yy(i);
824  const double halo_catalogue_z = halo_catalogue.zz(i);
825 
826  // pointer for functions
827  const vector<double> vect{halo_mass / h}; // Msun unit
828  const vector<double> vect_h{halo_mass}; // Unit of h if the input catalogue is in unit of h
829 
830  auto fix_par = make_shared<vector<double>>(vect); // Used for Moster
831  auto fix_par_h = make_shared<vector<double>>(vect_h); // Used for everything else
832 
833  // mass halo in solar unit
834  const double halo_mass_wo_h = halo_mass / h;
835 
836 
837  // ---------------------------------------------------------------------------------------------------
838  // --------------- computing the average number of galaxy using function defined above ---------------
839  // ---------------------------------------------------------------------------------------------------
840 
841  double Navg_c = 0.;
842  if (HOD_Type == HODType::_Zehavi11_)
843  Navg_c = Average_c_Zehavi_2011(halo_mass, logMmin, logsigma_c);
844  if (HOD_Type == HODType::_Zehavi05_)
845  Navg_c = Average_c_Zehavi_2005(halo_mass, M_min);
846  if (HOD_Type == HODType::_Moster10_)
847  Navg_c = Average_c_Moster_2010(halo_mass_wo_h, starMass_threshold, k_c, M1_c, beta_c, gamma_c, sigma_c);
848 
849  random::CustomDistributionRandomNumbers StellarMass_c(CMF_c, fix_par, par_stellar_c, seed, starMass_threshold, M_stellarmax);
850 
851  // ------------------------------------------------
852  // --------------- central galaxies ---------------
853  // ------------------------------------------------
854 
855  // poiter for the central galaxies
856  auto galaxy_c = std::make_shared<cbl::catalogue::Galaxy>();
857  auto number_c = nearbyint(Navg_c);
858 
859  for (size_t j = 0; j < number_c; ++j) {
860  occupied[i] = true;
861  galaxy_c->set_xx(halo_catalogue_x);
862  galaxy_c->set_yy(halo_catalogue_y);
863  galaxy_c->set_zz(halo_catalogue_z);
864  galaxy_c->set_ID(i);
865  // galaxy_c -> set_IDHost(halo_catalogue_ID);
866  galaxy_c->set_mstar(StellarMass_c());
867  galaxy_c->set_massinfall(halo_mass); //used to write a file
868  galaxy_c->set_mass(halo_mass);
869  galaxy_c->set_galaxyTag(0);
870 
871  support_tot[i].emplace_back(galaxy_c);
872  }
873 
874 
875  // --------------------------------------------------
876  // --------------- satellite galaxies ---------------
877  // --------------------------------------------------
878 
879  if (occupied[i]) {
880  double Navg_s = 0.;
881  if (HOD_Type == HODType::_Zehavi11_)
882  Navg_s = Average_s_Zehavi_2011(halo_mass, M0, M1, alpha);
883  else if (HOD_Type == HODType::_Zehavi05_)
884  Navg_s = Average_s_Zehavi_2005(halo_mass, M1, alpha);
885  else if (HOD_Type == HODType::_Moster10_)
886  Navg_s = Average_s_Moster_2010(halo_mass_wo_h, starMass_threshold, k_s, M1_s, beta_s, gamma_s, Phi_s, alpha_s);
887 
888  random::CustomDistributionRandomNumbers StellarMass_s(CMF_s, fix_par, par_stellar_s, seed, starMass_threshold, M_stellarmax); //fix_par_s per massa sotto aloni
889  random::CustomDistributionRandomNumbers Radius(NFW_profile, fix_par_h, parameter_NFW, seed, x_NFW_min, x_NFW_max);
890  random::UniformRandomNumbers Theta(0., cbl::par::pi, seedtheta);
891  random::UniformRandomNumbers Phi(0., 2. * cbl::par::pi, seedphi);
892 
893  std::poisson_distribution<int> Poisson_s(Navg_s);
894  int number_s = Poisson_s(generator);
895 
896  // Extracting the stellar mass of satellite galaxies
897  vector<double> stellarmass_s(number_s);
898  for (int j = 0; j < number_s; ++j)
899  stellarmass_s[j] = StellarMass_s();
900 
901  //integration for the mass fraction
902  if (number_s > 0) {
903 
904  std::function<double(double)> shmf = [&par_SubHalo, &vect_h](const double lx)
905  {
906  double x = pow(10., lx);
907 
908  return (x * vect_h[0]) * par_SubHalo[0] * par_SubHalo[1] * pow(x * vect_h[0], par_SubHalo[2]) * exp(par_SubHalo[3] * pow(x, 3)) * log(10);
909  };
910 
911  double MinLogExtraction = log10(starMass_threshold / halo_mass);
912  //double f_min=log10(1.e10/halo_mass);
913  double f = cbl::wrapper::gsl::GSL_integrate_qag(shmf, -5, 0., prec, limit_size, rule);
914  double MaxLogExtraction = log10(f);
915 
916  random::CustomDistributionRandomNumbers SubHaloMass(SubMass, fix_par_h, par_SubHalo, seed, MinLogExtraction, MaxLogExtraction);
917 
918  const double a = 1.e-4;
919  double delta = 0.2 + a * number_s;
920  int retryCounter = 0;
921 
922  vector<double> subhalomass = {};
923 
924 
925  // if substructure is true, compute the right subhalo mass fraction
926 
927  if (substructures) {
928  vector<double> temp_subtot;
929  double temp_sum;
930  int temp_count;
931  double comp_f;
932  int counter_s = 0;
933 
934  while (true) {
935  retryCounter++;
936  temp_subtot = {};
937  temp_sum = 0;
938  temp_count = 0;
939 
940  while (temp_sum < 1. || temp_count < number_s) {
941  temp_subtot.emplace_back(pow(10., SubHaloMass()));
942  temp_sum += temp_subtot[temp_subtot.size() - 1];
943  temp_count++;
944  }
945 
946  counter_s = number_s;
947  comp_f = 0;
948  for (int jj = 0; jj < number_s; jj++)
949  comp_f += temp_subtot[jj];
950  if (comp_f < f + f * delta / 2.) {
951  while (!(comp_f > f - f * delta / 2. && comp_f < f + f * delta / 2.)) {
952  counter_s++;
953  comp_f += temp_subtot[counter_s - 1];
954  if (comp_f > f + f * delta / 2.)
955  break;
956  }
957 
958  if (comp_f > f - f * delta / 2. && comp_f < f + f * delta / 2.)
959  break;
960  }
961  }
962 
963  for (int kk = 0; kk < counter_s; kk++)
964  subhalomass.emplace_back(temp_subtot[kk] * halo_mass);
965 
966  // If you are in hurry we can save your time! But the substructures lose their meaning.
967  }
968  else
969  for (int j = 0; j < number_s; ++j)
970  subhalomass.emplace_back(pow(10, SubHaloMass()) * halo_mass);
971 
972  double Sum = 0;
973  for (size_t j = 0; j < subhalomass.size(); j++)
974  Sum += subhalomass[j];
975 
976  if (subhalomass.size() > 0) {
977  std::sort(subhalomass.begin(), subhalomass.end(), greater<double>());
978  std::sort(stellarmass_s.begin(), stellarmass_s.end(), greater<double>());
979 
980  for (int j = 0; j < number_s; ++j) {
981  auto galaxy_s = std::make_shared<cbl::catalogue::Galaxy>();
982 
983  vector<double> par_infall{subhalomass[j]};
984  const double radius = cosm.r_vir(halo_mass, z) * Radius();
985  const double theta = Theta();
986  const double phi = Phi();
987  double M_infall = InfallMass(radius, fix_par_h, par_infall);
988 
989  galaxy_s->set_xx(halo_catalogue_x + radius * sin(theta) * cos(phi));
990  galaxy_s->set_yy(halo_catalogue_y + radius * sin(theta) * sin(phi));
991  galaxy_s->set_zz(halo_catalogue_z + radius * cos(theta));
992  galaxy_s->set_ID(i);
993  galaxy_s->set_mstar(stellarmass_s[j] * h);
994  galaxy_s->set_massinfall(M_infall);
995  galaxy_s->set_mass(subhalomass[j]);
996  galaxy_s->set_galaxyTag(1);
997 
998  support_tot[i].emplace_back(galaxy_s);
999  }
1000  }
1001  }
1002  }
1003  }
1004  }
1005 
1006  // End of parallelisation all the information are put toghether
1007 
1008  for (int i=0; i<N_halo; ++i)
1009  for (size_t j = 0; j < support_tot[i].size(); j++)
1010  m_object.emplace_back(support_tot[i][j]);
1011 
1012  if (HOD_Type!=HODType::_Zehavi11_) {
1013  (void)(logMmin);
1014  (void)(logsigma_c);
1015  (void)(M0);
1016  (void)(M1);
1017  (void)(alpha);
1018  }
1019 
1020  if (HOD_Type!=HODType::_Zehavi05_) {
1021  (void)(M_min);
1022  (void)(M1);
1023  (void)(alpha);
1024  }
1025 
1026  cout.flush();
1027  coutCBL << "\n ...Done!" << endl;
1028 
1029  auto endTimer = chrono::steady_clock::now();
1030 
1031  float seconds = chrono::duration_cast<chrono::seconds>(endTimer - startTimer).count();
1032 
1033 
1034  coutCBL << "Time spent to compute: " << seconds << " seconds " << endl;
1035  //coutCBL << "Time spent to compute: " << seconds / 60. << " minutes " << endl;
1036  //coutCBL << "Time spent to compute: " << seconds / 3600. << " hours " << endl;
1037  coutCBL << "Writing time log file: timeLog.txt" << endl;
1038  cout << endl;
1039 
1040  // Create and open the timelog file
1041  ofstream timeLogFile("./output/timelog.txt");
1042 
1043  // Write to the file the timings
1044  timeLogFile << "Time spent to compute: " << seconds << " seconds " << endl;
1045 
1046  // Close the timeLog file
1047  timeLogFile.close();
1048 
1049 }
The class Catalogue
#define coutCBL
CBL print message.
Definition: Kernel.h:734
The class Catalogue.
Definition: Catalogue.h:654
Catalogue()=default
default constructor
double yy(const int i) const
get the private member Catalogue::m_object[i]->m_yy
Definition: Catalogue.h:1814
double mass(const int i) const
get the private member Catalogue::m_object[i]->m_mass
Definition: Catalogue.h:2023
size_t nObjects() const
get the number of objects of the catalogue
Definition: Catalogue.h:2264
double xx(const int i) const
get the private member Catalogue::m_object[i]->m_xx
Definition: Catalogue.h:1807
double zz(const int i) const
get the private member Catalogue::m_object[i]->m_zz
Definition: Catalogue.h:1821
The class Cosmology.
Definition: Cosmology.h:277
double hh() const
get the private member Cosmology::m_hh
Definition: Cosmology.h:1191
double r_vir(const double M_vir, const double redshift, const std::string author="BryanNorman", const bool unit1=false) const
the virial radius, given the virial mass and the redshift
Definition: Cosmology.cpp:1331
double concentration_NFW_Duffy(const double Mass, const double redshift, const std::string halo_def="vir") const
the halo concentration-mass relation for NFW prfile and Duffy model
Definition: Cosmology.cpp:1461
The class CustomDistributionRandomNumbers.
The class UniformRandomNumbers.
static const std::string col_green
green colour (used when printing something on the screen)
Definition: Constants.h:309
static const std::string col_default
default colour (used when printing something on the screen)
Definition: Constants.h:297
static const double pi
: the ratio of a circle's circumference to its diameter
Definition: Constants.h:199
static const double alpha
: the fine-structure constant
Definition: Constants.h:233
double Average_c_Zehavi_2005(const double x, const double Mmin)
return the average number of central galaies inside an halo of mass x
double Average_c_Zehavi_2011(const double x, const double logMmin, const double logsigma_c)
return the average number of central galaies inside an halo of mass x
HODType
type of HOD catalogue, which corresponds to the authors of the calibrated HOD model
Definition: Catalogue.h:426
double Average_s_Zehavi_2005(const double x, const double alpha, const double M1)
return the average number of satellite galaies per halo of mass x
double Average_s_Zehavi_2011(const double x, const double M0, const double M1, const double alpha)
return the average number of satellite galaies per halo of mass x
double GSL_integrate_qag(gsl_function Func, const double a, const double b, const double rel_err=1.e-3, const double abs_err=0, const int limit_size=1000, const int rule=6)
integral, computed using the GSL qag method
Definition: GSLwrapper.cpp:180
The global namespace of the CosmoBolognaLib
Definition: CAMB.h:38
T Radius(const T Mass, const T Rho)
the radius of a sphere of a given mass and density
Definition: Func.h:1220
int ErrorCBL(const std::string msg, const std::string functionCBL, const std::string fileCBL, const cbl::glob::ExitCode exitCode=cbl::glob::ExitCode::_error_)
throw an exception: it is used for handling exceptions inside the CosmoBolognaLib
Definition: Kernel.h:780
std::function< double(double, std::shared_ptr< void >, std::vector< double >)> distribution_func
generic distribution function
Definition: RandomNumbers.h:50