def redund(matrix, verbose=False): if not os.path.isdir(relative_path('tmp')): os.makedirs(relative_path('tmp')) rank = str(get_process_rank()) matrix = to_fractions(matrix) binary = get_redund_binary() matrix_path = relative_path('tmp' + os.sep + 'matrix' + rank + '.ine') matrix_nonredundant_path = relative_path('tmp' + os.sep + 'matrix_nored' + rank + '.ine') if matrix.shape[0] <= 1: return matrix with open(matrix_path, 'w') as file: file.write('V-representation\n') file.write('begin\n') file.write('%d %d rational\n' % (matrix.shape[0], matrix.shape[1] + 1)) for row in range(matrix.shape[0]): file.write(' 0') for col in range(matrix.shape[1]): file.write(' %s' % str(matrix[row, col])) file.write('\n') file.write('end\n') system('%s %s > %s' % (binary, matrix_path, matrix_nonredundant_path)) if not os.path.exists(matrix_nonredundant_path): raise ValueError( 'An error occurred during removal of redundant vectors from an input matrix: ' 'redund did not write an output file after being presented input file "%s". \r\n\r\n' 'Please check if your input matrix contains erroneous data, and let us know via https://github.com/SystemsBioinformatics/ecmtool/issues ' 'if you think the input matrix seems fine. It helps if you attach the matrix file mentioned above when creating an issue.' ) matrix_nored = np.ndarray(shape=(0, matrix.shape[1] + 1), dtype='object') with open(matrix_nonredundant_path) as file: lines = file.readlines() for line in [line for line in lines if line not in ['\n', '']]: # Skip comment and INE format lines if np.any([ target in line for target in ['*', 'V-representation', 'begin', 'end', 'rational'] ]): continue row = [ Fraction(x) for x in line.replace('\n', '').split(' ') if x != '' ] matrix_nored = np.append(matrix_nored, [row], axis=0) remove(matrix_path) remove(matrix_nonredundant_path) if verbose: print('Removed %d redundant rows' % (matrix.shape[0] - matrix_nored.shape[0])) return matrix_nored[:, 1:]
def mp_print(*args, **kwargs): """ Multiprocessing wrapper for print(). Prints the given arguments, but only on process 0 unless named argument PRINT_IF_RANK_NONZERO is set to true. :return: """ if get_process_rank() == 0: print(*args) elif 'PRINT_IF_RANK_NONZERO' in kwargs and kwargs['PRINT_IF_RANK_NONZERO']: print(*args)
def redund(matrix, verbose=False): if not os.path.isdir(relative_path('tmp')): os.makedirs(relative_path('tmp')) rank = str(get_process_rank()) matrix = to_fractions(matrix) binary = get_redund_binary() matrix_path = relative_path('tmp' + os.sep + 'matrix' + rank + '.ine') matrix_nonredundant_path = relative_path('tmp' + os.sep + 'matrix_nored' + rank + '.ine') if matrix.shape[0] <= 1: return matrix with open(matrix_path, 'w') as file: file.write('V-representation\n') file.write('begin\n') file.write('%d %d rational\n' % (matrix.shape[0], matrix.shape[1] + 1)) for row in range(matrix.shape[0]): file.write(' 0') for col in range(matrix.shape[1]): file.write(' %s' % str(matrix[row, col])) file.write('\n') file.write('end\n') system('%s %s > %s' % (binary, matrix_path, matrix_nonredundant_path)) matrix_nored = np.ndarray(shape=(0, matrix.shape[1] + 1), dtype='object') with open(matrix_nonredundant_path) as file: lines = file.readlines() for line in [line for line in lines if line not in ['\n', '']]: # Skip comment and INE format lines if np.any([ target in line for target in ['*', 'V-representation', 'begin', 'end', 'rational'] ]): continue row = [ Fraction(x) for x in line.replace('\n', '').split(' ') if x != '' ] matrix_nored = np.append(matrix_nored, [row], axis=0) remove(matrix_path) remove(matrix_nonredundant_path) if verbose: print('Removed %d redundant rows' % (matrix.shape[0] - matrix_nored.shape[0])) return matrix_nored[:, 1:]
def drop_redundant_rays(ray_matrix, verbose=True, use_pre_filter=False, rays_are_unique=True, linearities=False, normalised=True): """ :param ray_matrix: :param verbose: :param use_pre_filter: Sometimes, use_pre_filter=True can speed up the calculations, but mostly it doesn't :param rays_are_unique: Boolean that states whether rays given as input are already unique :param linearities: Boolean indicating if linearities are still present :param normalised: Boolean indicating if ray_matrix columns are already normalised :return: """ extreme_inds = [] non_extreme_inds = [] if not rays_are_unique: # First make sure that no duplicate rays are in the matrix ray_matrix = np.transpose( unique(np.transpose(normalize_columns_fraction(ray_matrix)))) # Find 'cycles': combinations of columns of matrix_indep_rows that add up to zero, and remove them if linearities: if verbose: mp_print('Detecting linearities in H_ineq.') ray_matrix, cycle_rays = remove_cycles_redund(ray_matrix) else: cycle_rays = np.zeros((ray_matrix.shape[0], 0)) if not normalised: if verbose: mp_print('Normalizing columns.') matrix_normalized = normalize_columns(ray_matrix) else: matrix_normalized = np.array(ray_matrix, dtype='float') if verbose: mp_print('Selecting independent rows.') matrix_indep_rows = independent_rows_qr(matrix_normalized) if use_pre_filter: filtered_inds = pre_redund(matrix_indep_rows) else: filtered_inds = np.arange(matrix_indep_rows.shape[1]) mpi_size = mpi_wrapper.get_process_size() mpi_rank = mpi_wrapper.get_process_rank() matrix_indep_rows = matrix_indep_rows[:, filtered_inds] # then find any column basis of R_indep start_basis = get_basis_columns_qr(matrix_indep_rows) start_basis_inv = np.linalg.inv(matrix_indep_rows[:, start_basis]) number_rays = matrix_indep_rows.shape[1] for i in range(number_rays): if i % mpi_size == mpi_rank: if i % (10 * mpi_size) == mpi_rank: mp_print( "Process %d is on redundancy test %d of %d (%f %%). Found %d redundant rays." % (mpi_rank, i, number_rays, i / number_rays * 100, len(non_extreme_inds)), PRINT_IF_RANK_NONZERO=True) basis = add_first_ray(matrix_indep_rows, start_basis_inv, start_basis, i) extreme = check_extreme(matrix_indep_rows, i, basis) if extreme: extreme_inds.append(filtered_inds[i]) else: non_extreme_inds.append(filtered_inds[i]) # MPI communication step extreme_sets = mpi_wrapper.world_allgather(extreme_inds) for i in range(mpi_size): if i != mpi_rank: extreme_inds.extend(extreme_sets[i]) extreme_inds.sort() return extreme_inds, cycle_rays