mirror of
https://github.com/Richard-Sti/csiborgtools_public.git
synced 2025-05-13 06:01:13 +00:00
Fix overlap runs (#125)
* Update nb * Update script * Update script * Rename * Update script * Update script * Remove warning * Ignore minors when extracting MAH * Fix paths bug * Move notebooks * Move files * Rename and delete things * Rename file * Move file * Rename things * Remove old print statement * Add basic MAH plot * Add random MAH path * Output snapshot numbers * Add MAH random extraction * Fix redshift bug * Edit script * Add extracting random MAH * Little updates * Add CB2 redshift * Add some caching * Add diagnostic plots * Add caching * Minor updates * Update nb * Update notebook * Update script * Add Sorce randoms * Add CB2 varysmall * Update nb * Update nb * Update nb * Use catalogue HMF * Move definition of radec2galactic * Update nb * Update import * Update import * Add galatic coords to catalogues * Update nb
This commit is contained in:
parent
c71f5a8513
commit
ee222cd010
31 changed files with 1813 additions and 798 deletions
|
@ -19,8 +19,9 @@ from .utils import (center_of_mass, delta2ncells, number_counts,
|
|||
binned_statistic, cosine_similarity, fprint, # noqa
|
||||
hms_to_degrees, dms_to_degrees, great_circle_distance, # noqa
|
||||
radec_to_cartesian, cartesian_to_radec, # noqa
|
||||
thin_samples_by_acl, numpyro_gof) # noqa
|
||||
from .params import paths_glamdring, simname2boxsize, simname2Omega_m # noqa
|
||||
thin_samples_by_acl, numpyro_gof, radec_to_galactic) # noqa
|
||||
from .params import (paths_glamdring, simname2boxsize, simname2Omega_m, # noqa
|
||||
snap2redshift) # noqa
|
||||
|
||||
|
||||
###############################################################################
|
||||
|
|
|
@ -26,8 +26,6 @@ from warnings import catch_warnings, simplefilter, warn
|
|||
import numpy as np
|
||||
import numpyro
|
||||
import numpyro.distributions as dist
|
||||
from astropy import units as u
|
||||
from astropy.coordinates import SkyCoord
|
||||
from astropy.cosmology import FlatLambdaCDM
|
||||
from h5py import File
|
||||
from jax import jit
|
||||
|
@ -43,6 +41,7 @@ from sklearn.model_selection import KFold
|
|||
from tqdm import trange
|
||||
|
||||
from ..params import simname2Omega_m
|
||||
from ..utils import radec_to_galactic
|
||||
|
||||
SPEED_OF_LIGHT = 299792.458 # km / s
|
||||
H0 = 100 # km / s / Mpc
|
||||
|
@ -53,24 +52,6 @@ def t():
|
|||
return datetime.now().strftime("%H:%M:%S")
|
||||
|
||||
|
||||
def radec_to_galactic(ra, dec):
|
||||
"""
|
||||
Convert right ascension and declination to galactic coordinates (all in
|
||||
degrees.)
|
||||
|
||||
Parameters
|
||||
----------
|
||||
ra, dec : float or 1-dimensional array
|
||||
Right ascension and declination in degrees.
|
||||
|
||||
Returns
|
||||
-------
|
||||
l, b : float or 1-dimensional array
|
||||
"""
|
||||
c = SkyCoord(ra=ra*u.degree, dec=dec*u.degree, frame='icrs')
|
||||
return c.galactic.l.degree, c.galactic.b.degree
|
||||
|
||||
|
||||
###############################################################################
|
||||
# Data loader #
|
||||
###############################################################################
|
||||
|
|
|
@ -16,6 +16,62 @@
|
|||
Various user parameters for CSiBORGTools.
|
||||
"""
|
||||
|
||||
CB2_REDSHIFT = [69.0000210000063, 40.250007218751264, 28.24050991940438,
|
||||
21.6470609550175, 17.480001404480106, 14.608109099433955,
|
||||
12.508772664512199, 10.90721705951751, 9.64516173673259,
|
||||
8.625000360937513, 7.7832702592057235, 7.0769233254437935,
|
||||
6.475728365821477, 5.95783150553419, 5.50704240932355,
|
||||
5.111111246913583, 4.760598622974984, 4.448113312911626,
|
||||
4.1677853285437605, 3.914893700679041, 3.685598452365574,
|
||||
3.476744253718227, 3.285714346938776, 3.1103203402819117,
|
||||
2.9487179993425383, 2.7993421515051513, 2.6608558268213116,
|
||||
2.5321101306287352, 2.4121122957547967, 2.3000000330000008,
|
||||
2.1950207773798662, 2.096514773533915, 2.003901196522936,
|
||||
1.9166666909722223, 1.8343558508261513, 1.7565632668759008,
|
||||
1.6829268488994646, 1.613122190273029, 1.5468577900064306,
|
||||
1.4838709837669097, 1.4239244641145379, 1.366803292753544,
|
||||
1.3123123255056859, 1.2602739849878026, 1.210526327423823,
|
||||
1.162921359250726, 1.117323566656109, 1.0736086272735772,
|
||||
1.0316622782422846, 0.9913793189283591, 0.9526627299814432,
|
||||
0.9154228931957131, 0.8795768989699038, 0.8450479301016136,
|
||||
0.8117647122768166, 0.7796610229819017, 0.7486752517178681,
|
||||
0.7187500053710938, 0.6898317534223188, 0.6618705083794834,
|
||||
0.6348195374209455, 0.6086351017498701, 0.5832762206018658,
|
||||
0.5587044572276223, 0.5348837244997295, 0.5117801080759505,
|
||||
0.48936170529651424, 0.46759847820604516, 0.4464621192761633,
|
||||
0.42592592856652933, 0.4059647012034677, 0.3865546241790834,
|
||||
0.3676731815824261, 0.34929906746973005, 0.3314121056648591,
|
||||
0.31399317585528075, 0.2970241454144613, 0.28048780643961924,
|
||||
0.2643678175452504, 0.2486486499985392, 0.23331553782343795,
|
||||
0.21835443153641232, 0.20375195520916023, 0.18949536658248856,
|
||||
0.17557251998135315, 0.1619718318042056, 0.14868224838055033,
|
||||
0.13569321600925854, 0.122994653006949, 0.11057692361085425,
|
||||
0.09843081359419292, 0.08654750746436402, 0.0749185671253807,
|
||||
0.06353591189600438, 0.05239179978414388, 0.04147880992632613,
|
||||
0.03078982610853953, 0.020318021291547472,
|
||||
0.010056843069963017, 0.0]
|
||||
|
||||
|
||||
def snap2redshift(snapnum, simname):
|
||||
"""
|
||||
Convert a snapshot number to redshift.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
snapnum : int
|
||||
Snapshot number.
|
||||
simname : str
|
||||
Simulation name.
|
||||
|
||||
Returns
|
||||
-------
|
||||
float
|
||||
"""
|
||||
if "csiborg2_" in simname:
|
||||
return CB2_REDSHIFT[snapnum]
|
||||
else:
|
||||
raise ValueError(f"Unknown simname: {simname}")
|
||||
|
||||
|
||||
def simname2boxsize(simname):
|
||||
"""
|
||||
|
@ -65,6 +121,7 @@ def simname2Omega_m(simname):
|
|||
d = {"csiborg1": 0.307,
|
||||
"csiborg2_main": 0.3111,
|
||||
"csiborg2_random": 0.3111,
|
||||
"csiborg2_varysmall": 0.3111,
|
||||
"borg1": 0.307,
|
||||
"Carrick2015": 0.3,
|
||||
}
|
||||
|
|
|
@ -23,6 +23,7 @@ from functools import lru_cache
|
|||
from gc import collect
|
||||
from itertools import product
|
||||
from math import floor
|
||||
from astropy.cosmology import FlatLambdaCDM
|
||||
|
||||
import numpy
|
||||
from h5py import File
|
||||
|
@ -30,7 +31,8 @@ from sklearn.neighbors import NearestNeighbors
|
|||
|
||||
from ..params import paths_glamdring
|
||||
from ..utils import (cartesian_to_radec, great_circle_distance, number_counts,
|
||||
periodic_distance_two_points, real2redshift)
|
||||
periodic_distance_two_points, real2redshift,
|
||||
radec_to_galactic)
|
||||
from .paths import Paths
|
||||
from .snapshot import is_instance_of_base_snapshot_subclass
|
||||
|
||||
|
@ -46,6 +48,7 @@ class BaseCatalogue(ABC):
|
|||
"""
|
||||
_properties = ["cartesian_pos",
|
||||
"spherical_pos",
|
||||
"galactic_pos",
|
||||
"dist",
|
||||
"cartesian_redshiftspace_pos",
|
||||
"spherical_redshiftspace_pos",
|
||||
|
@ -596,6 +599,9 @@ class BaseCatalogue(ABC):
|
|||
elif key == "spherical_pos":
|
||||
out = cartesian_to_radec(
|
||||
self["__cartesian_pos"] - self.observer_location)
|
||||
elif key == "galactic_pos":
|
||||
out = self["__spherical_pos"]
|
||||
out[:, 1], out[:, 2] = radec_to_galactic(out[:, 1], out[:, 2])
|
||||
elif key == "dist":
|
||||
out = numpy.linalg.norm(
|
||||
self["__cartesian_pos"] - self.observer_location, axis=1)
|
||||
|
@ -985,7 +991,6 @@ class CSiBORG2MergerTreeReader:
|
|||
group2treeid : dict
|
||||
Dictionary with group number as key and tree ID as value.
|
||||
"""
|
||||
print("Creating group to tree ID mapping...")
|
||||
with File(self.paths.trees(self.nsim, self.simname), 'r') as f:
|
||||
groupnr = f["TreeHalos/GroupNr"][:]
|
||||
snapnum = f["TreeHalos/SnapNum"][:]
|
||||
|
@ -1020,6 +1025,11 @@ class CSiBORG2MergerTreeReader:
|
|||
"TreeNextProgenitor",
|
||||
"TreeProgenitor",
|
||||
"SubhaloMass",
|
||||
"Group_M_Crit200",
|
||||
"SubhaloSpin",
|
||||
"SubhaloVmax",
|
||||
"SubhaloHalfmassRad",
|
||||
"SubhaloVmaxRad",
|
||||
]
|
||||
|
||||
with File(self.paths.trees(self.nsim, self.simname), 'r') as f:
|
||||
|
@ -1082,44 +1092,58 @@ class CSiBORG2MergerTreeReader:
|
|||
|
||||
n = first_fof # Index of the current main progenitor
|
||||
|
||||
time, redshift, main_progenitor_mass = [], [], []
|
||||
max_next_progenitor_mass, total_next_progenitor_mass = [], []
|
||||
snap_num, redshift, main_progenitor_mass, group_m200c = [], [], [], []
|
||||
main_progenitor_vmax, main_progenitor_spin = [], []
|
||||
main_progenitor_vmaxrad, main_progenitor_halfmassrad = [], []
|
||||
while True:
|
||||
# First off attempt to find the next progenitors of the current
|
||||
# halo. Deal with the main progenitor later.
|
||||
next_prog = tree["TreeNextProgenitor"][n]
|
||||
if next_prog != -1:
|
||||
minors = []
|
||||
while True:
|
||||
minors.append(tree["SubhaloMass"][next_prog])
|
||||
# NOTE: 'Minors' are ignored. This is only relevant if we wanted
|
||||
# to find the other subhaloes in the current FoF group.
|
||||
|
||||
next_prog = tree["TreeNextProgenitor"][next_prog]
|
||||
# # First off attempt to find the next progenitors of the current
|
||||
# # halo. Deal with the main progenitor later.
|
||||
# next_prog = tree["TreeNextProgenitor"][n]
|
||||
# if next_prog != -1:
|
||||
# minors = []
|
||||
# while True:
|
||||
# minors.append(tree["SubhaloMass"][next_prog])
|
||||
|
||||
if next_prog == -1:
|
||||
break
|
||||
else:
|
||||
# Fiducially set it to zero.
|
||||
minors = [0]
|
||||
# next_prog = tree["TreeNextProgenitor"][next_prog]
|
||||
|
||||
# if next_prog == -1:
|
||||
# break
|
||||
# else:
|
||||
# # Fiducially set it to zero.
|
||||
# minors = [0]
|
||||
|
||||
# Update data with information from the current main progenitor.
|
||||
major = tree["SubhaloMass"][n]
|
||||
main_progenitor_mass.append(major)
|
||||
max_next_progenitor_mass.append(max(minors))
|
||||
total_next_progenitor_mass.append(sum(minors))
|
||||
group_m200c.append(tree["Group_M_Crit200"][n])
|
||||
main_progenitor_vmax.append(tree["SubhaloVmax"][n])
|
||||
main_progenitor_spin.append(tree["SubhaloSpin"][n])
|
||||
main_progenitor_vmaxrad.append(tree["SubhaloVmaxRad"][n])
|
||||
main_progenitor_halfmassrad.append(tree["SubhaloHalfmassRad"][n])
|
||||
snap_num.append(tree["SnapNum"][n])
|
||||
redshift.append(tree["Redshift"][tree["SnapNum"][n]])
|
||||
time.append(tree["Time"][tree["SnapNum"][n]])
|
||||
|
||||
# Update n to the next main progenitor.
|
||||
# Update `n` to the next main progenitor.
|
||||
n = tree["TreeMainProgenitor"][n]
|
||||
|
||||
if n == -1:
|
||||
break
|
||||
|
||||
return {"Time": numpy.array(time),
|
||||
# For calculating age of the Universe at each redshift.
|
||||
cosmo = FlatLambdaCDM(H0=67.66, Om0=0.3111)
|
||||
|
||||
return {"SnapNum": numpy.array(snap_num, dtype=numpy.int32),
|
||||
"Age": numpy.array(cosmo.age(redshift).value),
|
||||
"Redshift": numpy.array(redshift),
|
||||
"Group_M_Crit200": numpy.array(group_m200c) * 1e10,
|
||||
"MainProgenitorMass": numpy.array(main_progenitor_mass) * 1e10,
|
||||
"MaxNextProgenitorMass": numpy.array(max_next_progenitor_mass) * 1e10, # noqa
|
||||
"TotalNextProgenitorMass": numpy.array(total_next_progenitor_mass) * 1e10, # noqa
|
||||
"MainProgenitorVmax": numpy.array(main_progenitor_vmax),
|
||||
"MainProgenitorSpin": numpy.array(main_progenitor_spin),
|
||||
"MainProgenitorVmaxRad": numpy.array(main_progenitor_vmaxrad),
|
||||
"MainProgenitorHalfmassRad": numpy.array(main_progenitor_halfmassrad), # noqa
|
||||
}
|
||||
|
||||
|
||||
|
@ -1148,7 +1172,6 @@ class CSiBORG2SUBFINDCatalogue(BaseCatalogue):
|
|||
"""
|
||||
def __init__(self, nsim, nsnap, kind, paths=None,
|
||||
bounds=None, flip_xz=True, cache_maxsize=64):
|
||||
# TODO: finish all this!
|
||||
super().__init__()
|
||||
super().init_with_snapshot(
|
||||
f"csiborg2_{kind}", nsim, nsnap, paths, None, bounds,
|
||||
|
@ -1156,7 +1179,8 @@ class CSiBORG2SUBFINDCatalogue(BaseCatalogue):
|
|||
cache_maxsize)
|
||||
|
||||
self._custom_keys = ["SubhaloSpin", "SubhaloVelDisp", "Central",
|
||||
"ParentMass"]
|
||||
"SubhaloVmax", "SubhaloVmaxRad",
|
||||
"SubhaloHalfmassRad", "ParentMass"]
|
||||
|
||||
@property
|
||||
def kind(self):
|
||||
|
@ -1235,6 +1259,18 @@ class CSiBORG2SUBFINDCatalogue(BaseCatalogue):
|
|||
def SubhaloVelDisp(self):
|
||||
return self._read_subfind_catalogue("SubhaloVelDisp")
|
||||
|
||||
@property
|
||||
def SubhaloVmax(self):
|
||||
return self._read_subfind_catalogue("SubhaloVmax")
|
||||
|
||||
@property
|
||||
def SubhaloVmaxRad(self):
|
||||
return self._read_subfind_catalogue("SubhaloVmaxRad")
|
||||
|
||||
@property
|
||||
def SubhaloHalfmassRad(self):
|
||||
return self._read_subfind_catalogue("SubhaloHalfmassRad")
|
||||
|
||||
@property
|
||||
def SubhaloContamination(self):
|
||||
mass_type = self._read_subfind_catalogue("SubhaloMassType")
|
||||
|
|
|
@ -301,7 +301,7 @@ class Paths:
|
|||
return join(self.csiborg2_main_srcdir, f"chain_{nsim}", "output",
|
||||
"trees.hdf5")
|
||||
elif simname == "csiborg2_random":
|
||||
return join(self.csiborg2_ranodm_srcdir, f"chain_{nsim}", "output",
|
||||
return join(self.csiborg2_random_srcdir, f"chain_{nsim}", "output",
|
||||
"trees.hdf5")
|
||||
elif simname == "csiborg2_varysmall":
|
||||
return join(self.csiborg2_varysmall_srcdir,
|
||||
|
@ -351,6 +351,26 @@ class Paths:
|
|||
fname = fname.replace("overlap", "overlap_smoothed")
|
||||
return join(fdir, fname)
|
||||
|
||||
def random_mah(self, simname, nsim):
|
||||
"""
|
||||
Path to the files containing MAHs from random simulations.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
simname : str
|
||||
Simulation name.
|
||||
nsim0 : int
|
||||
IC realisation index of the simulation.
|
||||
|
||||
Returns
|
||||
-------
|
||||
str
|
||||
"""
|
||||
fdir = join(self.postdir, "random_mah")
|
||||
try_create_directory(fdir)
|
||||
|
||||
return join(fdir, f"random_mah_{simname}_{nsim}.hdf5")
|
||||
|
||||
def match_max(self, simname, nsim0, nsimx, min_logmass, mult):
|
||||
"""
|
||||
Path to the files containing matching based on [1].
|
||||
|
|
|
@ -82,9 +82,9 @@ class PairOverlap:
|
|||
self._cat0 = cat0
|
||||
self._catx = catx
|
||||
self._paths = cat0.paths
|
||||
self.load(cat0, catx, min_logmass, maxdist)
|
||||
self._load(cat0, catx, min_logmass, maxdist)
|
||||
|
||||
def load(self, cat0, catx, paths, min_logmass, maxdist=None):
|
||||
def _load(self, cat0, catx, min_logmass, maxdist=None):
|
||||
r"""
|
||||
Load overlap calculation results. Matches the results back to the two
|
||||
catalogues in question.
|
||||
|
@ -107,14 +107,13 @@ class PairOverlap:
|
|||
"""
|
||||
nsim0 = cat0.nsim
|
||||
nsimx = catx.nsim
|
||||
paths = cat0.paths
|
||||
|
||||
# We first load in the output files. We need to find the right
|
||||
# combination of the reference and cross simulation.
|
||||
fname = paths.overlap(cat0.simname, nsim0, nsimx, min_logmass,
|
||||
smoothed=False)
|
||||
fname_inv = paths.overlap(cat0.simname, nsimx, nsim0, min_logmass,
|
||||
smoothed=False)
|
||||
fname = self._paths.overlap(cat0.simname, nsim0, nsimx, min_logmass,
|
||||
smoothed=False)
|
||||
fname_inv = self._paths.overlap(cat0.simname, nsimx, nsim0,
|
||||
min_logmass, smoothed=False)
|
||||
if isfile(fname):
|
||||
data_ngp = numpy.load(fname, allow_pickle=True)
|
||||
to_invert = False
|
||||
|
@ -125,8 +124,8 @@ class PairOverlap:
|
|||
else:
|
||||
raise FileNotFoundError(f"No file found for {nsim0} and {nsimx}.")
|
||||
|
||||
fname_smooth = paths.overlap(cat0.simname, cat0.nsim, catx.nsim,
|
||||
min_logmass, smoothed=True)
|
||||
fname_smooth = self._paths.overlap(cat0.simname, cat0.nsim, catx.nsim,
|
||||
min_logmass, smoothed=True)
|
||||
data_smooth = numpy.load(fname_smooth, allow_pickle=True)
|
||||
|
||||
# Create mapping from halo indices to array positions in the catalogue.
|
||||
|
@ -609,6 +608,7 @@ class NPairsOverlap:
|
|||
|
||||
self._pairs = pairs
|
||||
|
||||
@lru_cache()
|
||||
def max_overlap(self, min_overlap, from_smoothed, verbose=True):
|
||||
"""
|
||||
Calculate maximum overlap of each halo in the reference simulation with
|
||||
|
@ -644,6 +644,7 @@ class NPairsOverlap:
|
|||
for y_ in pair.overlap(from_smoothed)])
|
||||
return numpy.vstack(out).T
|
||||
|
||||
@lru_cache()
|
||||
def max_overlap_key(self, key, min_overlap, from_smoothed, verbose=True):
|
||||
"""
|
||||
Calculate maximum overlap mass of each halo in the reference
|
||||
|
@ -674,6 +675,7 @@ class NPairsOverlap:
|
|||
|
||||
return numpy.vstack(out).T
|
||||
|
||||
@lru_cache()
|
||||
def summed_overlap(self, from_smoothed, verbose=True):
|
||||
"""
|
||||
Calculate summed overlap of each halo in the reference simulation with
|
||||
|
|
|
@ -19,6 +19,8 @@ from copy import deepcopy
|
|||
from datetime import datetime
|
||||
|
||||
import numpy as np
|
||||
from astropy import units as u
|
||||
from astropy.coordinates import SkyCoord
|
||||
from numba import jit
|
||||
from numpyro.infer import util
|
||||
from scipy.stats import multivariate_normal
|
||||
|
@ -154,6 +156,24 @@ def radec_to_cartesian(X):
|
|||
]).T
|
||||
|
||||
|
||||
def radec_to_galactic(ra, dec):
|
||||
"""
|
||||
Convert right ascension and declination to galactic coordinates (all in
|
||||
degrees.)
|
||||
|
||||
Parameters
|
||||
----------
|
||||
ra, dec : float or 1-dimensional array
|
||||
Right ascension and declination in degrees.
|
||||
|
||||
Returns
|
||||
-------
|
||||
l, b : float or 1-dimensional array
|
||||
"""
|
||||
c = SkyCoord(ra=ra*u.degree, dec=dec*u.degree, frame='icrs')
|
||||
return c.galactic.l.degree, c.galactic.b.degree
|
||||
|
||||
|
||||
@jit(nopython=True, fastmath=True, boundscheck=False)
|
||||
def great_circle_distance(x1, x2):
|
||||
"""
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue