def gas_velo_at_particle_pos( varfiles="last4", sim=False, scheme="tsc", use_IDL=False, OVERWRITE=False ): """This script calulates the gas velocity at the particle position and stores this together with particle position, containing grid cell idicies, particle velocities, and particle index in a gas_velo_at_particle_pos file. Args: varfiles: specifiy varfiles for calculation, e.g. 'last', 'first', 'all', 'VAR###', 'last4', 'first3' scheme: possible are: - ngp: nearest grid point - cic: cloud in cell - tsc: triangular shaped cloud OVERWRITE: set to True to overwrite already calculated results """ from pencil import get_sim from pencil import read from pencil import diag from pencil.io import mkdir from os import listdir from os.path import exists, join, dirname import numpy as np GAS_VELO_TAG = "gas_velo_at_particle_pos" if sim == False: sim = get_sim() if sim == False: print("! ERROR: Specify simulation object!") return False SIM = sim if use_IDL: print( "? WARNING: IDL VERSION OF THIS SCRIPT BY JOHANSEN, not recommended for 2D data" ) from ...backpack import pidly print("## starting IDL engine..") IDL = pidly.IDL(long_delay=0.05) # start IDL engine ## skip if nothing is new if ( (not OVERWRITE) and (exists(join(SIM.pc_datadir, "sigma.pkl"))) and (exists(join(SIM.pc_datadir, "zeta.pkl"))) ): print( "~ " + SIM.name + " is already calculated and up-to-date! -> skipping it!" ) else: ## start calculations print( '~ Calculating gas_velo_at_particle_pos for "' + SIM.name + '" in "' + SIM.path + '"' ) IDL( ".COMPILE " + str( join( dirname(diag.particle.__file__), "gas_velo_at_particle_pos.pro" ) ) ) IDL.pro( "gas_velo_at_particle_pos", datadir=SIM.datadir, destination=GAS_VELO_TAG, doforthelastNvar=varfiles[4:], ) files = [ i.split("_")[-1].split(".sav")[0] for i in listdir(join(SIM.pc_datadir, GAS_VELO_TAG)) if i.startswith(GAS_VELO_TAG) and i.endswith(".sav") or i.endswith(".pkl") ] if files == []: print( "!! ERROR: No calc_gas_speed_at_particle_position-files found for " + SIM.name + "! Use idl script to produce them first!" ) IDL.close() return True else: print( '~ Calculating gas_velo_at_particle_pos for "' + SIM.name + '" in "' + SIM.path + '"' ) save_destination = join(SIM.pc_datadir, GAS_VELO_TAG) mkdir(save_destination) varlist = SIM.get_varlist(pos=varfiles, particle=False) pvarlist = SIM.get_varlist(pos=varfiles, particle=True) for f, p in zip(varlist, pvarlist): save_filename = GAS_VELO_TAG + "_" + scheme + "_" + f[3:] if not OVERWRITE and exists(save_filename, folder=save_destination): continue print("## Reading " + f + " ...") ff = read.var(datadir=SIM.datadir, varfile=f, quiet=True, trimall=False) pp = read.pvar(datadir=SIM.datadir, varfile=p) ## remove ghost zones from grid, call the reduced grid the "real grid" realgridx = ff.x[ff.l1 : ff.l2] realgridy = ff.y[ff.m1 : ff.m2] realgridz = ff.z[ff.n1 : ff.n2] nx = ff.l2 - ff.l1 ny = ff.m2 - ff.m1 nz = ff.n2 - ff.n1 ## prepare list for all quantities l_ipars = pp.ipars # particle number KNOWN l_px = pp.xp l_py = pp.yp l_pz = pp.zp # particle absolut position KNOWN l_vx = pp.vpx l_vy = pp.vpy l_vz = pp.vpz # particle velocity KNOWN l_rix = [] l_riy = [] l_riz = ( [] ) # particle untrimmed realgrid index (grid index = l/m/n + readgrid index ???) l_ix = [] l_iy = [] l_iz = [] # particle grid index (in untrimmed grid) l_ux = [] l_uy = [] l_uz = [] # underlying gas velocity at position of particle ## get index of realgrid cell for each particle for i in range(len(l_ipars)): l_rix.append(np.abs(realgridx - l_px[i]).argmin()) l_riy.append(np.abs(realgridy - l_py[i]).argmin()) l_riz.append(np.abs(realgridz - l_pz[i]).argmin()) ## convert into untrimmed grid l_ix = np.array(l_rix) + ff.l1 l_iy = np.array(l_riy) + ff.m1 l_iz = np.array(l_riz) + ff.n1 ## NGP if scheme == "ngp" or scheme == "NGP": print("## Calculating gas velocities via " + scheme) l_ux = ff.ux[l_iz, l_iy, l_ix] l_uy = ff.uy[l_iz, l_iy, l_ix] l_uz = ff.uz[l_iz, l_iy, l_ix] ## CIC if scheme == "cic" or scheme == "CIC": print("## Calculating gas velocities via " + scheme) for ix0, iy0, iz0, px, py, pz in zip( l_ix, l_iy, l_iz, l_px, l_py, l_pz ): # for each particle if ff.x[ix0] > px: ix0 = ix0 - 1 # ix0 must be left to particle if ff.y[iy0] > py: iy0 = iy0 - 1 # iy0 must be below the particle if ff.z[iz0] > pz: iz0 = iz0 - 1 # iz0 must be under particle ix1 = ix0 iy1 = iy0 iz1 = iz0 # if a dim. is zero, this is default, else: if nx > 1: ix1 = ix0 + 1 dx_1 = ( 1.0 / ff.dx ) # if a dim is non-zero, ajust ix1 to right cell if ny > 1: iy1 = iy0 + 1 dy_1 = ( 1.0 / ff.dy ) # if a dim is non-zero, ajust iy1 to above cell if nz > 1: iz1 = iz0 + 1 dz_1 = ( 1.0 / ff.dz ) # if a dim is non-zero, ajust iz1 to above cell ux = 0.0 uy = 0.0 uz = 0.0 for ix in [ix0, ix1]: for iy in [iy0, iy1]: for iz in [iz0, iz1]: weight = 1.0 if nx > 1: weight = weight * (1.0 - abs(px - ff.x[ix]) * dx_1) if ny > 1: weight = weight * (1.0 - abs(py - ff.y[iy]) * dy_1) if nz > 1: weight = weight * (1.0 - abs(pz - ff.z[iz]) * dz_1) ux = ux + weight * ff.ux[iz, iy, ix] uy = uy + weight * ff.uy[iz, iy, ix] uz = uz + weight * ff.uz[iz, iy, ix] if iz0 == iz1: break # beware of degeneracy: if iy0 == iy1: break # beware of degeneracy: if ix0 == ix1: break # beware of degeneracy: l_ux.append(ux) l_uy.append(uy) l_uz.append(uz) ## TSC if scheme == "tsc" or scheme == "TSC": for ix0, iy0, iz0, px, py, pz in zip( l_ix, l_iy, l_iz, l_px, l_py, l_pz ): # for each particle ixx0 = ix0 ixx1 = ix0 # beware of degeneracy iyy0 = iy0 iyy1 = iy0 izz0 = iz0 izz1 = iz0 if nx > 1: ixx0 = ix0 - 1 ixx1 = ix0 + 1 dx_1 = 1.0 / ff.dx dx_2 = 1.0 / ff.dx ** 2 if ny > 1: iyy0 = iy0 - 1 iyy1 = iy0 + 1 dy_1 = 1.0 / ff.dy dy_2 = 1.0 / ff.dy ** 2 if nz > 1: izz0 = iz0 - 1 izz1 = iz0 + 1 dz_1 = 1.0 / ff.dz dz_2 = 1.0 / ff.dz ** 2 ux = 0.0 uy = 0.0 uz = 0.0 for ix in [ix0, ixx0, ixx1]: weight_x = 0.0 if ix - ix0 == -1 or ix - ix0 == 1: weight_x = ( 1.125 - 1.5 * abs(px - ff.x[ix]) * dx_1 + 0.5 * abs(px - ff.x[ix]) ** 2 * dx_2 ) elif nx != 1: weight_x = 0.75 - (px - ff.x[ix]) ** 2 * dx_2 for iy in [iy0, iyy0, iyy1]: weight_y = 0.0 if iy - iy0 == -1 or iy - iy0 == 1: weight_y = ( 1.125 - 1.5 * abs(py - ff.y[iy]) * dy_1 + 0.5 * abs(py - ff.y[iy]) ** 2 * dy_2 ) elif ny != 1: weight_y = 0.75 - (py - ff.y[iy]) ** 2 * dy_2 for iz in [iz0, izz0, izz1]: weight_z = 0.0 if iz - iz0 == -1 or iz - iz0 == 1: weight_z = ( 1.125 - 1.5 * abs(pz - ff.z[iz]) * dz_1 + 0.5 * abs(pz - ff.z[iz]) ** 2 * dz_2 ) elif nz != 1: weight_z = 0.75 - (pz - ff.z[iz]) ** 2 * dz_2 weight = 1.0 if nx > 1: weight = weight * weight_x if ny > 1: weight = weight * weight_y if nz > 1: weight = weight * weight_z ux = ux + weight * ff.ux[iz, iy, ix] uy = uy + weight * ff.uy[iz, iy, ix] uz = uz + weight * ff.uz[iz, iy, ix] if izz0 == izz1: break # beware of degeneracy: if iyy0 == iyy1: break # beware of degeneracy: if ixx0 == ixx1: break # beware of degeneracy: l_ux.append(ux) l_uy.append(uy) l_uz.append(uz) ## Convert all information into a single record array data_set = np.core.records.fromarrays( [ l_ipars.astype("int"), l_px, l_py, l_pz, l_vx, l_vy, l_vz, l_rix, l_riy, l_riz, l_ix, l_iy, l_iz, l_ux, l_uy, l_uz, ], names="ipar, ipx, ipy, ipz, vx, vy, vz, rix, riy, riz, ix, iy, iz, ux, uy, uz", formats="int, float, float, float, float, float, float, int, int, int, int, int, int, float, float, float", ) gas_velo_at_particle_pos = np.sort(data_set, order=["ix", "iy", "iz"]) Nix = int(gas_velo_at_particle_pos["rix"].max() + 1) Niy = int(gas_velo_at_particle_pos["riy"].max() + 1) Niz = int(gas_velo_at_particle_pos["riz"].max() + 1) Npar_arr = np.array( [ gas_velo_at_particle_pos["rix"], gas_velo_at_particle_pos["riy"], gas_velo_at_particle_pos["riz"], ] ) # rgrid_edges = (grid.x[1:]-(grid.x[1:]-grid.x[:-1])/2)[2:-2] xrange = np.arange(0, float(gas_velo_at_particle_pos["rix"].max()) + 2) xrange = xrange - 0.5 yrange = np.arange(0, float(gas_velo_at_particle_pos["riy"].max()) + 2) zrange = np.arange(0, float(gas_velo_at_particle_pos["riz"].max()) + 2) Npar_hist, edges = np.histogramdd(Npar_arr.T, bins=(xrange, yrange, zrange)) Npar_hist, edges = np.histogramdd(Npar_arr.T, bins=(Nix, Niy, Niz)) gas_velo_at_particle_pos = { "time": ff.t, "par_pos": np.array( [ gas_velo_at_particle_pos["ipx"], gas_velo_at_particle_pos["ipy"], gas_velo_at_particle_pos["ipz"], ] ), "par_velo": np.array( [ gas_velo_at_particle_pos["vx"], gas_velo_at_particle_pos["vy"], gas_velo_at_particle_pos["vz"], ] ), "par_idx": np.array( [ gas_velo_at_particle_pos["rix"], gas_velo_at_particle_pos["riy"], gas_velo_at_particle_pos["riz"], ] ), "npar": np.array( Npar_hist[ gas_velo_at_particle_pos["rix"], gas_velo_at_particle_pos["riy"], gas_velo_at_particle_pos["riz"], ] ), "gas_velo": np.array( [ gas_velo_at_particle_pos["ux"], gas_velo_at_particle_pos["uy"], gas_velo_at_particle_pos["uz"], ] ), } print("## Saving dataset into " + save_destination + "...") pkl_save( {"gas_velo_at_particle_pos": gas_velo_at_particle_pos, "t": ff.t}, save_filename, folder=save_destination, ) print("## Done!")
def particles_to_vtk( var_file="pvar.dat", datadir="data", proc=-1, destination="particles.vtk", ti=-1, tf=-1, binary=True, ): """ Read the pVAR files from Pencil Code and write them as vtk files. call signature: particles_to_vtk(var_file='pvar.dat', datadir='data', proc=-1, destination='particles.vtk', ti=-1, tf=-1, binary=True) Keyword arguments: *var_file*: Name of the PVAR file. *datadir*: Directory where the data is stored. *proc*: Processor to be read. If -1 read all and assemble to one array. *destination*: Destination file (only if ti, tf > 0). *ti*: Initial time index for animation. *tf*: Final time index for animation. *binary*: Determines if binary or clear text data for the vtk files. """ from pencil import read # Read the particle data and save it in a list. pvar_list = [] if (ti >= 0) and (tf >= 0): for tidx in range(ti, tf): var_file = "PVAR{0}".format(tidx) pvar = read.pvar(varfile=var_file, datadir=datadir, proc=proc) pvar_list.append(pvar) else: pvar = read.pvar(varfile=var_file, datadir=datadir, proc=proc) pvar_list.append(pvar) # Convert the data into vtk. particles_vtk_tmp = ParticlesVtk() particles_vtk_tmp.convert_to_vtk(pvar_list) # Define some constants. particles_vtk_tmp.ti = ti particles_vtk_tmp.tf = tf particles_vtk_tmp.binary = binary particles_vtk_tmp.destination = destination # Write the data inot vtk files. particles_vtk_tmp.write_to_vtk() return particles_vtk_tmp
def gas_velo_at_particle_pos(varfiles='last4', sim=False, scheme='tsc', use_IDL=False, OVERWRITE=False): """This script calulates the gas velocity at the particle position and stores this together with particle position, containing grid cell idicies, particle velocities, and particle index in a gas_velo_at_particle_pos file. Args: varfiles: specifiy varfiles for calculation, e.g. 'last', 'first', 'all', 'VAR###', 'last4', 'first3' scheme: possible are: - ngp: nearest grid point - cic: cloud in cell - tsc: triangular shaped cloud OVERWRITE: set to True to overwrite already calculated results """ import os from pencil import io from pencil import read from pencil import get_sim from os.path import exists import numpy as np GAS_VELO_TAG = 'gas_velo_at_particle_pos' if sim == False: sim = get_sim() if sim == False: print('! ERROR: Specify simulation object!') return False SIM = sim if use_IDL: print( '? WARNING: IDL VERSION OF THIS SCRIPT BY JOHANSEN, not recommended for 2D data' ) from pencil.backpack import pidly print('## starting IDL engine..') IDL = pidly.IDL(long_delay=0.05) # start IDL engine ## skip if nothing is new if (not OVERWRITE) and (exists( os.path.join(SIM.pc_datadir, 'sigma.pkl'))) and (exists( os.path.join(SIM.pc_datadir, 'zeta.pkl'))): print('~ ' + SIM.name + ' is already calculated and up-to-date! -> skipping it!') else: ## start calculations print('~ Calculating gas_velo_at_particle_pos for "' + SIM.name + '" in "' + SIM.path + '"') IDL.pro('gas_velo_at_particle_pos', datadir=SIM.datadir, destination=GAS_VELO_TAG, doforthelastNvar=varfiles[4:]) files = [ i.split('_')[-1].split('.sav')[0] for i in os.listdir(os.path.join(SIM.pendatadir, GAS_VELO_TAG)) if i.startswith(GAS_VELO_TAG) and i.endswith('.sav') or i.endswith('.pkl') ] if files == []: print( '!! ERROR: No calc_gas_speed_at_particle_position-files found for ' + SIM.name + '! Use idl script to produce them first!') IDL.close() return True else: print('~ Calculating gas_velo_at_particle_pos for "' + SIM.name + '" in "' + SIM.path + '"') save_destination = os.path.join(SIM.pc_datadir, GAS_VELO_TAG) io.mkdir(save_destination) varlist = SIM.get_varlist(pos=varfiles, particle=False) pvarlist = SIM.get_varlist(pos=varfiles, particle=True) for f, p in zip(varlist, pvarlist): save_filename = GAS_VELO_TAG + '_' + scheme + '_' + f[3:] if not OVERWRITE and exists(save_filename, folder=save_destination): continue print('## Reading ' + f + ' ...') ff = read.var(datadir=SIM.datadir, varfile=f, quiet=True, trimall=False) pp = read.pvar(datadir=SIM.datadir, varfile=p) ## remove ghost zones from grid, call the reduced grid the "real grid" realgridx = ff.x[ff.l1:ff.l2] realgridy = ff.y[ff.m1:ff.m2] realgridz = ff.z[ff.n1:ff.n2] nx = ff.l2 - ff.l1 ny = ff.m2 - ff.m1 nz = ff.n2 - ff.n1 ## prepare list for all quantities l_ipars = pp.ipars # particle number KNOWN l_px = pp.xp l_py = pp.yp l_pz = pp.zp # particle absolut position KNOWN l_vx = pp.vpx l_vy = pp.vpy l_vz = pp.vpz # particle velocity KNOWN l_rix = [] l_riy = [] l_riz = [ ] # particle untrimmed realgrid index (grid index = l/m/n + readgrid index ???) l_ix = [] l_iy = [] l_iz = [] # particle grid index (in untrimmed grid) l_ux = [] l_uy = [] l_uz = [] # underlying gas velocity at position of particle ## get index of realgrid cell for each particle for i in range(len(l_ipars)): l_rix.append(np.abs(realgridx - l_px[i]).argmin()) l_riy.append(np.abs(realgridy - l_py[i]).argmin()) l_riz.append(np.abs(realgridz - l_pz[i]).argmin()) ## convert into untrimmed grid l_ix = np.array(l_rix) + ff.l1 l_iy = np.array(l_riy) + ff.m1 l_iz = np.array(l_riz) + ff.n1 ## NGP if scheme == 'ngp' or scheme == 'NGP': print('## Calculating gas velocities via ' + scheme) l_ux = ff.ux[l_iz, l_iy, l_ix] l_uy = ff.uy[l_iz, l_iy, l_ix] l_uz = ff.uz[l_iz, l_iy, l_ix] ## CIC if scheme == 'cic' or scheme == 'CIC': print('## Calculating gas velocities via ' + scheme) for ix0, iy0, iz0, px, py, pz in zip( l_ix, l_iy, l_iz, l_px, l_py, l_pz): # for each particle if ff.x[ix0] > px: ix0 = ix0 - 1 # ix0 must be left to particle if ff.y[iy0] > py: iy0 = iy0 - 1 # iy0 must be below the particle if ff.z[iz0] > pz: iz0 = iz0 - 1 # iz0 must be under particle ix1 = ix0 iy1 = iy0 iz1 = iz0 # if a dim. is zero, this is default, else: if nx > 1: ix1 = ix0 + 1 dx_1 = 1. / ff.dx # if a dim is non-zero, ajust ix1 to right cell if ny > 1: iy1 = iy0 + 1 dy_1 = 1. / ff.dy # if a dim is non-zero, ajust iy1 to above cell if nz > 1: iz1 = iz0 + 1 dz_1 = 1. / ff.dz # if a dim is non-zero, ajust iz1 to above cell ux = 0. uy = 0. uz = 0. for ix in [ix0, ix1]: for iy in [iy0, iy1]: for iz in [iz0, iz1]: weight = 1. if nx > 1: weight = weight * ( 1. - abs(px - ff.x[ix]) * dx_1) if ny > 1: weight = weight * ( 1. - abs(py - ff.y[iy]) * dy_1) if nz > 1: weight = weight * ( 1. - abs(pz - ff.z[iz]) * dz_1) ux = ux + weight * ff.ux[iz, iy, ix] uy = uy + weight * ff.uy[iz, iy, ix] uz = uz + weight * ff.uz[iz, iy, ix] if iz0 == iz1: break # beware of degeneracy: if iy0 == iy1: break # beware of degeneracy: if ix0 == ix1: break # beware of degeneracy: l_ux.append(ux) l_uy.append(uy) l_uz.append(uz) ## TSC if scheme == 'tsc' or scheme == 'TSC': for ix0, iy0, iz0, px, py, pz in zip( l_ix, l_iy, l_iz, l_px, l_py, l_pz): # for each particle ixx0 = ix0 ixx1 = ix0 # beware of degeneracy iyy0 = iy0 iyy1 = iy0 izz0 = iz0 izz1 = iz0 if nx > 1: ixx0 = ix0 - 1 ixx1 = ix0 + 1 dx_1 = 1. / ff.dx dx_2 = 1. / ff.dx**2 if ny > 1: iyy0 = iy0 - 1 iyy1 = iy0 + 1 dy_1 = 1. / ff.dy dy_2 = 1. / ff.dy**2 if nz > 1: izz0 = iz0 - 1 izz1 = iz0 + 1 dz_1 = 1. / ff.dz dz_2 = 1. / ff.dz**2 ux = 0. uy = 0. uz = 0. for ix in [ix0, ixx0, ixx1]: weight_x = 0. if ix - ix0 == -1 or ix - ix0 == 1: weight_x = 1.125 - 1.5 * abs( px - ff.x[ix]) * dx_1 + 0.5 * abs( px - ff.x[ix])**2 * dx_2 elif nx != 1: weight_x = 0.75 - (px - ff.x[ix])**2 * dx_2 for iy in [iy0, iyy0, iyy1]: weight_y = 0. if iy - iy0 == -1 or iy - iy0 == 1: weight_y = 1.125 - 1.5 * abs( py - ff.y[iy]) * dy_1 + 0.5 * abs( py - ff.y[iy])**2 * dy_2 elif ny != 1: weight_y = 0.75 - (py - ff.y[iy])**2 * dy_2 for iz in [iz0, izz0, izz1]: weight_z = 0. if iz - iz0 == -1 or iz - iz0 == 1: weight_z = 1.125 - 1.5 * abs( pz - ff.z[iz]) * dz_1 + 0.5 * abs( pz - ff.z[iz])**2 * dz_2 elif nz != 1: weight_z = 0.75 - (pz - ff.z[iz])**2 * dz_2 weight = 1. if nx > 1: weight = weight * weight_x if ny > 1: weight = weight * weight_y if nz > 1: weight = weight * weight_z ux = ux + weight * ff.ux[iz, iy, ix] uy = uy + weight * ff.uy[iz, iy, ix] uz = uz + weight * ff.uz[iz, iy, ix] if izz0 == izz1: break # beware of degeneracy: if iyy0 == iyy1: break # beware of degeneracy: if ixx0 == ixx1: break # beware of degeneracy: l_ux.append(ux) l_uy.append(uy) l_uz.append(uz) ## Convert all information into a single record array data_set = np.core.records.fromarrays( [ l_ipars.astype('int'), l_px, l_py, l_pz, l_vx, l_vy, l_vz, l_rix, l_riy, l_riz, l_ix, l_iy, l_iz, l_ux, l_uy, l_uz ], names= 'ipar, ipx, ipy, ipz, vx, vy, vz, rix, riy, riz, ix, iy, iz, ux, uy, uz', formats= 'int, float, float, float, float, float, float, int, int, int, int, int, int, float, float, float' ) gas_velo_at_particle_pos = np.sort(data_set, order=['ix', 'iy', 'iz']) Nix = int(gas_velo_at_particle_pos['rix'].max() + 1) Niy = int(gas_velo_at_particle_pos['riy'].max() + 1) Niz = int(gas_velo_at_particle_pos['riz'].max() + 1) Npar_arr = np.array([ gas_velo_at_particle_pos['rix'], gas_velo_at_particle_pos['riy'], gas_velo_at_particle_pos['riz'] ]) #rgrid_edges = (grid.x[1:]-(grid.x[1:]-grid.x[:-1])/2)[2:-2] xrange = np.arange( 0, float(gas_velo_at_particle_pos['rix'].max()) + 2) xrange = xrange - 0.5 yrange = np.arange( 0, float(gas_velo_at_particle_pos['riy'].max()) + 2) zrange = np.arange( 0, float(gas_velo_at_particle_pos['riz'].max()) + 2) Npar_hist, edges = np.histogramdd(Npar_arr.T, bins=(xrange, yrange, zrange)) Npar_hist, edges = np.histogramdd(Npar_arr.T, bins=(Nix, Niy, Niz)) gas_velo_at_particle_pos = { 'time': ff.t, 'par_pos': np.array([ gas_velo_at_particle_pos['ipx'], gas_velo_at_particle_pos['ipy'], gas_velo_at_particle_pos['ipz'] ]), 'par_velo': np.array([ gas_velo_at_particle_pos['vx'], gas_velo_at_particle_pos['vy'], gas_velo_at_particle_pos['vz'] ]), 'par_idx': np.array([ gas_velo_at_particle_pos['rix'], gas_velo_at_particle_pos['riy'], gas_velo_at_particle_pos['riz'] ]), 'npar': np.array(Npar_hist[gas_velo_at_particle_pos['rix'], gas_velo_at_particle_pos['riy'], gas_velo_at_particle_pos['riz']]), 'gas_velo': np.array([ gas_velo_at_particle_pos['ux'], gas_velo_at_particle_pos['uy'], gas_velo_at_particle_pos['uz'] ]) } print('## Saving dataset into ' + save_destination + '...') io.pkl_save( { 'gas_velo_at_particle_pos': gas_velo_at_particle_pos, 't': ff.t }, save_filename, folder=save_destination) print('## Done!')