def compute(self, ctx, imts, mean, sig, tau, phi): """ Returns the mean and standard deviations calling the input GMPE for the mean acceleration for PGA and Sa (1.0) on the reference rock, defining the amplification factors and code spectrum to return the mean ground motion at the desired period, before the calling the input GMPE once more in order to return the standard deviations for the required IMT. """ # Get PGA and Sa (1.0) from GMPE ctx_r = copy.copy(ctx) ctx_r.vs30 = np.full_like(ctx_r.vs30, self.rock_vs30) rock = contexts.get_mean_stds(self.gmpe, ctx_r, [PGA(), SA(1.0)]) pga_r = rock[0, 0] s_1_rp = rock[0, 1] s_s_rp = CONSTANTS["F0"] * np.exp(pga_r) s_1_rp = np.exp(s_1_rp) # Get the short and long period amplification factors if self.kind == 'euro8': ec8 = get_ec8_class(ctx.vs30, ctx.h800) else: ec8 = None f_s, f_l = get_amplification_factor(self.kind, self.F1, self.FS, s_s_rp, s_1_rp, ctx, ec8) s_1 = f_l * s_1_rp s_s = f_s * s_s_rp # NB: this is wasteful since means are computed and then discarded out = contexts.get_mean_stds(self.gmpe, ctx_r, imts) for m, imt in enumerate(imts): # Get the mean ground motion using the design code spectrum mean[m] = get_amplified_mean(s_s, s_1, s_1_rp, imt) sig[m] = out[1, m] tau[m] = out[2, m] phi[m] = out[3, m]
def test_get_mean_and_stddevs_good(self): """ Tests the full execution of the GMPE tables for valid data """ gsim = GMPETable(gmpe_table=self.TABLE_FILE) ctx = RuptureContext() ctx.mag = 6.0 # Test values at the given distances and those outside range ctx.rjb = np.array([0.5, 1.0, 10.0, 100.0, 500.0]) ctx.vs30 = 1000. * np.ones(5) ctx.sids = np.arange(5) stddevs = [const.StdDev.TOTAL] expected_mean = np.array([2.0, 2.0, 1.0, 0.5, 1.0E-20]) expected_sigma = 0.25 * np.ones(5) imts = [imt_module.PGA(), imt_module.SA(1.0), imt_module.PGV()] # PGA mean, sigma = gsim.get_mean_and_stddevs(ctx, ctx, ctx, imts[0], stddevs) np.testing.assert_array_almost_equal(np.exp(mean), expected_mean, 5) np.testing.assert_array_almost_equal(sigma[0], expected_sigma, 5) # SA mean, sigma = gsim.get_mean_and_stddevs(ctx, ctx, ctx, imts[1], stddevs) np.testing.assert_array_almost_equal(np.exp(mean), expected_mean, 5) np.testing.assert_array_almost_equal(sigma[0], 0.4 * np.ones(5), 5) # PGV mean, sigma = gsim.get_mean_and_stddevs(ctx, ctx, ctx, imts[2], stddevs) np.testing.assert_array_almost_equal(np.exp(mean), 10. * expected_mean, 5) np.testing.assert_array_almost_equal(sigma[0], expected_sigma, 5) # StdDev.ALL check contexts.get_mean_stds([gsim], ctx, imts)
def oq_mean_stddevs( model: gsim.base.GMPE, ctx: contexts.RuptureContext, im: imt.IMT, stddev_types: Sequence[const.StdDev], ): """Calculate mean and standard deviations given openquake input structures. model: gsim.base.GMPE OQ models we use are subclass of gsim.base.GMPE ctx: contexts.RuptureContext OQ RuptureContext that contains the following information - Site - Distance - Rupture im: imt.IMT stddev_types: Sequence[const.StdDev] """ # contexts.get_mean_stds returns ndarray, size of 4 # mean, std_total, std_inter and std_intra # std_devs order may vary results = contexts.get_mean_stds(model, ctx, [im]) mean_stddev_dict = {f"{convert_im_label(im)}_mean": results[0][0]} for idx, std_dev in enumerate(stddev_types): # std_devs are index between 1 and 3 from results mean_stddev_dict[ f"{convert_im_label(im)}_std_{std_dev.split()[0]}"] = results[idx + 1][0] return pd.DataFrame(mean_stddev_dict)
def compute(self, ctx, imts, mean, sig, tau, phi): """ Call the get mean and stddevs of the GMPE for the respective IMT """ gsims = [self.kwargs[imt.string] for imt in imts] mean[:], sig[:], tau[:], phi[:] = contexts.get_mean_stds( gsims, ctx, imts)
def compute(self, ctx, imts, mean, sig, tau, phi): for m, imt in enumerate(imts): cornerp = get_corner_period(ctx.mag) # capping period only compares # - highest period with a coefficient # - corner period # - 2.0 if it's bindi sp = get_capping_period(cornerp, self.gmpe, imt) hp = sp[-1] # 1 - if imt.period < cornerp, no changes needed if self.extr and imt.period <= cornerp and imt.period <= hp: [mean_] = contexts.get_mean_stds([self.gmpe], ctx, [imt], None) # if the period is larger than the corner period but the corner # period is less than the highest period elif self.extr and imt.period >= cornerp and cornerp <= hp: [mean_] = contexts.get_mean_stds( [self.gmpe], ctx, [SA(cornerp)], None) disp = get_disp_from_acc(mean_, cornerp) mean_ = get_acc_from_disp(disp, imt.period) # if the corner period is longer than highest and imt is above # highets but below corner elif self.extr and cornerp > hp and hp <= imt.period < cornerp: mean_ = extrapolate_in_PSA(self.gmpe, ctx, hp, sp, imt.period) elif self.extr and cornerp > hp and imt.period > cornerp: mean_ = extrapolate_in_PSA(self.gmpe, ctx, hp, sp, cornerp) disp = get_disp_from_acc(mean, cornerp) mean_ = get_acc_from_disp(disp, imt.period) else: [mean_] = contexts.get_mean_stds([self.gmpe], ctx, [imt], None) kappa = 1 if self.kappa_file: if imt.period == 0: kappa = self.KAPPATAB[SA(0.01)][self.kappa_val] elif imt.period > 2.0: kappa = self.KAPPATAB[SA(2.0)][self.kappa_val] else: kappa = self.KAPPATAB[imt][self.kappa_val] mean[m] = mean_ + np.log(kappa) sig[m], tau[m], sig[m] = get_stddevs( self.ergodic, self.PHI_SS, self.PHI_S2SS, self.phi_ss_quantile, self.phi_model, self.tau_model, self.TAU, ctx.mag, imt)
def compute(self, ctx, imts, mean, sig, tau, phi): """ Call the underlying GMPEs and return the weighted mean and stddev """ mean_, sig_, tau_, phi_ = contexts.get_mean_stds(self.gsims, ctx, imts) mean[:] = np.average(mean_, 0, self.weights) sig[:] = np.sqrt(np.average(sig_**2, 0, self.weights)) tau[:] = np.sqrt(np.average(tau_**2, 0, self.weights)) phi[:] = np.sqrt(np.average(phi_**2, 0, self.weights))
def compute(self, ctx, imts, mean, sig, tau, phi): """ Call the get mean and stddevs of the GMPE for the respective IMT """ gsims = [self.kwargs[imt.string] for imt in imts] outs = contexts.get_mean_stds(gsims, ctx, imts, const.StdDev.ALL) for m, out in enumerate(outs): mean[m] = out[0] sig[m] = out[1] tau[m] = out[2] phi[m] = out[3]
def compute(self, ctx, imts, mean, sig, tau, phi): """ See :meth:`superclass method <.base.GroundShakingIntensityModel.compute>` for spec of input and result values. """ # compute mean and standard deviation out = contexts.get_mean_stds(self.gmpe, ctx, imts) for m, imt in enumerate(imts): mean[m] = out[0, m] sig[m], tau[m], phi[m] = _get_stddvs(self.between_absolute, self.within_absolute, out[1, m])
def compute(self, ctx, imts, mean, sig, tau, phi): """ See documentation for method `GroundShakingIntensityModel` in :class:~`openquake.hazardlib.gsim.base.GSIM` """ mean_stds = [] # 5 arrays of shape (2, M, N) for gsim in self.gsims: # add equivalent distances if isinstance(gsim, AtkinsonBoore2006Modified2011): c = utils.add_distances_east(ctx, ab06=True) else: c = utils.add_distances_east(ctx) mean_stds.extend( contexts.get_mean_stds([gsim], c, imts, StdDev.TOTAL)) for m, imt in enumerate(imts): cff = self.COEFFS_SITE[imt] # Pezeshk et al. 2011 - Rrup mean1, stds1 = mean_stds[0][:, m] mean1 = apply_correction_to_BC(cff, mean1, imt, ctx.repi) # Atkinson 2008 - Rjb mean2, stds2 = mean_stds[1][:, m] # Silva single corner mean4, stds4 = mean_stds[2][:, m] mean4 = apply_correction_to_BC(cff, mean4, imt, ctx.repi) # Silva double corner mean5, stds5 = mean_stds[3][:, m] mean5 = apply_correction_to_BC(cff, mean5, imt, ctx.repi) # Atkinson and Boore 2006 - Rrup mean3, stds3 = mean_stds[4][:, m] # Computing adjusted mean and stds mean[ m] = mean1 * 0.2 + mean2 * 0.2 + mean3 * 0.2 + mean4 * 0.2 + mean5 * 0.2 # Note that in this case we do not apply a triangular smoothing on # distance as explained at page 996 of Atkinson and Adams (2013) # for the calculation of the standard deviation stds = np.log( np.exp(stds1) * 0.2 + np.exp(stds2) * 0.2 + np.exp(stds3) * 0.2 + np.exp(stds4) * 0.2 + np.exp(stds5) * 0.2) sig[m] = get_sigma(imt) if self.sgn: mean[m] += self.sgn * (stds + _get_delta(stds, ctx.repi))
def compute(self, ctx, imts, mean, sig, tau, phi): """ See :meth:`superclass method <.base.GroundShakingIntensityModel.compute>` for spec of input and result values. """ ctx_rock = copy.copy(ctx) ctx_rock.vs30 = np.full_like(ctx_rock.vs30, 1100.) mea = contexts.get_mean_stds(self.gmpe, ctx_rock, [PGA()])[0] pga1100 = np.exp(mea[0]) # from shape (M, N) -> N for m, imt in enumerate(imts): C = self.COEFFS[imt] mean[m] = (_compute_base_term(C, ctx) + _compute_faulting_style_term(C, ctx) + _compute_site_response_term(C, imt, ctx, pga1100)) sig[m], tau[m], phi[m] = _get_stddevs(C, ctx)
def compute(self, ctx, imts, mean, sig, tau, phi): """ :param imts: must be a single IMT of kind AvgSA """ sas = [SA(period) for period in self.avg_periods] out = contexts.get_mean_stds(self.gmpe, ctx, sas) stddvs_avgsa = 0. for i1 in range(self.tnum): mean[:] += out[0, i1] for i2 in range(self.tnum): rho = self.corr_func(i1, i2) stddvs_avgsa += rho * out[1, i1] * out[1, i2] mean[:] /= self.tnum sig[:] = np.sqrt(stddvs_avgsa) / self.tnum
def compute(self, ctx, imts, mean, sig, tau, phi): """ Call the underlying GMPEs and return the weighted mean and stddev """ outs = contexts.get_mean_stds(self.gsims, ctx, imts, const.StdDev.ALL) # shape (G, O, M, N) G = len(outs) M, N = outs[0].shape[1:] data = np.zeros((G, 4, M, N)) for i, out in enumerate(outs): data[i, 0] = out[0] for s in range(len(out) - 1): data[i, 1 + s] = out[1 + s]**2 mean[:] = np.average(data[:, 0], 0, self.weights) sig[:] = np.sqrt(np.average(data[:, 1], 0, self.weights)) tau[:] = np.sqrt(np.average(data[:, 2], 0, self.weights)) phi[:] = np.sqrt(np.average(data[:, 3], 0, self.weights))
def extrapolate_in_PSA(gmpe, ctx, imt_high, set_imt, imt): extrap_mean = [] t_log10 = np.log10([im for im in set_imt]) for d in np.arange(0, len(ctx.rjb)): c = copy.copy(ctx) if hasattr(ctx, 'rjb'): c.rjb = np.array([ctx.rjb[d]]) if hasattr(ctx, 'rrup'): c.rrup = np.array([ctx.rrup[d]]) means_log10 = [] for im in set_imt: [mean_ln] = contexts.get_mean_stds([gmpe], c, [SA(im)], None) mean = np.exp(mean_ln[0]) means_log10.append(np.log10(mean)) mb = np.polyfit(t_log10, means_log10, 1) mean_imt_log10 = mb[0] * np.log10(imt) + mb[1] extrap_mean.append(np.log(10**mean_imt_log10)) return extrap_mean
def compute(self, ctx, imts, mean, sig, tau, phi): """ See :meth:`superclass method <.base.GroundShakingIntensityModel.get_mean_and_stddevs>` for spec of input and result values. """ mean_zh06, mean_am09, mean_ab15, mean_ga14 = contexts.get_mean_stds( self.gsims, ctx, imts, None) # Computing adjusted means for m, imt in enumerate(imts): cff = self.COEFFS_SITE[imt] mean[m] = (np.log(np.exp(mean_zh06[0, m]) * cff['mf']) * 0.1 + mean_am09[0, m] * 0.5 + mean_ab15[0, m] * 0.2 + np.log(np.exp(mean_ga14[0, m]) * cff['mf']) * 0.2) if self.sgn: delta = np.minimum((0.15 - 0.0007 * ctx.rrup), 0.35) mean[m] += self.sgn * delta sig[m] = get_sigma(imt)
def compute(self, ctx, imts, mean, sig, tau, phi): """ See :meth:`superclass method <.base.GroundShakingIntensityModel.compute>` for spec of input and result values. """ mean_, sig_, tau_, phi_ = contexts.get_mean_stds( [self.VGMPE, self.HGMPE], ctx, imts) for m, imt in enumerate(imts): # V/H model, Equation 1 and 12 (in natural log units) mean[m] = mean_[0, m] - mean_[1, m] # Get standard deviations C = self.COEFFS[imt] t = _get_tau_vh(C, ctx.mag, tau_[0, m], tau_[1, m]) p = _get_phi_vh(C, ctx.mag, phi_[0, m], phi_[1, m]) sig[m] = np.sqrt(t**2 + p**2) tau[m] = t phi[m] = p
def compute(self, ctx, imts, mean, sig, tau, phi): """ Returns the mean and standard deviations """ ctx_r = copy.copy(ctx) ctx_r.vs30 = np.full_like(ctx_r.vs30, self.rock_vs30) rock = contexts.get_mean_stds(self.gmpe, ctx_r, imts) for m, imt in enumerate(imts): psarock = np.exp(rock[MEAN][m]) C = self.COEFFS_SITE[imt] if self.region: ck = self.COEFFS_REG[imt][self.region] else: ck = 0.0 mean[m] = rock[MEAN][m] + get_site_amplification( C, psarock, ctx, ck) t = rock[INTER][m] p = rock[INTRA][m] sig[m], tau[m], phi[m] = get_stddevs(self.phi_0, C, t, p, psarock, ctx.vs30, imt)