def subhalo_positions(groups_fname, groups_number, mass_interval, min_mass, max_mass, velocities=False): #read SUBFIND CDM subhalos information halos = readsubf.subfind_catalog(groups_fname, groups_number, group_veldisp=True, masstab=True, long_ids=True, swap=False) Pos = halos.sub_pos / 1e3 #Mpc/h Vel = halos.sub_vel #km/s ---> they are physical velocities! if mass_interval: a = halos.sub_mass > min_mass b = halos.sub_mass < max_mass c = a * b halos_indexes = np.where(c == True)[0] del a, b, c, halos Pos = Pos[halos_indexes] Vel = Vel[halos_indexes] if velocities: return [Pos, Vel] else: return Pos
def center_halo(halo): import numpy as np import readsubf # Initialize variables: base_id = halo.base_id base = halo.base snap_num = halo.snap_num sub_id = halo.sub_id save_dir = halo.save_dir interact = halo.interact type_thresh = halo.type_thresh scale_factor = halo.scale_factor all_pos = halo.all_pos all_vel = halo.all_vel all_mass = halo.all_mass all_pot = halo.all_pot all_T_gas = halo.all_T_gas all_rho_gas = halo.all_rho_gas #all_age = halo.all_age # Move to the frame where the most tightly bound particle is at rest, and at the origin: print "Re-centering..." cat = readsubf.subfind_catalog(base,snap_num,masstab=True) halo_cent_pos = cat.sub_pos[sub_id] halo_cent_vel = cat.sub_vel[sub_id] #rescale to physical coordinates: halo_cent_pos = halo_cent_pos * scale_factor halo_cent_vel = halo_cent_vel * np.sqrt(scale_factor) for j in np.arange(3): all_pos[j] = all_pos[j] - halo_cent_pos all_vel[j] = all_vel[j] - halo_cent_vel # Calculate radii for all particles: all_radii = [0]*3 for j in np.arange(3): all_radii[j] = np.zeros(len(all_pos[j])) all_radii[j] = np.float64(all_radii[j]) for k in np.arange(len(all_pos[j])): all_radii[j][k] = np.sqrt(np.dot(all_pos[j][k],all_pos[j][k])) print "np.sort(all_radii[0]): ", np.sort(all_radii[0]) # Exporting variables halo.all_pos = all_pos halo.all_vel = all_vel halo.all_radii = all_radii
def group_catalog( self, hdf5_names=["GroupPos", "Group_M_Crit200", "Group_R_Crit200"], masstab=True, group_veldisp=True, file_prefix="", files=-1, path="", dirname="groups_", filename="fof_subhalo_tab_", ): """Read data from the group catalog corresponding to the snapshot. Usage: my_snapshot.group_catalog(<hdf5_names>, <masstab>, <group_veldisp>, <file_prefix>, <files>, <path>, <dirname>, <filename>) Arguments: hdf5_names List of hdf5 names of the data fields to be loaded (see 'my_snapshot.show_group_catalog_contents()'), optional, default '['GroupPos', 'Group_M_Crit200', 'Group_R_Crit200']' masstab Only needed for Gadget format, optional group_veldisp Only needed for Gadget format, optional file_prefix Prefix for the group directory, optional, default '' files List of files to be loaded from the group catalog, optional, default '-1' (all files) path path where the group catalog is stored, optional, default: same path as snapshot data dirname directory name for the group catalog subdirectories, optional, default 'groups_' filename filename for the individual catalog files, optional, default '/fof_subhalo_tab_' Example: my_snapshot.group_catalog(['GroupPos', 'SubhaloPos']) This will load the positions of all groups and subhalos. """ if not self.hdf5: self.cat = readsubf.subfind_catalog( self.directory + file_prefix, self.snapnum, masstab=masstab, group_veldisp=group_veldisp, ) else: self.fast_group_catalog( hdf5_names=hdf5_names, files=files, path=path, dirname=dirname, filename=filename, file_prefix=file_prefix, )
def center_halo(halo): import numpy as np import readsubf # Initialize variables: base_id = halo.base_id base = halo.base snap_num = halo.snap_num sub_id = halo.sub_id save_dir = halo.save_dir interact = halo.interact type_thresh = halo.type_thresh gal_pos = halo.gal_pos gal_vel = halo.gal_vel gal_mass = halo.gal_mass gal_pot = halo.gal_pot gal_T_gas = halo.gal_T_gas gal_rho_gas = halo.gal_rho_gas #gal_age = halo.gal_age # Move to the frame where the center of the galaxy is at rest, and at the origin: print "Re-centering..." cat = readsubf.subfind_catalog(base,snap_num,masstab=True) gal_cent_pos = cat.sub_pos[sub_id] gal_cent_vel = cat.sub_vel[sub_id] for j in np.arange(3): gal_pos[j] = gal_pos[j] - gal_cent_pos gal_vel[j] = gal_vel[j] - gal_cent_vel # Exporting variables halo.gal_pos = gal_pos halo.gal_vel = gal_vel
def halo_positions(groups_fname, groups_number, mass_interval, min_mass, max_mass): #read SUBFIND CDM halos information halos = readsubf.subfind_catalog(groups_fname, groups_number, group_veldisp=True, masstab=True, long_ids=True, swap=False) Pos = halos.group_pos / 1e3 #Mpc/h if mass_interval: a = halos.group_m_mean200 > min_mass b = halos.group_m_mean200 < max_mass c = a * b halos_indexes = np.where(c == True)[0] del a, b, c, halos Pos = Pos[halos_indexes] return Pos
def find_all_halos(num, base, min_mass): """Get a halo catalogue and return its members, filtering out those with masses below min_mass. Select halos via their M_200 mass, defined in terms of the critical density. Arguments: num - snapnumber base - simulation directory min_mass - minimum mass of halos to use Returns: ind - list of halo indices used sub_mass - halo masses in M_sun /h sub_cofm - halo positions sub_radii - R_Crit200 for halo radii""" try: subs=readsubf.subfind_catalog(base,num,masstab=True,long_ids=True) #Get list of halos resolved, using a mass cut; cuts off at about 2e9 for 512**3 particles. ind=np.where(subs.group_m_crit200 > min_mass) #Store the indices of the halos we are using #Get particle center of mass, use group catalogue. sub_cofm=np.array(subs.group_pos[ind]) #halo masses in M_sun/h: use M_200 sub_mass=np.array(subs.group_m_crit200[ind])*UnitMass_in_g/SolarMass_in_g #r200 in kpc. sub_radii = np.array(subs.group_r_crit200[ind]) del subs except IOError: # We might have the halo catalog stored in the new format, which is HDF5. subs=readsubfHDF5.subfind_catalog(base, num,long_ids=True) #Get list of halos resolved, using a mass cut; cuts off at about 2e9 for 512**3 particles. ind=np.where(subs.Group_M_Crit200 > min_mass) #Store the indices of the halos we are using #Get particle center of mass, use group catalogue. sub_cofm=np.array(subs.GroupPos[ind]) #halo masses in M_sun/h: use M_200 sub_mass=np.array(subs.Group_M_Crit200[ind])*UnitMass_in_g/SolarMass_in_g #r200 in kpc/h (comoving). sub_radii = np.array(subs.Group_R_Crit200[ind]) del subs return (ind, sub_mass,sub_cofm,sub_radii)
def mass_function(groups_fname, groups_number, obj, BoxSize, bins, f_out, min_mass=None, max_mass=None, long_ids_flag=True, SFR_flag=False): #bins_mass=np.logspace(np.log10(min_mass),np.log10(max_mass),bins+1) #mass_mean=10**(0.5*(np.log10(bins_mass[1:])+np.log10(bins_mass[:-1]))) #dM=bins_mass[1:]-bins_mass[:-1] if obj == 'FoF': #read FoF halos information fof = readfof.FoF_catalog(groups_fname, groups_number, long_ids=long_ids_flag, swap=False, SFR=SFR_flag) F_pos = fof.GroupPos / 1e3 #positions in Mpc/h F_mass = fof.GroupMass * 1e10 #masses in Msun/h F_part = fof.GroupLen #number particles belonging to the group F_Mpart = F_mass[0] / F_part[0] #mass of a single particle in Msun/h del fof #some verbose print '\nNumber of FoF halos=', len(F_pos) print '%f < X_fof < %f' % (np.min(F_pos[:, 0]), np.max(F_pos[:, 0])) print '%f < Y_fof < %f' % (np.min(F_pos[:, 1]), np.max(F_pos[:, 1])) print '%f < Z_fof < %f' % (np.min(F_pos[:, 2]), np.max(F_pos[:, 2])) print '%e < M_fof < %e\n' % (np.min(F_mass), np.max(F_mass)) #Correct the masses of the FoF halos F_mass = F_Mpart * (F_part * (1.0 - F_part**(-0.6))) #compute the minimum and maximum mass if min_mass == None: min_mass = np.min(F_mass) if max_mass == None: max_mass = np.max(F_mass) print 'M_min = %e' % (min_mass) print 'M_max = %e\n' % (max_mass) #find the masses and mass intervals bins_mass = np.logspace(np.log10(min_mass), np.log10(max_mass), bins + 1) mass_mean = 10**(0.5 * (np.log10(bins_mass[1:]) + np.log10(bins_mass[:-1]))) dM = bins_mass[1:] - bins_mass[:-1] #compute the number of halos within each mass interval number = np.histogram(F_mass, bins=bins_mass)[0] print number print np.sum(number, dtype=np.float64) elif obj == 'halos_m200': #read CDM halos information halos = readsubf.subfind_catalog(groups_fname, groups_number, group_veldisp=True, masstab=True, long_ids=True, swap=False) H_pos = halos.group_pos / 1e3 #positions in Mpc/h H_mass = halos.group_m_mean200 * 1e10 #masses in Msun/h H_radius_m = halos.group_r_mean200 / 1e3 #radius in Mpc/h del halos #some verbose print '\nNumber of halos=', len(H_pos) print '%f < X < %f' % (np.min(H_pos[:, 0]), np.max(H_pos[:, 0])) print '%f < Y < %f' % (np.min(H_pos[:, 1]), np.max(H_pos[:, 1])) print '%f < Z < %f' % (np.min(H_pos[:, 2]), np.max(H_pos[:, 2])) print '%e < M < %e\n' % (np.min(H_mass), np.max(H_mass)) #compute the minimum and maximum mass if min_mass == None: min_mass = np.min(H_mass) if max_mass == None: max_mass = np.max(H_mass) #compute the number of halos within each mass interval bins_mass = np.logspace(np.log10(min_mass), np.log10(max_mass), bins + 1) mass_mean = 10**(0.5 * (np.log10(bins_mass[1:]) + np.log10(bins_mass[:-1]))) dM = bins_mass[1:] - bins_mass[:-1] number = np.histogram(H_mass, bins=bins_mass)[0] print number print np.sum(number, dtype=np.float64) elif obj == 'halos_c200': #read CDM halos information halos = readsubf.subfind_catalog(groups_fname, groups_number, group_veldisp=True, masstab=True, long_ids=True, swap=False) H_pos = halos.group_pos / 1e3 #positions in Mpc/h H_mass = halos.group_m_crit200 * 1e10 #masses in Msun/h H_radius_m = halos.group_r_crit200 / 1e3 #radius in Mpc/h del halos #some verbose print '\nNumber of halos=', len(H_pos) print '%f < X < %f' % (np.min(H_pos[:, 0]), np.max(H_pos[:, 0])) print '%f < Y < %f' % (np.min(H_pos[:, 1]), np.max(H_pos[:, 1])) print '%f < Z < %f' % (np.min(H_pos[:, 2]), np.max(H_pos[:, 2])) print '%e < M < %e\n' % (np.min(H_mass), np.max(H_mass)) #compute the minimum and maximum mass if min_mass == None: min_mass = np.min(H_mass) if max_mass == None: max_mass = np.max(H_mass) #compute the number of halos within each mass interval bins_mass = np.logspace(np.log10(min_mass), np.log10(max_mass), bins + 1) mass_mean = 10**(0.5 * (np.log10(bins_mass[1:]) + np.log10(bins_mass[:-1]))) dM = bins_mass[1:] - bins_mass[:-1] number = np.histogram(H_mass, bins=bins_mass)[0] print number print np.sum(number, dtype=np.float64) elif obj == 'subhalos': #read CDM halos information halos = readsubf.subfind_catalog(groups_fname, groups_number, group_veldisp=True, masstab=True, long_ids=True, swap=False) S_pos = halos.sub_pos / 1e3 #positions in Mpc/h S_mass = halos.sub_mass * 1e10 #masses in Msun/h del halos #some verbose print '\nNumber of subhalos=', len(S_pos) print '%f < X < %f' % (np.min(S_pos[:, 0]), np.max(S_pos[:, 0])) print '%f < Y < %f' % (np.min(S_pos[:, 1]), np.max(S_pos[:, 1])) print '%f < Z < %f' % (np.min(S_pos[:, 2]), np.max(S_pos[:, 2])) print '%e < M < %e\n' % (np.min(S_mass), np.max(S_mass)) #compute the minimum and maximum mass if min_mass == None: min_mass = np.min(S_mass) if max_mass == None: max_mass = np.max(S_mass) #compute the number of halos within each mass interval bins_mass = np.logspace(np.log10(min_mass), np.log10(max_mass), bins + 1) mass_mean = 10**(0.5 * (np.log10(bins_mass[1:]) + np.log10(bins_mass[:-1]))) dM = bins_mass[1:] - bins_mass[:-1] number = np.histogram(S_mass, bins=bins_mass)[0] print number print np.sum(number, dtype=np.float64) else: print 'bad object type selected' sys.exit() MF = number / (dM * BoxSize**3) delta_MF = np.sqrt(number) / (dM * BoxSize**3) f = open(f_out, 'w') for i in range(bins): f.write( str(mass_mean[i]) + ' ' + str(MF[i]) + ' ' + str(delta_MF[i]) + '\n') f.close()
def pairwise_match(base1,base2,snapnum1,snapnum2,ids1=-1,ids2=-1): import readsubf import numpy as np # Important parameters: minM=10. maxM=10.**5 massDiff_thresh = 0.3 #ratio centerDiff_thresh = 30. #kpc box_size = 20000. #kpc # Load subfind catalogues cat = [readsubf.subfind_catalog(base1,snapnum1,masstab=True),\ readsubf.subfind_catalog(base2,snapnum2,masstab=True)] nruns = 2 #len(cat_list) sub_ids = [0]*nruns M = [0]*nruns pos = [0]*nruns match_ids1 = np.array([]) match_ids2 = np.array([]) for i in np.arange(nruns): # Load only primary subhalos within groups, or load preselected list of IDs sub_ids[i] = cat[i].group_firstsub #if (i == 0 and ids1 == -1) or (i == 1 and ids2 == -1): sub_ids[i] = cat[i].group_firstsub #elif i == 0: sub_ids[0] = ids1 #elif i == 1: sub_ids[1] = ids2 M[i] = cat[i].sub_mass[sub_ids[i][:-1]] pos[i] = cat[i].sub_pos[sub_ids[i][:-1]] # Apply mass cuts: M_cut1 = M[i] > minM sub_ids[i] = sub_ids[i][M_cut1] M[i] = M[i][M_cut1] M_cut2 = M[i] < maxM sub_ids[i] = sub_ids[i][M_cut2] M[i] = M[i][M_cut2] for j in np.arange(len(sub_ids[0])): locM = M[0][j] locPos = pos[0][j] massDiff = abs(M[1]-locM)/locM M_matches = abs(massDiff) < massDiff_thresh N_match1 = M_matches.sum() #print "N_match1 ",N_match1 if N_match1 > 0: match1_ids = sub_ids[1][M_matches] match1_pos = pos[1][M_matches] posDiff = locPos - match1_pos centerDiff = np.arange(N_match1) for k in np.arange(N_match1): centerDiff[k] = np.sqrt( np.dot(posDiff[k],posDiff[k])) pos_matches = centerDiff < centerDiff_thresh #pos_matches = np.logical_or(centerDiff < centerDiff_thresh,centerDiff > box_size-centerDiff_thresh) N_match2 = pos_matches.sum() #print "N_match2 ",N_match2 if N_match2 == 1: match_ids1 = np.append(match_ids1,sub_ids[0][j]) match_ids2 = np.append(match_ids2,sub_ids[1][M_matches][pos_matches]) elif N_match2 > 1: print "More than 1 possible match for a halo found!" closest = np.argmin(centerDiff[pos_matches]) match_ids1 = np.append(match_ids1,sub_ids[0][j]) match_ids2 = np.append(match_ids2,sub_ids[1][M_matches][pos_matches][closest]) N_matches = len(match_ids1) print "\n\n"+"Matched "+str(N_matches)+" Halos" #print "Matching catalog: " #for i in np.arange(N_matches): # print "1: ",match_ids1[i], " -- 2: ",match_ids2[i] return [match_ids1,match_ids2]
#import CalcHsml #=============================================================================================== resnap_name = "base102" base = directory(resnap_name)[0] snapnum = 313 #directory(resnap_name)[1] print resnap_name snapname = base + "/snapdir_"+str(snapnum).zfill(3)+ "/snap_"+str(snapnum).zfill(3) #snapname = base + "/snapdir_"+str(snapnum).zfill(3)+"_SAVE"+ "/snap_"+str(snapnum).zfill(3) print "snapname ", snapname #=============================================================================================== cat = readsubf.subfind_catalog(base,snapnum,masstab=True) nsubs = cat.nsubs print str(nsubs) + " subhalos!\n" parttype_list = [0,1,4] all_ids = np.array([],dtype="uint32") types = np.array([],dtype="uint32") mass = np.array([],dtype="float64") pos = np.array([],dtype="float64") vel = np.array([],dtype="float64") u = np.array([],dtype="float64") T = np.array([],dtype="float64") rho = np.array([],dtype="float64") sfr = np.array([],dtype="float64")
#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 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
def bary_mass(code_type="Arepo_ENERGY",res="512_20Mpc"): import numpy as np import readsubf import os from run_bd import run_bd import bd ############# #Control Parameters base_folder = "/n/hernquistfs1/mvogelsberger/ComparisonProject/" #code_type = "Gadget" #code_type = "Arepo_ENERGY" out_folder = "/output" snap_num = 314 # Interactive mode? interact = 0 # Restrict analysis to only primary subhalos in given group? first_subs_only = 0 # Analyze all subhalos within a given mass range: M_botlim = 25. M_toplim = 100. ############################################################################################ resnap = code_type+"_"+res+"_resnap"+str(snap_num).zfill(3)+'.dat' snap_type = 1 snap_name = resnap out_folder = "/output" base = base_folder + res + "/" + code_type + out_folder save_dir = code_type[0]+res+"_test"+"/" if not os.path.exists(save_dir): os.system('mkdir '+save_dir) #os.path.mkdir(save_dir) cat = readsubf.subfind_catalog(base,snap_num,masstab=True) if first_subs_only == 1: sub_ids = cat.group_firstsub else: sub_ids = np.arange(cat.nsubs) M_subs = cat.sub_mass[sub_ids] ind = np.logical_and(M_subs >= M_botlim, M_subs < M_toplim) M_subs = M_subs[ind] sub_ids = sub_ids[ind] N_subs = np.uint32(len(sub_ids)) print "writing ",N_subs," subhalos" err_flag = np.zeros(N_subs) bary_mass = np.zeros(N_subs) star_mass = np.zeros(N_subs) sub_posx = np.zeros(N_subs) sub_posy = np.zeros(N_subs) sub_posz = np.zeros(N_subs) sub_velx = np.zeros(N_subs) sub_vely = np.zeros(N_subs) sub_velz = np.zeros(N_subs) for i in np.arange(N_subs): sub_id = sub_ids[i] print "sub_id ",sub_id halo = bd.Halo() halo.interact = interact halo.code_type = code_type halo.res = res halo.snap_num = snap_num halo.sub_id = sub_id halo.save_dir = save_dir halo.snap_name = snap_name halo.base = base halo.snap_type = snap_type halo.err_flag = 0 bd.read_halo(halo) if halo.err_flag != 1: bd.recenter_halo(halo) print "sub_pos ",halo.sub_pos sub_posx[i] = halo.sub_pos[0] sub_posy[i] = halo.sub_pos[1] sub_posz[i] = halo.sub_pos[2] sub_velx[i] = halo.sub_vel[0] sub_vely[i] = halo.sub_vel[1] sub_velz[i] = halo.sub_vel[2] err_flag[i] = halo.err_flag bary_mass[i] = halo.bary_mass star_mass[i] = halo.star_mass print "outputting close pairs list :)" g = open(save_dir+"bary.dat",'wb') sub_ids = np.uint32(sub_ids) err_flag = np.uint32(err_flag) M_subs = np.float64(M_subs) N_subs.astype("uint32").tofile(g) sub_ids.astype("uint32").tofile(g) err_flag.astype("uint32").tofile(g) sub_posx.astype("float64").tofile(g) sub_posy.astype("float64").tofile(g) sub_posz.astype("float64").tofile(g) sub_velx.astype("float64").tofile(g) sub_vely.astype("float64").tofile(g) sub_velz.astype("float64").tofile(g) M_subs.astype("float64").tofile(g) bary_mass.astype("float64").tofile(g) star_mass.astype("float64").tofile(g) g.close() print "sub_pos x",sub_posx print "sub_pos y",sub_posy print "sub_pos z",sub_posz
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
def load_subhalos(base_list,snapnum): import numpy as np import readsubf global cat, N_subs, subhalo_Offset, subhalo_Len, subhalo_Pos, subhalo_VelDisp, \ subhalo_Vel, subhalo_Vmax, subhalo_GrNr, subhalo_Parent, subhalo_CM, subhalo_VmaxRad, \ subhalo_IDMostBound, subhalo_Mass, subhalo_Spin, subhalo_HmassRad, subhalo_IDs cat = [0]*len(base_list) N_subs = [0]*len(base_list) subhalo_Offset = [0]*len(base_list) subhalo_Len = [0]*len(base_list) subhalo_Pos = [0]*len(base_list) subhalo_VelDisp = [0]*len(base_list) subhalo_Vel = [0]*len(base_list) subhalo_Vmax = [0]*len(base_list) subhalo_GrNr = [0]*len(base_list) subhalo_Parent = [0]*len(base_list) subhalo_CM = [0]*len(base_list) subhalo_VmaxRad = [0]*len(base_list) subhalo_IDMostBound = [0]*len(base_list) subhalo_Mass = [0]*len(base_list) subhalo_Spin = [0]*len(base_list) subhalo_HmassRad = [0]*len(base_list) subhalo_IDs = [0]*len(base_list) global TEST TEST = [0]*len(base_list) for i in np.arange(len(base_list)): cat[i] = readsubf.subfind_catalog(base_list[i],snapnum,masstab=True) N_subs[i] = cat[i].nsubs TEST[i] = cat[i].group_firstsub print str(N_subs[i])+ " subhalos!" subhalo_Offset[i] = np.zeros(N_subs[i]) subhalo_Len[i] = np.zeros(N_subs[i]) subhalo_Pos[i] = np.zeros([N_subs[i],3]) subhalo_VelDisp[i] = np.zeros(N_subs[i]) subhalo_Vel[i] = np.zeros([N_subs[i],3]) subhalo_Vmax[i] = np.zeros(N_subs[i]) subhalo_GrNr[i] = np.zeros(N_subs[i]) subhalo_Parent[i] = np.zeros(N_subs[i]) subhalo_CM[i] = np.zeros([N_subs[i],3]) subhalo_VmaxRad[i] = np.zeros(N_subs[i]) subhalo_IDMostBound[i] = np.zeros(N_subs[i]) subhalo_Mass[i] = np.zeros(N_subs[i]) subhalo_Spin[i] = np.zeros([N_subs[i],3]) subhalo_HmassRad[i] = np.zeros(N_subs[i]) subhalo_IDs[i] = [0]*N_subs[i] all_ids = readsubf.subf_ids(base_list[i],snapnum,0, 0, long_ids=True,read_all=True).SubIDs for j in np.arange(N_subs[i]): subhalo_Offset[i][j] = cat[i].sub_offset[j] subhalo_Len[i][j] = cat[i].sub_len[j] subhalo_Pos[i][j] = cat[i].sub_pos[j] subhalo_VelDisp[i][j] = cat[i].sub_veldisp[j] subhalo_Vel[i][j] = cat[i].sub_vel[j] subhalo_Vmax[i][j] = cat[i].sub_vmax[j] subhalo_GrNr[i][j] = cat[i].sub_grnr[j] subhalo_Parent[i][j] = cat[i].sub_parent[j] subhalo_CM[i][j] = cat[i].sub_cm[j] subhalo_VmaxRad[i][j] = cat[i].sub_vmaxrad[j] subhalo_IDMostBound[i][j] = cat[i].sub_id_mostbound[j] subhalo_Mass[i][j] = cat[i].sub_mass[j] subhalo_Spin[i][j] = cat[i].sub_spin[j] subhalo_HmassRad[i][j] = cat[i].sub_halfmassrad[j] subhalo_IDs[i][j] = all_ids[subhalo_Offset[i][j]:subhalo_Offset[i][j]]
def read_halo(halo): import numpy as np import readsubf # Initialize variables: base = halo.base snap_type = halo.snap_type snap_name = halo.snap_name snap_num = halo.snap_num sub_id = halo.sub_id code_type = halo.code_type res = halo.res save_dir = halo.save_dir sub_id = halo.sub_id type_thresh = 25 #snap_type == 0: regular HDF5 snapshot #snap_type == 1: a "resorted" snapshot according to the subfind catalog #snap_type == 2: a *.snap file created by subsnap_write, which only contains the information for the specific halo in question print "Reading snapshot..." if snap_type == 0: gal_ids = [0]*3 gal_pos = [0]*3 gal_vel = [0]*3 gal_mass = [0]*3 gal_pot = [0]*3 gal_T_gas = [0]*3 print "opening "+snap_name # 0th element: gas. 1st element: dm. 2nd element: stars gal_ids[0] = rs.read_block(snap_name,"ID ",parttype=0) gal_ids[1] = rs.read_block(snap_name,"ID ",parttype=1) gal_ids[2] = np.append(rs.read_block(snap_name,"ID ",parttype=2),\ rs.read_block(snap_name,"ID ",parttype=3)) gal_pos[0] = rs.read_block(snap_name,"POS ",parttype=0) gal_pos[1] = rs.read_block(snap_name,"POS ",parttype=1) gal_pos[2] = np.append(rs.read_block(snap_name,"POS ",parttype=2),\ rs.read_block(snap_name,"POS ",parttype=3),axis=0) gal_vel[0] = rs.read_block(snap_name,"VEL ",parttype=0) gal_vel[1] = rs.read_block(snap_name,"VEL ",parttype=1) gal_vel[2] = np.append(rs.read_block(snap_name,"VEL ",parttype=2),\ rs.read_block(snap_name,"VEL ",parttype=3),axis=0) gal_mass[0] = rs.read_block(snap_name,"MASS",parttype=0) gal_mass[1] = rs.read_block(snap_name,"MASS",parttype=1) gal_mass[2] = np.append(rs.read_block(snap_name,"MASS",parttype=2),\ rs.read_block(snap_name,"MASS",parttype=3)) disk_mass = rs.read_block(snap_name,"MASS",parttype=2) bulge_mass = rs.read_block(snap_name,"MASS",parttype=3) gal_pot[0] = rs.read_block(snap_name,"POT ",parttype=0) gal_pot[1] = rs.read_block(snap_name,"POT ",parttype=1) gal_pot[2] = np.append(rs.read_block(snap_name,"POT ",parttype=2),\ rs.read_block(snap_name,"POT ",parttype=3)) total_D = disk_mass.sum() total_B = bulge_mass.sum() accepted_D_T = total_D/(total_D+total_B) print "Accepted D/T: ", accepted_D_T gal_T_gas = conv_T(rs.read_block(snap_name,"U ",parttype=0)) #cosmological runs: #type 0: gas, type 1: dm, type 4: stars #arrays: # spot 0: gas, spot 1: dm, spot 2: stars #ptorrey isolated runs: #type 0: gas, type 1: dm, type 2: disk stars, type 3: bulge stars, type 4: formed stars (0 initially) elif snap_type == 1: ######################################## # READ IN DATA FROM RE-SORTED SNAPSHOT # ######################################## gal_ids = [0]*3 gal_pos = [0]*3 gal_vel = [0]*3 gal_mass = [0]*3 gal_pot = [0]*3 #gal_T_gas = [0]*3 #gal_age = [0]*3 print "opening "+snap_name f = open(snap_name, 'rb') f.seek(0) nsub = np.fromfile(f,dtype="uint32",count=1)[0] npart = np.fromfile(f,dtype="uint32",count=1)[0] cat = readsubf.subfind_catalog(base,snap_num,masstab=True) sub_pos = cat.sub_pos[sub_id] sub_cm = cat.sub_cm[sub_id] sub_vel = cat.sub_vel[sub_id] halo.sub_pos = sub_pos #print "sub_pos ",sub_pos halo.sub_cm = sub_cm halo.sub_vel = sub_vel temp = sub_pos-sub_cm cent_offset = np.sqrt(np.dot(temp,temp)) halo.cent_offset = cent_offset #if np.sqrt(np.dot(pos_offset,pos_offset)) > 10.: sub_offset = cat.sub_offset[sub_id] sub_len = cat.sub_len[sub_id] sub_mass = cat.sub_mass[sub_id] halo.sub_mass = sub_mass types = np.fromfile(f,dtype="uint32",count=npart)[sub_offset:sub_offset+sub_len] mass = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] posx = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] posy = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] posz = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] velx = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] vely = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] velz = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] T = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] rho = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] sfr = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] age = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] pot = np.fromfile(f,dtype="float64",count=npart)[sub_offset:sub_offset+sub_len] ### GAS ### index_gas = types == 0 ngas = index_gas.sum() print "Ngas "+str(ngas) if ngas < type_thresh: print "Insufficient gas in this galaxy!" halo.err_flag = 1 return gal_mass[0] = mass[index_gas] gal_pot[0] = pot[index_gas] gas_len = len(gal_mass[0]) gal_pos[0] = np.zeros([gas_len,3]) gal_pos[0][:,0] = posx[index_gas] gal_pos[0][:,1] = posy[index_gas] gal_pos[0][:,2] = posz[index_gas] gal_vel[0] = np.zeros([gas_len,3]) gal_vel[0][:,0] = velx[index_gas] gal_vel[0][:,1] = vely[index_gas] gal_vel[0][:,2] = velz[index_gas] gal_T_gas = T[index_gas] gal_rho_gas = rho[index_gas] ### DM ### index_dm = types == 1 ndm = index_dm.sum() print "Ndm "+str(ndm) if ndm < type_thresh: print "Insufficient dm in this galaxy!" halo.err_flag = 1 return gal_mass[1] = mass[index_dm] gal_pot[1] = pot[index_dm] dm_len = len(gal_mass[1]) gal_pos[1] = np.zeros([dm_len,3]) gal_pos[1][:,0] = posx[index_dm] gal_pos[1][:,1] = posy[index_dm] gal_pos[1][:,2] = posz[index_dm] gal_vel[1] = np.zeros([dm_len,3]) gal_vel[1][:,0] = velx[index_dm] gal_vel[1][:,1] = vely[index_dm] gal_vel[1][:,2] = velz[index_dm] ### STARS ### index_star = types == 4 nstar = index_star.sum() print "Nstar "+str(nstar) if nstar < type_thresh: print "Insufficient stars in this galaxy!" halo.err_flag = 1 return gal_mass[2] = mass[index_star] gal_pot[2] = pot[index_star] star_len = len(gal_mass[2]) gal_pos[2] = np.zeros([star_len,3]) gal_pos[2][:,0] = posx[index_star] gal_pos[2][:,1] = posy[index_star] gal_pos[2][:,2] = posz[index_star] gal_vel[2] = np.zeros([star_len,3]) gal_vel[2][:,0] = velx[index_star] gal_vel[2][:,1] = vely[index_star] gal_vel[2][:,2] = velz[index_star] gal_age = age[index_star] print "done loading from snapshot" f.close() elif snap_type == 2: ###################################################### # READ IN DATA FROM *.snap FILE ASSOCIATED WITH HALO # ###################################################### subsnap_name = save_dir+"S"+str(snap_num).zfill(3)+"_H"+str(sub_id).zfill(5)+".snap" g = open(subsnap_name,"rb") #gal_ids = [0]*3 gal_pos = [0]*3 gal_vel = [0]*3 gal_mass = [0]*3 gal_pot = [0]*3 ### GAS ### ngas = np.fromfile(g,dtype="uint32",count=1) if ngas < type_thresh: print "Insufficient gas in this galaxy!" halo.err_flag = 1 return else: # Mass gal_mass[0] = np.fromfile(g,dtype="float64",count=ngas) # Potential gal_pot[0] = np.fromfile(g,dtype="float64",count=ngas) # Positions gal_pos[0] = np.zeros([ngas,3]) gal_pos[0][:,0] = np.fromfile(g,dtype="float64",count=ngas) gal_pos[0][:,1] = np.fromfile(g,dtype="float64",count=ngas) gal_pos[0][:,2] = np.fromfile(g,dtype="float64",count=ngas) # Velocities gal_vel[0] = np.zeros([ngas,3]) gal_vel[0][:,0] = np.fromfile(g,dtype="float64",count=ngas) gal_vel[0][:,1] = np.fromfile(g,dtype="float64",count=ngas) gal_vel[0][:,2] = np.fromfile(g,dtype="float64",count=ngas) # Temperature gal_T_gas = np.fromfile(g,dtype="float64",count=ngas) # Density gal_rho_gas = np.fromfile(g,dtype="float64",count=ngas) ### DM ### ndm = np.fromfile(g,dtype="uint32",count=1) if ndm < type_thresh: print "Insufficient dm in this galaxy!" halo.err_flag = 1 return else: # Mass gal_mass[1] = np.fromfile(g,dtype="float64",count=ndm) # Potential gal_pot[1] = np.fromfile(g,dtype="float64",count=ndm) # Positions gal_pos[1] = np.zeros([ndm,3]) gal_pos[1][:,0] = np.fromfile(g,dtype="float64",count=ndm) gal_pos[1][:,1] = np.fromfile(g,dtype="float64",count=ndm) gal_pos[1][:,2] = np.fromfile(g,dtype="float64",count=ndm) # Velocities gal_vel[1] = np.zeros([ndm,3]) gal_vel[1][:,0] = np.fromfile(g,dtype="float64",count=ndm) gal_vel[1][:,1] = np.fromfile(g,dtype="float64",count=ndm) gal_vel[1][:,2] = np.fromfile(g,dtype="float64",count=ndm) ### STARS ### nstar = np.fromfile(g,dtype="uint32",count=1) if nstar < type_thresh: print "Insufficient stars in this galaxy!" halo.err_flag = 1 return else: # Mass gal_mass[2] = np.fromfile(g,dtype="float64",count=nstar) # Potential gal_pot[2] = np.fromfile(g,dtype="float64",count=nstar) # Positions gal_pos[2] = np.zeros([nstar,3]) gal_pos[2][:,0] = np.fromfile(g,dtype="float64",count=nstar) gal_pos[2][:,1] = np.fromfile(g,dtype="float64",count=nstar) gal_pos[2][:,2] = np.fromfile(g,dtype="float64",count=nstar) # Velocities gal_vel[2] = np.zeros([nstar,3]) gal_vel[2][:,0] = np.fromfile(g,dtype="float64",count=nstar) gal_vel[2][:,1] = np.fromfile(g,dtype="float64",count=nstar) gal_vel[2][:,2] = np.fromfile(g,dtype="float64",count=nstar) # Age gal_age = np.fromfile(g,dtype="float64",count=nstar) print "done loading from *.snap file" g.close() # Exporting variables halo.gal_pos = gal_pos halo.gal_vel = gal_vel halo.gal_mass= gal_mass halo.gal_pot = gal_pot halo.gal_T_gas = gal_T_gas halo.gal_rho_gas = gal_rho_gas halo.gal_age = gal_age halo.type_thresh = type_thresh
def sub_list(snapnum=314,M_botlim=10.,M_toplim=10.**5,code_type="Arepo_ENERGY",res="512_20Mpc",first_subs_only=1,matching=1): import readsubf import numpy as np import readsnapHDF5 as rs base = "/n/hernquistfs1/mvogelsberger/ComparisonProject/" out_folder = "/output" if matching == 0: base_out = base + res + "/" + code_type + out_folder cat = readsubf.subfind_catalog(base_out,snapnum,masstab=True) if first_subs_only == 1: sub_ids = cat.group_firstsub else: print "Have not yet added functionality for analyzing not-first-in-group subhalos" M_subs = cat.sub_mass[sub_ids] ind = np.logical_and(M_subs > M_botlim, M_subs < M_toplim) M_subs = M_subs[ind] sub_ids = sub_ids[ind] return sub_ids if matching == 1: save_catalog = 0 massDiffThresh = 1.0 #unitless posDiffThresh = 60 #kpc code_type1 = "Arepo_ENERGY" code_type2 = "Gadget" code_type_list = [code_type1,code_type2] base1 = base + res + "/" + code_type1 + out_folder base2 = base + res + "/" + code_type2 + out_folder base_out = [base1,base2] cat = [readsubf.subfind_catalog(base_out[0],snapnum,masstab=True),readsubf.subfind_catalog(base_out[1],snapnum,masstab=True)] if first_subs_only == 1: sub_ids = [cat[0].group_firstsub, cat[1].group_firstsub] else: print "Have not yet added functionality for analyzing not-first-in-group subhalos" N_subs = [len(sub_ids[0]),len(sub_ids[1])] M = [cat[0].sub_mass[sub_ids[0]],cat[1].sub_mass[sub_ids[1]]] pos = [cat[0].sub_pos[sub_ids[0]],cat[1].sub_pos[sub_ids[1]]] matching_catalog = [] print "N_subs[0]",N_subs[0] for i in np.arange(N_subs[0]): locMass = M[0][i] locPos = pos[0][i] if locMass > M_botlim and locMass < M_toplim: # Only match halos in given mass range displace = locPos - pos[1] posDiff = np.arange(len(displace)) for j in np.arange(len(displace)): posDiff[j] = np.sqrt( np.dot(displace[j],displace[j])) if np.min(posDiff) < posDiffThresh: #require centers to overlap within given distance ind1 = posDiff < posDiffThresh N_match1 = ind1.sum() M1 = M[1][ind1] pos1 = pos[1][ind1] massDiff = abs(M1-locMass)/locMass if np.min(massDiff) < massDiffThresh: #require mass to match within given range ind2 = massDiff < massDiffThresh N_match = ind2.sum() if N_match > 1: print "More than 1 possible match for a halo found!" ind2 = np.argmin(massDiff) matching_catalog.append([sub_ids[0][i],sub_ids[1][ind1][ind2]]) N_matches = len(matching_catalog) print "\n\n"+"Matched "+str(N_matches)+" Halos" matching_catalog = np.array(matching_catalog) print "Matching catalog: " print matching_catalog if save_catalog == 1: # Save the matching catalog into a file: filename = res+'_'+'matching_groups_'+str(snapnum).zfill(3)+'.dat' #data = {'base_list': base_list, 'matching_catalog': matching_catalog} output = open(filename, 'wb') N_matches = np.uint32(N_matches) N_matches.astype("uint32").tofile(output) matching_catalog1 = matching_catalog[:,0] matching_catalog2 = matching_catalog[:,1] matching_catalog1.astype("uint32").tofile(output) matching_catalog2.astype("uint32").tofile(output) output.close() return matching_catalog
def run_series(base_id="base102", snap_num=313): import numpy as np import readsubf import os from base_lookup import directory from run_J_align import run_J_align from subsnap_write import subsnap_write import time import glob ############# #Control Parameters base = directory(base_id)[0] snap_num = 313 #directory(base_id)[1] save_dir = base_id + "/" resnap_folder = 'resnaps/' subsnap_folder = save_dir+'subsnaps/' # Overwrite past analysis? overw = 0 # (Analysis restricted to only primary subhalos in given group) # Analyze subhalos within a given mass range: M_botlim = 10. M_toplim = 1000. # Analyze set # of subhalos? analyze_N = 3#-1. # JOB CONTROL: #Concurrent jobs? job_limit = 10 #Time between job submission? wait_time = 1 #seconds ############################################################################################ if not os.path.exists(save_dir): os.system('mkdir '+save_dir) if not os.path.exists(subsnap_folder): os.system('mkdir '+subsnap_folder) cat = readsubf.subfind_catalog(base,snap_num,masstab=True) sub_ids = cat.group_firstsub M_subs = cat.sub_mass[sub_ids] ind = np.logical_and(M_subs >= M_botlim, M_subs < M_toplim) M_subs = M_subs[ind] sub_ids = sub_ids[ind] #N_subs = np.uint32(M_subs.size) # Can insert specific subhalos instead: sub_ids = [469] if analyze_N > 0.: sub_ids = sub_ids[0:analyze_N] print "Will submit "+str(len(sub_ids))+" jobs.\n" raw_input("Press Enter to continue...") ################################################################################################# resnap = resnap_folder+base_id+"_"+"S"+str(snap_num).zfill(3)+'.resnap' #Write intermediate .snap files: subsnap_write(resnap_name=resnap,base=base,snap_num=snap_num,sub_ids=sub_ids,save_dir=save_dir) # Job group control: grp_name = "/bd_decomp" add_grp = "bgadd -L "+str(job_limit)+" "+grp_name mod_grp = "bgmod -L "+str(job_limit)+" "+grp_name os.system(add_grp) os.system(mod_grp) ################################################ def submit_job(base_id, base, snap_num, sub_id, dat_list, save_dir): if overw == 0: subsnap_name = save_dir+str(sub_id).zfill(5)+".dat" if subsnap_name in dat_list: print subsnap_name print "Done with this one!" else: print "Could not find ",subsnap_name,"... submitting job." #run_bd(base_id, base, snap_num, sub_id, grp_name) run_J_align(base_id, base, snap_num, sub_id, grp_name) print "Waiting ",str(wait_time), "seconds to submit next job..." time.sleep(wait_time) else: #run_bd(base_id, base, snap_num, sub_id, grp_name) run_J_align(base_id, base, snap_num, sub_id, grp_name) print "Waiting ",str(wait_time), "seconds to submit next job..." time.sleep(wait_time) ################################################ dat_list = glob.glob(save_dir+'*.dat') n_matches = len(sub_ids) for i in np.arange(n_matches): print str(i) +" of "+str(n_matches) submit_job(base_id=base_id,base=base,snap_num=snap_num,sub_id=sub_ids[i],dat_list=dat_list,save_dir=save_dir) print "Job submission done!"
def mass_function(groups_fname,groups_number,obj,BoxSize,bins,f_out, min_mass=None,max_mass=None, long_ids_flag=True,SFR_flag=False): #bins_mass=np.logspace(np.log10(min_mass),np.log10(max_mass),bins+1) #mass_mean=10**(0.5*(np.log10(bins_mass[1:])+np.log10(bins_mass[:-1]))) #dM=bins_mass[1:]-bins_mass[:-1] if obj=='FoF': #read FoF halos information fof=readfof.FoF_catalog(groups_fname,groups_number, long_ids=long_ids_flag,swap=False,SFR=SFR_flag) F_pos=fof.GroupPos/1e3 #positions in Mpc/h F_mass=fof.GroupMass*1e10 #masses in Msun/h F_part=fof.GroupLen #number particles belonging to the group F_Mpart=F_mass[0]/F_part[0] #mass of a single particle in Msun/h del fof #some verbose print '\nNumber of FoF halos=',len(F_pos) print '%f < X_fof < %f'%(np.min(F_pos[:,0]),np.max(F_pos[:,0])) print '%f < Y_fof < %f'%(np.min(F_pos[:,1]),np.max(F_pos[:,1])) print '%f < Z_fof < %f'%(np.min(F_pos[:,2]),np.max(F_pos[:,2])) print '%e < M_fof < %e\n'%(np.min(F_mass),np.max(F_mass)) #Correct the masses of the FoF halos F_mass=F_Mpart*(F_part*(1.0-F_part**(-0.6))) #compute the minimum and maximum mass if min_mass==None: min_mass=np.min(F_mass) if max_mass==None: max_mass=np.max(F_mass) print 'M_min = %e'%(min_mass) print 'M_max = %e\n'%(max_mass) #find the masses and mass intervals bins_mass=np.logspace(np.log10(min_mass),np.log10(max_mass),bins+1) mass_mean=10**(0.5*(np.log10(bins_mass[1:])+np.log10(bins_mass[:-1]))) dM=bins_mass[1:]-bins_mass[:-1] #compute the number of halos within each mass interval number=np.histogram(F_mass,bins=bins_mass)[0] print number; print np.sum(number,dtype=np.float64) elif obj=='halos_m200': #read CDM halos information halos=readsubf.subfind_catalog(groups_fname,groups_number, group_veldisp=True,masstab=True, long_ids=True,swap=False) H_pos=halos.group_pos/1e3 #positions in Mpc/h H_mass=halos.group_m_mean200*1e10 #masses in Msun/h H_radius_m=halos.group_r_mean200/1e3 #radius in Mpc/h del halos #some verbose print '\nNumber of halos=',len(H_pos) print '%f < X < %f'%(np.min(H_pos[:,0]),np.max(H_pos[:,0])) print '%f < Y < %f'%(np.min(H_pos[:,1]),np.max(H_pos[:,1])) print '%f < Z < %f'%(np.min(H_pos[:,2]),np.max(H_pos[:,2])) print '%e < M < %e\n'%(np.min(H_mass),np.max(H_mass)) #compute the minimum and maximum mass if min_mass==None: min_mass=np.min(H_mass) if max_mass==None: max_mass=np.max(H_mass) #compute the number of halos within each mass interval bins_mass=np.logspace(np.log10(min_mass),np.log10(max_mass),bins+1) mass_mean=10**(0.5*(np.log10(bins_mass[1:])+np.log10(bins_mass[:-1]))) dM=bins_mass[1:]-bins_mass[:-1] number=np.histogram(H_mass,bins=bins_mass)[0] print number; print np.sum(number,dtype=np.float64) elif obj=='halos_c200': #read CDM halos information halos=readsubf.subfind_catalog(groups_fname,groups_number, group_veldisp=True,masstab=True, long_ids=True,swap=False) H_pos=halos.group_pos/1e3 #positions in Mpc/h H_mass=halos.group_m_crit200*1e10 #masses in Msun/h H_radius_m=halos.group_r_crit200/1e3 #radius in Mpc/h del halos #some verbose print '\nNumber of halos=',len(H_pos) print '%f < X < %f'%(np.min(H_pos[:,0]),np.max(H_pos[:,0])) print '%f < Y < %f'%(np.min(H_pos[:,1]),np.max(H_pos[:,1])) print '%f < Z < %f'%(np.min(H_pos[:,2]),np.max(H_pos[:,2])) print '%e < M < %e\n'%(np.min(H_mass),np.max(H_mass)) #compute the minimum and maximum mass if min_mass==None: min_mass=np.min(H_mass) if max_mass==None: max_mass=np.max(H_mass) #compute the number of halos within each mass interval bins_mass=np.logspace(np.log10(min_mass),np.log10(max_mass),bins+1) mass_mean=10**(0.5*(np.log10(bins_mass[1:])+np.log10(bins_mass[:-1]))) dM=bins_mass[1:]-bins_mass[:-1] number=np.histogram(H_mass,bins=bins_mass)[0] print number; print np.sum(number,dtype=np.float64) elif obj=='subhalos': #read CDM halos information halos=readsubf.subfind_catalog(groups_fname,groups_number, group_veldisp=True,masstab=True, long_ids=True,swap=False) S_pos=halos.sub_pos/1e3 #positions in Mpc/h S_mass=halos.sub_mass*1e10 #masses in Msun/h del halos #some verbose print '\nNumber of subhalos=',len(S_pos) print '%f < X < %f'%(np.min(S_pos[:,0]),np.max(S_pos[:,0])) print '%f < Y < %f'%(np.min(S_pos[:,1]),np.max(S_pos[:,1])) print '%f < Z < %f'%(np.min(S_pos[:,2]),np.max(S_pos[:,2])) print '%e < M < %e\n'%(np.min(S_mass),np.max(S_mass)) #compute the minimum and maximum mass if min_mass==None: min_mass=np.min(S_mass) if max_mass==None: max_mass=np.max(S_mass) #compute the number of halos within each mass interval bins_mass=np.logspace(np.log10(min_mass),np.log10(max_mass),bins+1) mass_mean=10**(0.5*(np.log10(bins_mass[1:])+np.log10(bins_mass[:-1]))) dM=bins_mass[1:]-bins_mass[:-1] number=np.histogram(S_mass,bins=bins_mass)[0] print number; print np.sum(number,dtype=np.float64) else: print 'bad object type selected' sys.exit() MF=number/(dM*BoxSize**3) delta_MF=np.sqrt(number)/(dM*BoxSize**3) f=open(f_out,'w') for i in range(bins): f.write(str(mass_mean[i])+' '+str(MF[i])+' '+str(delta_MF[i])+'\n') f.close()
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
def mass_function_fsigma(groups_fname, groups_number, f_out, min_mass, max_mass, bins, BoxSize, obj, Omega_M, k, Pk): rhoM = rho_crit * Omega_M bins_mass = np.logspace(np.log10(min_mass), np.log10(max_mass), bins + 1) mass_mean = 10**(0.5 * (np.log10(bins_mass[1:]) + np.log10(bins_mass[:-1]))) if obj == 'FoF': #read FoF halos information fof = readfof.FoF_catalog(groups_fname, groups_number, long_ids=True, swap=False) F_pos = fof.GroupPos / 1e3 #positions in Mpc/h F_mass = fof.GroupMass * 1e10 #masses in Msun/h F_part = fof.GroupLen #number particles belonging to the group F_Mpart = F_mass[0] / F_part[0] #mass of a single particle in Msun/h del fof #Correct the masses of the FoF halos F_mass = F_Mpart * (F_part * (1.0 - F_part**(-0.6))) #some verbose print 'Number of FoF halos=', len(F_pos) print np.min(F_pos[:, 0]), '< X_fof <', np.max(F_pos[:, 0]) print np.min(F_pos[:, 1]), '< Y_fof <', np.max(F_pos[:, 1]) print np.min(F_pos[:, 2]), '< Z_fof <', np.max(F_pos[:, 2]) print np.min(F_mass), '< M_fof <', np.max(F_mass) number = np.histogram(F_mass, bins=bins_mass)[0] print number print np.sum(number, dtype=np.float64) elif obj == 'halos_m200': #read CDM halos information halos = readsubf.subfind_catalog(groups_fname, groups_number, group_veldisp=True, masstab=True, long_ids=True, swap=False) H_pos = halos.group_pos / 1e3 #positions in Mpc/h H_mass = halos.group_m_mean200 * 1e10 #masses in Msun/h H_radius_m = halos.group_r_mean200 / 1e3 #radius in Mpc/h del halos #some verbose print 'Number of halos=', len(H_pos) print np.min(H_pos[:, 0]), '< X_fof <', np.max(H_pos[:, 0]) print np.min(H_pos[:, 1]), '< Y_fof <', np.max(H_pos[:, 1]) print np.min(H_pos[:, 2]), '< Z_fof <', np.max(H_pos[:, 2]) print np.min(H_mass), '< M_fof <', np.max(H_mass) number = np.histogram(H_mass, bins=bins_mass)[0] print number print np.sum(number, dtype=np.float64) else: print 'bad object type selected' sys.exit() sigma_mean = np.empty(bins) f_sigma = np.empty(bins) delta_f_sigma = np.empty(bins) for i in range(bins): R1 = (3.0 * bins_mass[i] / (4.0 * pi * rhoM))**(1.0 / 3.0) sigma1 = sigma(k, Pk, R1) R2 = (3.0 * bins_mass[i + 1] / (4.0 * pi * rhoM))**(1.0 / 3.0) sigma2 = sigma(k, Pk, R2) sigma_mean[i] = 0.5 * (sigma2 + sigma1) f_sigma[i] = (number[i] / np.log(sigma2 / sigma1)) / BoxSize**3 f_sigma[i] = -(mass_mean[i] / rhoM) * f_sigma[i] delta_f_sigma[i] = (np.sqrt(number[i]) / np.log(sigma2 / sigma1)) / BoxSize**3 delta_f_sigma[i] = -(mass_mean[i] / rhoM) * delta_f_sigma[i] f = open(f_out, 'w') for i in range(bins): f.write( str(sigma_mean[i]) + ' ' + str(f_sigma[i]) + ' ' + str(delta_f_sigma[i]) + ' ' + str(mass_mean[i]) + '\n') f.close()
sys.exit() #just keep with the particles having HI masses M_HI = M_HI[IDs] pos = pos[IDs] R = R[IDs] del IDs #compute the value of Omega_HI print 'Omega_HI = %e' % (np.sum(M_HI, dtype=np.float64) / BoxSize**3 / rho_crit) #read FoF/Subfind halos information halos = readsubf.subfind_catalog(groups_fname, groups_number, group_veldisp=True, masstab=True, long_ids=long_ids_flag, swap=False) pos_SO = halos.group_pos / 1e3 #Mpc/h M_SO = halos.group_m_mean200 * 1e10 #Msun/h. SO mass R_SO = halos.group_r_mean200 / 1e3 #Mpc/h M_FoF = halos.group_mass * 1e10 #Msun/h. FoF mass del halos """#write X-Y positions and R of the halos f=open('borrar.dat','w') for i in range(len(R_SO)): print i if M_FoF[i]>8.75e8: f.write(str(pos_SO[i,0])+' '+str(pos_SO[i,1])+' '+str(pos_SO[i,2])+\ ' '+str(R_SO[i])+' '+str(M_FoF[i])+'\n') f.close()"""
def recenter_halo(halo): import numpy as np import readsubf # Initialize variables: base = halo.base snap_type = halo.snap_type snap_name = halo.snap_name snap_num = halo.snap_num sub_id = halo.sub_id code_type = halo.code_type res = halo.res save_dir = halo.save_dir sub_id = halo.sub_id gal_pos = halo.gal_pos gal_vel = halo.gal_vel gal_mass = halo.gal_mass gal_pot = halo.gal_pot gal_T_gas = halo.gal_T_gas gal_rho_gas = halo.gal_rho_gas gal_age = halo.gal_age type_thresh = halo.type_thresh # Move to the frame where the center of the galaxy is at rest, and at the origin: print "Re-centering..." if sub_id != -1: cat = readsubf.subfind_catalog(base,snap_num,masstab=True) gal_cent_pos = cat.sub_pos[sub_id] gal_cent_vel = cat.sub_vel[sub_id] for j in np.arange(3): gal_pos[j] = gal_pos[j] - gal_cent_pos gal_vel[j] = gal_vel[j] - gal_cent_vel # Cut off stars at a certain distance from the center: set by kpc_cutoff kpc_cutoff = 30. halo.kpc_cutoff = kpc_cutoff # First a crude cut (to save memory): for j in np.arange(3): #particle types for k in np.arange(3): #dimensions (x,y,z) bool_cut = abs(gal_pos[j][:,k]) < kpc_cutoff if bool_cut.sum() < type_thresh: print "Not enough particles within kpc_cutoff" halo.err_flag = 1 return else: gal_pos[j] = gal_pos[j][bool_cut] gal_vel[j] = gal_vel[j][bool_cut] gal_mass[j] = gal_mass[j][bool_cut] gal_pot[j] = gal_pot[j][bool_cut] if j == 0: gal_T_gas = gal_T_gas[bool_cut] gal_rho_gas = gal_rho_gas[bool_cut] elif j == 2: gal_age = gal_age[bool_cut] # Better cut (radial): #Calculate radii: radii = [0]*3 for j in np.arange(3): radii[j] = np.zeros(len(gal_pos[j])) for k in np.arange(len(gal_pos[j])): radii[j][k] = np.sqrt(np.dot(gal_pos[j][k],gal_pos[j][k])) for j in np.arange(3): #particle types bool_cut2 = abs(radii[j]) < kpc_cutoff if bool_cut2.sum() < type_thresh: print "Not enough particles within kpc_cutoff" halo.err_flag = 1 return else: gal_pos[j] = gal_pos[j][bool_cut2] gal_vel[j] = gal_vel[j][bool_cut2] gal_mass[j] = gal_mass[j][bool_cut2] gal_pot[j] = gal_pot[j][bool_cut2] radii[j] = radii[j][bool_cut2] if j == 0: gal_T_gas = gal_T_gas[bool_cut2] gal_rho_gas = gal_rho_gas[bool_cut2] elif j == 2: gal_age = gal_age[bool_cut2] # Calculate baryonic mass, stellar mass, gas fraction... gas_mass = gal_mass[0].sum() star_mass = gal_mass[2].sum() bary_mass = gas_mass + star_mass gas_frac = gas_mass/(gas_mass+star_mass) # Exporting variables halo.gal_pos = gal_pos halo.gal_vel = gal_vel halo.gal_mass= gal_mass halo.gal_pot = gal_pot halo.gal_T_gas = gal_T_gas halo.gal_rho_gas = gal_rho_gas halo.gal_age = gal_age halo.radii = radii halo.gas_mass = gas_mass halo.star_mass = star_mass halo.bary_mass = bary_mass halo.gas_frac = gas_frac
def mass_function_fsigma(groups_fname,groups_number,f_out,min_mass,max_mass, bins,BoxSize,obj,Omega_M,k,Pk): rhoM=rho_crit*Omega_M bins_mass=np.logspace(np.log10(min_mass),np.log10(max_mass),bins+1) mass_mean=10**(0.5*(np.log10(bins_mass[1:])+np.log10(bins_mass[:-1]))) if obj=='FoF': #read FoF halos information fof=readfof.FoF_catalog(groups_fname,groups_number, long_ids=True,swap=False) F_pos=fof.GroupPos/1e3 #positions in Mpc/h F_mass=fof.GroupMass*1e10 #masses in Msun/h F_part=fof.GroupLen #number particles belonging to the group F_Mpart=F_mass[0]/F_part[0] #mass of a single particle in Msun/h del fof #Correct the masses of the FoF halos F_mass=F_Mpart*(F_part*(1.0-F_part**(-0.6))) #some verbose print 'Number of FoF halos=',len(F_pos) print np.min(F_pos[:,0]),'< X_fof <',np.max(F_pos[:,0]) print np.min(F_pos[:,1]),'< Y_fof <',np.max(F_pos[:,1]) print np.min(F_pos[:,2]),'< Z_fof <',np.max(F_pos[:,2]) print np.min(F_mass),'< M_fof <',np.max(F_mass) number=np.histogram(F_mass,bins=bins_mass)[0] print number; print np.sum(number,dtype=np.float64) elif obj=='halos_m200': #read CDM halos information halos=readsubf.subfind_catalog(groups_fname,groups_number, group_veldisp=True,masstab=True, long_ids=True,swap=False) H_pos=halos.group_pos/1e3 #positions in Mpc/h H_mass=halos.group_m_mean200*1e10 #masses in Msun/h H_radius_m=halos.group_r_mean200/1e3 #radius in Mpc/h del halos #some verbose print 'Number of halos=',len(H_pos) print np.min(H_pos[:,0]),'< X_fof <',np.max(H_pos[:,0]) print np.min(H_pos[:,1]),'< Y_fof <',np.max(H_pos[:,1]) print np.min(H_pos[:,2]),'< Z_fof <',np.max(H_pos[:,2]) print np.min(H_mass),'< M_fof <',np.max(H_mass) number=np.histogram(H_mass,bins=bins_mass)[0] print number; print np.sum(number,dtype=np.float64) else: print 'bad object type selected' sys.exit() sigma_mean=np.empty(bins); f_sigma=np.empty(bins) delta_f_sigma=np.empty(bins) for i in range(bins): R1=(3.0*bins_mass[i]/(4.0*pi*rhoM))**(1.0/3.0) sigma1=sigma(k,Pk,R1) R2=(3.0*bins_mass[i+1]/(4.0*pi*rhoM))**(1.0/3.0) sigma2=sigma(k,Pk,R2) sigma_mean[i]=0.5*(sigma2+sigma1) f_sigma[i]=(number[i]/np.log(sigma2/sigma1))/BoxSize**3 f_sigma[i]=-(mass_mean[i]/rhoM)*f_sigma[i] delta_f_sigma[i]=(np.sqrt(number[i])/np.log(sigma2/sigma1))/BoxSize**3 delta_f_sigma[i]=-(mass_mean[i]/rhoM)*delta_f_sigma[i] f=open(f_out,'w') for i in range(bins): f.write(str(sigma_mean[i])+' '+str(f_sigma[i])+' '+str(delta_f_sigma[i])+' '+str(mass_mean[i])+'\n') f.close()