def _expand_corrections(ifgs, dm, params, ncoef, offsets): """ Convenience func returns model converted to data points. dm: design matrix (do not filter/remove nan cells) params: model parameters array from pinv() * dm ncoef: number of model coefficients (2 planar, 5 quadratic) offsets: True/False to calculate correction with offsets """ # NB: cannot work on singular ifgs due to date ID id/indexing requirement date_ids = get_date_ids(ifgs) corrections = [] for ifg in ifgs: jbm = date_ids[ifg.master] * ncoef # starting row index for master jbs = date_ids[ifg.slave] * ncoef # row start for slave par = params[jbs:jbs + ncoef] - params[jbm:jbm + ncoef] # estimate orbital correction effects # corresponds to "fullorb = B*parm + offset" in orbfwd.m cor = dm.dot(par).reshape(ifg.phase_data.shape) if offsets: off = np.ravel(ifg.phase_data - cor) # bring all ifgs to same base level cor -= nanmedian(off) corrections.append(cor) return corrections
def _est_ref_phs_method1(phase_data, comp): """ Convenience function for ref phs estimate method 1 parallelisation """ ifgv = np.ravel(phase_data, order='F') ifgv[comp == 1] = np.nan return nanmedian(ifgv)
def alt_orbital_correction(self, ifg, deg, offset): data = ifg.phase_data.reshape(ifg.num_cells) dm = get_design_matrix(ifg, deg, offset)[~isnan(data)] fd = data[~isnan(data)].reshape((dm.shape[0], 1)) dmt = dm.T invNbb = inv(dmt.dot(dm)) orbparams = invNbb.dot(dmt.dot(fd)) alt_params = lstsq(dm, fd)[0] # FIXME: precision assert_array_almost_equal(orbparams, alt_params, decimal=2) dm2 = get_design_matrix(ifg, deg, offset) if offset: fullorb = np.reshape(np.dot(dm2[:, :-1], orbparams[:-1]), ifg.phase_data.shape) else: fullorb = np.reshape(np.dot(dm2, orbparams), ifg.phase_data.shape) offset_removal = nanmedian( np.reshape(ifg.phase_data - fullorb, (1, -1))) fwd_correction = fullorb - offset_removal # ifg.phase_data -= (fullorb - offset_removal) return ifg.phase_data - fwd_correction
def independent_orbital_correction(ifg, params): """ Calculates and removes an orbital error surface from a single independent interferogram. Warning: This will write orbital error corrected phase_data to the ifg. :param Ifg class instance ifg: the interferogram to be corrected :param str degree: model to fit (PLANAR / QUADRATIC / PART_CUBIC) :param bool offset: True to calculate the model using an offset :param dict params: dictionary of configuration parameters :return: None - interferogram phase data is updated and saved to disk """ degree = params[cf.ORBITAL_FIT_DEGREE] offset = params[cf.ORBFIT_OFFSET] orbfit_correction_on_disc = MultiplePaths.orb_error_path( ifg.data_path, params) if not ifg.is_open: ifg.open() shared.nan_and_mm_convert(ifg, params) if orbfit_correction_on_disc.exists(): log.info( f'Reusing already computed orbital fit correction for {ifg.data_path}' ) orbital_correction = np.load(file=orbfit_correction_on_disc) else: # vectorise, keeping NODATA vphase = reshape(ifg.phase_data, ifg.num_cells) dm = get_design_matrix(ifg, degree, offset) # filter NaNs out before getting model clean_dm = dm[~isnan(vphase)] data = vphase[~isnan(vphase)] model = lstsq(clean_dm, data)[0] # first arg is the model params # calculate forward model & morph back to 2D if offset: fullorb = np.reshape(np.dot(dm[:, :-1], model[:-1]), ifg.phase_data.shape) else: fullorb = np.reshape(np.dot(dm, model), ifg.phase_data.shape) if not orbfit_correction_on_disc.parent.exists(): shared.mkdir_p(orbfit_correction_on_disc.parent) offset_removal = nanmedian(np.ravel(ifg.phase_data - fullorb)) orbital_correction = fullorb - offset_removal # dump to disc np.save(file=orbfit_correction_on_disc, arr=orbital_correction) # subtract orbital error from the ifg ifg.phase_data -= orbital_correction # set orbfit meta tag and save phase to file _save_orbital_error_corrected_phase(ifg) ifg.close()
def _remove_network_orb_error(coefs, dm, ifg, ids, offset): """ remove network orbital error from input interferograms """ orb = dm.dot(coefs[ids[ifg.slave]] - coefs[ids[ifg.master]]) orb = orb.reshape(ifg.shape) # offset estimation if offset: # bring all ifgs to same base level orb -= nanmedian(np.ravel(ifg.phase_data - orb)) # subtract orbital error from the ifg ifg.phase_data -= orb # set orbfit meta tag and save phase to file _save_orbital_error_corrected_phase(ifg)
def _est_ref_phs_method2(phase_data, half_chip_size, refpx, refpy, thresh): """ Convenience function for ref phs estimate method 2 parallelisation """ patch = phase_data[refpy - half_chip_size:refpy + half_chip_size + 1, refpx - half_chip_size:refpx + half_chip_size + 1] patch = np.reshape(patch, newshape=(-1, 1), order='F') nanfrac = np.sum(~np.isnan(patch)) if nanfrac < thresh: raise ReferencePhaseError('The data window at the reference pixel ' 'does not have enough valid observations. ' 'Actual = {}, Threshold = {}.'.format( nanfrac, thresh)) ref_ph = nanmedian(patch) return ref_ph
def _remove_network_orb_error(coefs, dm, ifg, ids, offset, params): """ remove network orbital error from input interferograms """ saved_orb_err_path = MultiplePaths.orb_error_path(ifg.data_path, params) orb = dm.dot(coefs[ids[ifg.second]] - coefs[ids[ifg.first]]) orb = orb.reshape(ifg.shape) # offset estimation if offset: # bring all ifgs to same base level orb -= nanmedian(np.ravel(ifg.phase_data - orb)) # subtract orbital error from the ifg ifg.phase_data -= orb # save orb error on disc np.save(file=saved_orb_err_path, arr=orb) # set orbfit meta tag and save phase to file _save_orbital_error_corrected_phase(ifg)
def _remove_network_orb_error(coefs, dm, ifg, ids, offset, params): """ remove network orbital error from input interferograms """ saved_orb_err_path = MultiplePaths.orb_error_path(ifg.data_path, params) orb = dm.dot(coefs[ids[ifg.second]] - coefs[ids[ifg.first]]) orb = orb.reshape(ifg.shape) # Estimate the offset of the interferogram as the median of ifg minus model # Only needed if reference phase correction has already been applied? if offset: # brings all ifgs to same reference level orb -= nanmedian(np.ravel(ifg.phase_data - orb)) # subtract orbital error from the ifg ifg.phase_data -= orb # save orb error on disc np.save(file=saved_orb_err_path, arr=orb) # set orbfit meta tag and save phase to file _save_orbital_error_corrected_phase(ifg, params)
def independent_orbital_correction(ifg, degree, offset, params): """ Calculates and removes an orbital error surface from a single independent interferogram. Warning: This will write orbital error corrected phase_data to the ifg. :param Ifg class instance ifg: the interferogram to be corrected :param str degree: model to fit (PLANAR / QUADRATIC / PART_CUBIC) :param bool offset: True to calculate the model using an offset :param dict params: dictionary of configuration parameters :return: None - interferogram phase data is updated and saved to disk """ ifg = shared.Ifg(ifg) if isinstance(ifg, str) else ifg if not ifg.is_open: ifg.open() shared.nan_and_mm_convert(ifg, params) # vectorise, keeping NODATA vphase = reshape(ifg.phase_data, ifg.num_cells) dm = get_design_matrix(ifg, degree, offset) # filter NaNs out before getting model clean_dm = dm[~isnan(vphase)] data = vphase[~isnan(vphase)] model = lstsq(clean_dm, data)[0] # first arg is the model params # calculate forward model & morph back to 2D if offset: fullorb = np.reshape(np.dot(dm[:, :-1], model[:-1]), ifg.phase_data.shape) else: fullorb = np.reshape(np.dot(dm, model), ifg.phase_data.shape) offset_removal = nanmedian(np.ravel(ifg.phase_data - fullorb)) # subtract orbital error from the ifg ifg.phase_data -= (fullorb - offset_removal) # set orbfit meta tag and save phase to file _save_orbital_error_corrected_phase(ifg) if ifg.open(): ifg.close()
def __orb_correction(fullres_dm, mlooked_dm, fullres_phase, mlooked_phase, offset=False): """ Function to perform the inversion to obtain orbital model parameters and return the orbital correction as the full resolution forward model. """ # perform inversion using pseudoinverse of DM orbparams = __orb_inversion(mlooked_dm, mlooked_phase) # compute forward model at full resolution fullorb = reshape(dot(fullres_dm, orbparams), fullres_phase.shape) # Estimate the offset of the interferogram as the median of ifg minus model # Only needed if reference phase correction has already been applied? if offset: offset_removal = nanmedian(np.ravel(fullres_phase - fullorb)) else: offset_removal = 0 orbital_correction = fullorb - offset_removal return orbital_correction