def __init__(self, tables, selectors, groups_lim, erad_weight=None): """ Compute AMR projection for some opacity tables Parameters: ----------- tables: dict a dictionaray that has for keys the names of the table and that has for values OpgHdf5 objetcs selectors: list containing SelectPoints, SelectRect objects groups_lim: typle (min, max) first and last group boundaries in eV erad_weight: tuple or (groups, weights) or None groups and weights are 1D arrays with len(groups) = len(weights)+1 """ from ..lib.multigroup import cellcentered_interpolate self.method = None self.func = None self.method_list = {'df1': self._method_df1, 'df2': self._method_df2, 'sg': self._method_sg} groups_dict = {key: op['groups'][:] for key, op in tables.iteritems()} groups_list = groups_dict.values() self.groups = groups_ref = groups_list[0] if len(groups_list)>1: for gidx, group in enumerate(groups_list[1:]): if not np.allclose(groups_ref, group, rtol=5e-4): print(groups_ref) print(group) raise ValueError("Opactity tables {0} and {1} don't have the same photon grid!".format(tables.keys()[0], tables.keys()[gidx+1])) if len(groups_lim)!=2: raise ValueError groups_lim_idx, val = project_on_grid(np.array(groups_lim), groups_ref) self.groups_slice = slice(groups_lim_idx[0], groups_lim_idx[1]) self.Ng_ini = len(groups_ref) - 1 self.Ng = groups_lim_idx[1] - groups_lim_idx[0] self.t_op = tables self.selectors = selectors self.t_selectors = t_selectors = {key: [] for key in tables} self.t_mask = t_mask = {} self.t_weight = t_weight = {} self.t_cost = {key: np.zeros((op.Nr, op.Nt), dtype='object') for key, op in tables.iteritems()} self.t_cost_wsum = {key: np.zeros(self.Ng) for key, op in tables.iteritems()} self.cost_fn = np.zeros(self.Ng) if erad_weight is None: self.erad_weight= np.ones(self.Ng) self.erad_eps = 0.0 else: erad_weight_in = np.zeros(self.Ng_ini) cellcentered_interpolate(erad_weight['groups'], erad_weight['weight'], groups_ref, erad_weight_in) self.erad_weight = (erad_weight_in[self.groups_slice]/erad_weight_in.max()) self.erad_eps = erad_weight['alpha'] # setting appropriate selectors for every table for key, op in tables.iteritems(): for sel in selectors: if re.match(sel.regexp, key): t_selectors[key].append(sel) for key in tables: if not len(t_selectors[key]): raise ValueError('No selectors were applied to the table {0}! \n\ Please change the selectors argument of TableProjGrid.'.format(key)) # getting a mask for every point that should be taken for key, op in tables.iteritems(): Nr, Nt = len(op['dens']), len(op['temp']) t_mask[key] = np.zeros((Nr,Nt), dtype='bool') t_weight[key] = np.zeros((Nr, Nt)) for sel in t_selectors[key]: ridx, tidx, weights = sel(op['dens'], op['temp']) t_mask[key][ridx, tidx] = True t_weight[key][ridx, tidx] += weights
def merge_tables(target, tables, columns=None): """ Merge a number of tables onto a target table. Tables must have registered merge rules via the `broadcast` function. Parameters ---------- target : str, DataFrameWrapper, or TableFuncWrapper Name of the table (or wrapped table) onto which tables will be merged. tables : list of `DataFrameWrapper`, `TableFuncWrapper`, or str All of the tables to merge. Should include the target table. columns : list of str, optional If given, columns will be mapped to `tables` and only those columns will be requested from each table. The final merged table will have only these columns. By default all columns are used from every table. Returns ------- merged : pandas.DataFrame """ # allow target to be string or table wrapper if isinstance(target, (DataFrameWrapper, TableFuncWrapper)): target = target.name # allow tables to be strings or table wrappers tables = [ get_table(t) if not isinstance(t, (DataFrameWrapper, TableFuncWrapper)) else t for t in tables ] merges = {t.name: {} for t in tables} tables = {t.name: t for t in tables} casts = _get_broadcasts(tables.keys()) logger.debug('attempting to merge tables {} to target table {}'.format( tables.keys(), target)) # relate all the tables by registered broadcasts for table, onto in casts: merges[onto][table] = merges[table] merges = {target: merges[target]} # verify that all the tables can be merged to the target all_tables = set(_all_reachable_tables(merges)) if all_tables != set(tables.keys()): raise RuntimeError( ('Not all tables can be merged to target "{}". Unlinked tables: {}' ).format(target, list(set(tables.keys()) - all_tables))) # add any columns necessary for indexing into other tables # during merges if columns: columns = list(columns) for c in casts.values(): if c.onto_on: columns.append(c.onto_on) if c.cast_on: columns.append(c.cast_on) # get column map for which columns go with which table colmap = column_map(tables.values(), columns) # get frames frames = { name: t.to_frame(columns=colmap[name]) for name, t in tables.items() } # perform merges until there's only one table left while merges[target]: nm = _next_merge(merges) onto = toolz.first(nm) onto_table = frames[onto] # loop over all the tables that can be broadcast onto # the onto_table and merge them all in. for cast in nm[onto]: cast_table = frames[cast] bc = casts[(cast, onto)] with log_start_finish('merge tables {} and {}'.format(onto, cast), logger): onto_table = pd.merge(onto_table, cast_table, left_on=bc.onto_on, right_on=bc.cast_on, left_index=bc.onto_index, right_index=bc.cast_index) # replace the existing table with the merged one frames[onto] = onto_table # free up space by dropping the cast table del frames[cast] # mark the onto table as having no more things to broadcast # onto it. _recursive_getitem(merges, onto)[onto] = {} logger.debug('finished merge') return frames[target]
def merge_tables(target, tables, columns=None): """ Merge a number of tables onto a target table. Tables must have registered merge rules via the `broadcast` function. Parameters ---------- target : str, DataFrameWrapper, or TableFuncWrapper Name of the table (or wrapped table) onto which tables will be merged. tables : list of `DataFrameWrapper`, `TableFuncWrapper`, or str All of the tables to merge. Should include the target table. columns : list of str, optional If given, columns will be mapped to `tables` and only those columns will be requested from each table. The final merged table will have only these columns. By default all columns are used from every table. Returns ------- merged : pandas.DataFrame """ # allow target to be string or table wrapper if isinstance(target, (DataFrameWrapper, TableFuncWrapper)): target = target.name # allow tables to be strings or table wrappers tables = [get_table(t) if not isinstance(t, (DataFrameWrapper, TableFuncWrapper)) else t for t in tables] merges = {t.name: {} for t in tables} tables = {t.name: t for t in tables} casts = _get_broadcasts(tables.keys()) logger.debug( 'attempting to merge tables {} to target table {}'.format( tables.keys(), target)) # relate all the tables by registered broadcasts for table, onto in casts: merges[onto][table] = merges[table] merges = {target: merges[target]} # verify that all the tables can be merged to the target all_tables = set(_all_reachable_tables(merges)) if all_tables != set(tables.keys()): raise RuntimeError( ('Not all tables can be merged to target "{}". Unlinked tables: {}' ).format(target, list(set(tables.keys()) - all_tables))) # add any columns necessary for indexing into other tables # during merges if columns: columns = list(columns) for c in casts.values(): if c.onto_on: columns.append(c.onto_on) if c.cast_on: columns.append(c.cast_on) # get column map for which columns go with which table colmap = column_map(tables.values(), columns) # get frames frames = {name: t.to_frame(columns=colmap[name]) for name, t in tables.items()} # perform merges until there's only one table left while merges[target]: nm = _next_merge(merges) onto = toolz.first(nm) onto_table = frames[onto] # loop over all the tables that can be broadcast onto # the onto_table and merge them all in. for cast in nm[onto]: cast_table = frames[cast] bc = casts[(cast, onto)] with log_start_finish( 'merge tables {} and {}'.format(onto, cast), logger): onto_table = pd.merge( onto_table, cast_table, left_on=bc.onto_on, right_on=bc.cast_on, left_index=bc.onto_index, right_index=bc.cast_index) # replace the existing table with the merged one frames[onto] = onto_table # free up space by dropping the cast table del frames[cast] # mark the onto table as having no more things to broadcast # onto it. _recursive_getitem(merges, onto)[onto] = {} logger.debug('finished merge') return frames[target]
def __init__(self, tables, selectors, groups_lim, erad_weight=None): """ Compute AMR projection for some opacity tables Parameters: ----------- tables: dict a dictionaray that has for keys the names of the table and that has for values OpgHdf5 objetcs selectors: list containing SelectPoints, SelectRect objects groups_lim: typle (min, max) first and last group boundaries in eV erad_weight: tuple or (groups, weights) or None groups and weights are 1D arrays with len(groups) = len(weights)+1 """ from ..lib.multigroup import cellcentered_interpolate self.method = None self.func = None self.method_list = { 'df1': self._method_df1, 'df2': self._method_df2, 'sg': self._method_sg } groups_dict = {key: op['groups'][:] for key, op in tables.iteritems()} groups_list = groups_dict.values() self.groups = groups_ref = groups_list[0] if len(groups_list) > 1: for gidx, group in enumerate(groups_list[1:]): if not np.allclose(groups_ref, group, rtol=5e-4): print(groups_ref) print(group) raise ValueError( "Opactity tables {0} and {1} don't have the same photon grid!" .format(tables.keys()[0], tables.keys()[gidx + 1])) if len(groups_lim) != 2: raise ValueError groups_lim_idx, val = project_on_grid(np.array(groups_lim), groups_ref) self.groups_slice = slice(groups_lim_idx[0], groups_lim_idx[1]) self.Ng_ini = len(groups_ref) - 1 self.Ng = groups_lim_idx[1] - groups_lim_idx[0] self.t_op = tables self.selectors = selectors self.t_selectors = t_selectors = {key: [] for key in tables} self.t_mask = t_mask = {} self.t_weight = t_weight = {} self.t_cost = { key: np.zeros((op.Nr, op.Nt), dtype='object') for key, op in tables.iteritems() } self.t_cost_wsum = { key: np.zeros(self.Ng) for key, op in tables.iteritems() } self.cost_fn = np.zeros(self.Ng) if erad_weight is None: self.erad_weight = np.ones(self.Ng) self.erad_eps = 0.0 else: erad_weight_in = np.zeros(self.Ng_ini) cellcentered_interpolate(erad_weight['groups'], erad_weight['weight'], groups_ref, erad_weight_in) self.erad_weight = (erad_weight_in[self.groups_slice] / erad_weight_in.max()) self.erad_eps = erad_weight['alpha'] # setting appropriate selectors for every table for key, op in tables.iteritems(): for sel in selectors: if re.match(sel.regexp, key): t_selectors[key].append(sel) for key in tables: if not len(t_selectors[key]): raise ValueError( 'No selectors were applied to the table {0}! \n\ Please change the selectors argument of TableProjGrid.'.format( key)) # getting a mask for every point that should be taken for key, op in tables.iteritems(): Nr, Nt = len(op['dens']), len(op['temp']) t_mask[key] = np.zeros((Nr, Nt), dtype='bool') t_weight[key] = np.zeros((Nr, Nt)) for sel in t_selectors[key]: ridx, tidx, weights = sel(op['dens'], op['temp']) t_mask[key][ridx, tidx] = True t_weight[key][ridx, tidx] += weights