def setUp(self): super(PointSourceSourceFilterTestCase, self).setUp() self.sitecol = SiteCollection(self.SITES) self.source1 = make_point_source( mfd=EvenlyDiscretizedMFD(min_mag=5, bin_width=1, occurrence_rates=[1]), rupture_aspect_ratio=1.9, upper_seismogenic_depth=0, lower_seismogenic_depth=18.5, magnitude_scaling_relationship=PeerMSR(), nodal_plane_distribution=PMF([ (0.5, NodalPlane(strike=1, dip=2, rake=3)), (0.5, NodalPlane(strike=1, dip=20, rake=3)), ]), location=Point(2.0, 0.0), ) self.source2 = make_point_source( mfd=EvenlyDiscretizedMFD(min_mag=6.5, bin_width=1, occurrence_rates=[1]), rupture_aspect_ratio=0.5, upper_seismogenic_depth=0, lower_seismogenic_depth=18.5, magnitude_scaling_relationship=PeerMSR(), nodal_plane_distribution=PMF([ (0.5, NodalPlane(strike=1, dip=10, rake=3)), (0.5, NodalPlane(strike=1, dip=20, rake=3)), ]), location=Point(2.0, 0.0), )
def __init__(self, source_id, name, tectonic_region_type, mfd, surface, rake): super(CharacteristicFaultSource, self).__init__(source_id, name, tectonic_region_type, mfd, None, None, None) NodalPlane.check_rake(rake) self.surface = surface self.rake = rake
def __init__(self, source_id, name, tectonic_region_type, mfd, surface, rake): super(CharacteristicFaultSource, self).__init__( source_id, name, tectonic_region_type, mfd, None, None, None ) NodalPlane.check_rake(rake) self.surface = surface self.rake = rake
def __init__(self, source_id, name, tectonic_region_type, mfd, temporal_occurrence_model, surface, rake, surface_node=None): super().__init__( source_id, name, tectonic_region_type, mfd, None, None, None, temporal_occurrence_model) NodalPlane.check_rake(rake) self.surface = surface self.rake = rake
def test(self): npd = PMF([(0.5, NodalPlane(1, 20, 3)), (0.5, NodalPlane(2, 2, 4))]) hd = PMF([(1, 14)]) mesh = Mesh(numpy.array([0, 1]), numpy.array([0.5, 1])) mmfd = MultiMFD('incrementalMFD', size=2, min_mag=[4.5], bin_width=[2.0], occurRates=[[.3, .1], [.4, .2, .1]]) mps = MultiPointSource('mp1', 'multi point source', 'Active Shallow Crust', mmfd, PeerMSR(), 1.0, 10, 20, npd, hd, mesh) # test the splitting splits = list(mps) self.assertEqual(len(splits), 2) for split in splits: self.assertEqual(split.grp_id, mps.grp_id) got = obj_to_node(mps).to_str() print(got) exp = '''\ multiPointSource{id='mp1', name='multi point source'} multiPointGeometry gml:posList [0.0, 0.5, 1.0, 1.0] upperSeismoDepth 10 lowerSeismoDepth 20 magScaleRel 'PeerMSR' ruptAspectRatio 1.0 multiMFD{kind='incrementalMFD', size=2} bin_width [2.0] min_mag [4.5] occurRates [0.3, 0.1, 0.4, 0.2, 0.1] lengths [2, 3] nodalPlaneDist nodalPlane{dip=20, probability=0.5, rake=3, strike=1} nodalPlane{dip=2, probability=0.5, rake=4, strike=2} hypoDepthDist hypoDepth{depth=14, probability=1.0} ''' self.assertEqual(got, exp) # test serialization to and from hdf5 tmp = general.gettemp(suffix='.hdf5') with hdf5.File(tmp, 'w') as f: f[mps.source_id] = mps with hdf5.File(tmp, 'r') as f: f[mps.source_id] # test the bounding box bbox = mps.get_bounding_box(maxdist=100) numpy.testing.assert_almost_equal( (-0.8994569916564479, -0.39932, 1.8994569916564479, 1.89932), bbox)
def make_area_source(polygon, discretization, **kwargs): default_arguments = { 'source_id': 'source_id', 'name': 'area source name', 'tectonic_region_type': TRT.VOLCANIC, 'mfd': TruncatedGRMFD(a_val=3, b_val=1, min_mag=5, max_mag=7, bin_width=1), 'nodal_plane_distribution': PMF([(1, NodalPlane(1, 2, 3))]), 'hypocenter_distribution': PMF([(0.5, 4.0), (0.5, 8.0)]), 'upper_seismogenic_depth': 1.3, 'lower_seismogenic_depth': 10.0, 'magnitude_scaling_relationship': PeerMSR(), 'rupture_aspect_ratio': 1.333, 'polygon': polygon, 'area_discretization': discretization, 'rupture_mesh_spacing': 12.33, 'temporal_occurrence_model': PoissonTOM(50.) } default_arguments.update(kwargs) kwargs = default_arguments source = AreaSource(**kwargs) return source
def __init__(self, mag, rake, tectonic_region_type, hypocenter, surface, source_typology, rupture_slip_direction=None, surface_nodes=()): if not mag > 0: raise ValueError('magnitude must be positive') if not hypocenter.depth > 0: raise ValueError('rupture hypocenter must have positive depth') NodalPlane.check_rake(rake) self.tectonic_region_type = tectonic_region_type self.rake = rake self.mag = mag self.hypocenter = hypocenter self.surface = surface self.source_typology = source_typology self.surface_nodes = surface_nodes self.rupture_slip_direction = rupture_slip_direction
def test_dilated(self): mfd = TruncatedGRMFD(a_val=1, b_val=2, min_mag=3, max_mag=5, bin_width=1) np_dist = PMF([(1, NodalPlane(0, 2, 4))]) source = make_point_source(nodal_plane_distribution=np_dist, mfd=mfd) polygon = source.get_rupture_enclosing_polygon(dilation=20) self.assertIsInstance(polygon, Polygon) elons = [ 1.3917408, 1.3908138, 1.3880493, 1.3834740, 1.3771320, 1.3690846, 1.3594093, 1.3481992, 1.3355624, 1.3216207, 1.3065082, 1.2903704, 1.2733628, 1.2556490, 1.2373996, 1.2187902, 1.2000000, 1.1812098, 1.1626004, 1.1443510, 1.1266372, 1.1096296, 1.0934918, 1.0783793, 1.0644376, 1.0518008, 1.0405907, 1.0309154, 1.0228680, 1.0165260, 1.0119507, 1.0091862, 1.0082592, 1.0091788, 1.0119361, 1.0165049, 1.0228411, 1.0308838, 1.0405556, 1.0517635, 1.0643995, 1.0783420, 1.0934567, 1.1095979, 1.1266103, 1.1443298, 1.1625858, 1.1812023, 1.2000000, 1.2187977, 1.2374142, 1.2556702, 1.2733897, 1.2904021, 1.3065433, 1.3216580, 1.3356005, 1.3482365, 1.3594444, 1.3691162, 1.3771589, 1.3834951, 1.3880639, 1.3908212, 1.3917408 ] elats = [ 3.3999810, 3.3812204, 3.3626409, 3.3444213, 3.3267370, 3.3097585, 3.2936490, 3.2785638, 3.2646481, 3.2520357, 3.2408482, 3.2311932, 3.2231637, 3.2168369, 3.2122738, 3.2095182, 3.2085967, 3.2095182, 3.2122738, 3.2168369, 3.2231637, 3.2311932, 3.2408482, 3.2520357, 3.2646481, 3.2785638, 3.2936490, 3.3097585, 3.3267370, 3.3444213, 3.3626409, 3.3812204, 3.3999810, 3.4187420, 3.4373226, 3.4555440, 3.4732305, 3.4902120, 3.5063247, 3.5214135, 3.5353329, 3.5479490, 3.5591401, 3.5687983, 3.5768308, 3.5831599, 3.5877248, 3.5904815, 3.5914033, 3.5904815, 3.5877248, 3.5831599, 3.5768308, 3.5687983, 3.5591401, 3.5479490, 3.5353329, 3.5214135, 3.5063247, 3.4902120, 3.4732305, 3.4555440, 3.4373226, 3.4187420, 3.3999810 ] numpy.testing.assert_allclose(polygon.lons, elons) numpy.testing.assert_allclose(polygon.lats, elats)
def make_point_source(lon=1.2, lat=3.4, **kwargs): default_arguments = { 'source_id': 'source_id', 'name': 'source name', 'tectonic_region_type': TRT.SUBDUCTION_INTRASLAB, 'mfd': TruncatedGRMFD(a_val=1, b_val=2, min_mag=3, max_mag=5, bin_width=1), 'location': Point(lon, lat, 5.6), 'nodal_plane_distribution': PMF([(1, NodalPlane(1, 2, 3))]), 'hypocenter_distribution': PMF([(1, 4)]), 'upper_seismogenic_depth': 1.3, 'lower_seismogenic_depth': 4.9, 'magnitude_scaling_relationship': PeerMSR(), 'rupture_aspect_ratio': 1.333, 'rupture_mesh_spacing': 1.234, 'temporal_occurrence_model': PoissonTOM(50.) } default_arguments.update(kwargs) kwargs = default_arguments ps = PointSource(**kwargs) assert_pickleable(ps) return ps
def test(self): mfd = TruncatedGRMFD(a_val=1, b_val=2, min_mag=3, max_mag=5, bin_width=1) np_dist = PMF([(0.5, NodalPlane(1, 20, 3)), (0.5, NodalPlane(2, 2, 4))]) source = make_point_source(nodal_plane_distribution=np_dist, mfd=mfd) radius = source._get_max_rupture_projection_radius() self.assertAlmostEqual(radius, 1.2830362) mfd = TruncatedGRMFD(a_val=1, b_val=2, min_mag=5, max_mag=6, bin_width=1) np_dist = PMF([(0.5, NodalPlane(1, 40, 3)), (0.5, NodalPlane(2, 30, 4))]) source = make_point_source(nodal_plane_distribution=np_dist, mfd=mfd) radius = source._get_max_rupture_projection_radius() self.assertAlmostEqual(radius, 3.8712214)
def _get_rupture(self, min_mag, max_mag, hypocenter_depth, aspect_ratio, dip, rupture_mesh_spacing, upper_seismogenic_depth=2, lower_seismogenic_depth=16): source_id = name = 'test-source' trt = TRT.ACTIVE_SHALLOW_CRUST mfd = TruncatedGRMFD(a_val=2, b_val=1, min_mag=min_mag, max_mag=max_mag, bin_width=1) location = Point(0, 0) nodal_plane = NodalPlane(strike=45, dip=dip, rake=-123.23) nodal_plane_distribution = PMF([(1, nodal_plane)]) hypocenter_distribution = PMF([(1, hypocenter_depth)]) magnitude_scaling_relationship = PeerMSR() rupture_aspect_ratio = aspect_ratio tom = PoissonTOM(time_span=50) point_source = PointSource( source_id, name, trt, mfd, rupture_mesh_spacing, magnitude_scaling_relationship, rupture_aspect_ratio, tom, upper_seismogenic_depth, lower_seismogenic_depth, location, nodal_plane_distribution, hypocenter_distribution ) ruptures = list(point_source.iter_ruptures()) self.assertEqual(len(ruptures), 1) [rupture] = ruptures self.assertIs(rupture.temporal_occurrence_model, tom) self.assertIs(rupture.tectonic_region_type, trt) self.assertEqual(rupture.rake, nodal_plane.rake) self.assertIsInstance(rupture.surface, PlanarSurface) return rupture
def test_no_dilation(self): mfd = TruncatedGRMFD(a_val=1, b_val=2, min_mag=3, max_mag=5, bin_width=1) np_dist = PMF([(1, NodalPlane(0, 2, 4))]) source = make_point_source(nodal_plane_distribution=np_dist, mfd=mfd) polygon = source.get_rupture_enclosing_polygon() self.assertIsInstance(polygon, Polygon) elons = [ 1.2115590, 1.2115033, 1.2113368, 1.2110612, 1.2106790, 1.2101940, 1.2096109, 1.2089351, 1.2081734, 1.2073329, 1.2064218, 1.2054488, 1.2044234, 1.2033554, 1.2022550, 1.2011330, 1.2000000, 1.1988670, 1.1977450, 1.1966446, 1.1955766, 1.1945512, 1.1935782, 1.1926671, 1.1918266, 1.1910649, 1.1903891, 1.1898060, 1.1893210, 1.1889388, 1.1886632, 1.1884967, 1.1884410, 1.1884967, 1.1886631, 1.1889387, 1.1893209, 1.1898058, 1.1903890, 1.1910647, 1.1918265, 1.1926670, 1.1935781, 1.1945511, 1.1955765, 1.1966446, 1.1977449, 1.1988670, 1.2000000, 1.2011330, 1.2022551, 1.2033554, 1.2044235, 1.2054489, 1.2064219, 1.2073330, 1.2081735, 1.2089353, 1.2096110, 1.2101942, 1.2106791, 1.2110613, 1.2113369, 1.2115033, 1.2115590 ] elats = [ 3.3999999, 3.3988689, 3.3977489, 3.3966505, 3.3955843, 3.3945607, 3.3935894, 3.3926799, 3.3918409, 3.3910805, 3.3904060, 3.3898238, 3.3893397, 3.3889582, 3.3886831, 3.3885169, 3.3884614, 3.3885169, 3.3886831, 3.3889582, 3.3893397, 3.3898238, 3.3904060, 3.3910805, 3.3918409, 3.3926799, 3.3935894, 3.3945607, 3.3955843, 3.3966505, 3.3977489, 3.3988689, 3.3999999, 3.4011309, 3.4022510, 3.4033494, 3.4044156, 3.4054392, 3.4064105, 3.4073200, 3.4081590, 3.4089194, 3.4095940, 3.4101761, 3.4106603, 3.4110418, 3.4113169, 3.4114831, 3.4115386, 3.4114831, 3.4113169, 3.4110418, 3.4106603, 3.4101761, 3.4095940, 3.4089194, 3.4081590, 3.4073200, 3.4064105, 3.4054392, 3.4044156, 3.4033494, 3.4022510, 3.4011309, 3.3999999 ] numpy.testing.assert_allclose(polygon.lons, elons) numpy.testing.assert_allclose(polygon.lats, elats)
def test_case_11(self): hypocenter_probability = (Decimal(1) / len(test_data.SET1_CASE11_HYPOCENTERS)) hypocenter_pmf = PMF([ (hypocenter_probability, hypocenter) for hypocenter in test_data.SET1_CASE11_HYPOCENTERS ]) # apart from hypocenter pmf repeats case 10 sources = [ AreaSource( source_id='area', name='area', tectonic_region_type=const.TRT.ACTIVE_SHALLOW_CRUST, mfd=test_data.SET1_CASE11_MFD, nodal_plane_distribution=PMF([(1, NodalPlane(0.0, 90.0, 0.0))]), hypocenter_distribution=hypocenter_pmf, upper_seismogenic_depth=0.0, lower_seismogenic_depth=10.0, magnitude_scaling_relationship=PointMSR(), rupture_aspect_ratio=test_data.SET1_RUPTURE_ASPECT_RATIO, temporal_occurrence_model=PoissonTOM(1.), polygon=test_data.SET1_CASE11_SOURCE_POLYGON, area_discretization=10.0, rupture_mesh_spacing=10.0) ] sites = SiteCollection([ test_data.SET1_CASE11_SITE1, test_data.SET1_CASE11_SITE2, test_data.SET1_CASE11_SITE3, test_data.SET1_CASE11_SITE4 ]) gsims = {const.TRT.ACTIVE_SHALLOW_CRUST: SadighEtAl1997()} truncation_level = 0 imts = {str(test_data.IMT): test_data.SET1_CASE11_IMLS} curves = calc_hazard_curves(sources, sites, imts, gsims, truncation_level) s1hc, s2hc, s3hc, s4hc = curves[str(test_data.IMT)] assert_hazard_curve_is(self, s1hc, test_data.SET1_CASE11_SITE1_POES, atol=1e-4, rtol=1e-1) assert_hazard_curve_is(self, s2hc, test_data.SET1_CASE11_SITE2_POES, atol=1e-4, rtol=1e-1) assert_hazard_curve_is(self, s3hc, test_data.SET1_CASE11_SITE3_POES, atol=1e-4, rtol=1e-1) assert_hazard_curve_is(self, s4hc, test_data.SET1_CASE11_SITE4_POES, atol=1e-4, rtol=1e-1)
def test(self): npd = PMF([(0.5, NodalPlane(1, 20, 3)), (0.5, NodalPlane(2, 2, 4))]) hd = PMF([(1, 14)]) mesh = Mesh(numpy.array([0, 1]), numpy.array([0.5, 1])) tom = PoissonTOM(50.) mmfd = MultiMFD('incrementalMFD', size=2, min_mag=[4.5], bin_width=[2.0], occurRates=[[.3, .1], [.4, .2, .1]]) mps = MultiPointSource('mp1', 'multi point source', 'Active Shallow Crust', mmfd, 2.0, PeerMSR(), 1.0, tom, 10, 20, npd, hd, mesh) mps.src_group_id = 1 # test the splitting splits = list(split_source(mps)) self.assertEqual(len(splits), 2) for split in splits: self.assertEqual(split.src_group_id, mps.src_group_id) got = obj_to_node(mps).to_str() print(got) self.assertEqual(got, '''\ multiPointSource{id='mp1', name='multi point source', tectonicRegion='Active Shallow Crust'} multiPointGeometry gml:posList [0, 0.5, 1, 1.0] upperSeismoDepth 10 lowerSeismoDepth 20 magScaleRel 'PeerMSR' ruptAspectRatio 1.0 multiMFD{kind='incrementalMFD', size=2} bin_width [2.0] min_mag [4.5] occurRates [0.29999999999999999, 0.10000000000000001, 0.40000000000000002, 0.20000000000000001, 0.10000000000000001] lengths [2, 3] nodalPlaneDist nodalPlane{dip=20, probability=0.5, rake=3, strike=1} nodalPlane{dip=2, probability=0.5, rake=4, strike=2} hypoDepthDist hypoDepth{depth=14, probability=1.0} ''')
def setUp(self): # time span of 10 million years self.time_span = 10e6 nodalplane = NodalPlane(strike=0.0, dip=90.0, rake=0.0) self.mfd = TruncatedGRMFD(a_val=3.5, b_val=1.0, min_mag=5.0, max_mag=6.5, bin_width=0.1) # area source of circular shape with radius of 100 km # centered at 0., 0. self.area1 = AreaSource( source_id='src_1', name='area source', tectonic_region_type='Active Shallow Crust', mfd=self.mfd, nodal_plane_distribution=PMF([(1.0, nodalplane)]), hypocenter_distribution=PMF([(1.0, 5.0)]), upper_seismogenic_depth=0.0, lower_seismogenic_depth=10.0, magnitude_scaling_relationship=WC1994(), rupture_aspect_ratio=1.0, polygon=Point(0., 0.).to_polygon(100.), area_discretization=9.0, rupture_mesh_spacing=1.0, temporal_occurrence_model=PoissonTOM(self.time_span)) # area source of circular shape with radius of 100 km # centered at 1., 1. self.area2 = AreaSource( source_id='src_1', name='area source', tectonic_region_type='Active Shallow Crust', mfd=self.mfd, nodal_plane_distribution=PMF([(1.0, nodalplane)]), hypocenter_distribution=PMF([(1.0, 5.0)]), upper_seismogenic_depth=0.0, lower_seismogenic_depth=10.0, magnitude_scaling_relationship=WC1994(), rupture_aspect_ratio=1.0, polygon=Point(5., 5.).to_polygon(100.), area_discretization=9.0, rupture_mesh_spacing=1.0, temporal_occurrence_model=PoissonTOM(self.time_span)) # non-parametric source self.np_src, _ = make_non_parametric_source()
def test_case_10(self): hypocenter_pmf = PMF([(1, test_data.SET1_CASE10_HYPOCENTER_DEPTH)]) sources = [ AreaSource( source_id='area', name='area', tectonic_region_type=const.TRT.ACTIVE_SHALLOW_CRUST, mfd=test_data.SET1_CASE10_MFD, nodal_plane_distribution=PMF([(1, NodalPlane(0.0, 90.0, 0.0))]), hypocenter_distribution=hypocenter_pmf, upper_seismogenic_depth=0.0, lower_seismogenic_depth=10.0, magnitude_scaling_relationship=PeerMSR(), rupture_aspect_ratio=test_data.SET1_RUPTURE_ASPECT_RATIO, polygon=test_data.SET1_CASE10_SOURCE_POLYGON, area_discretization=30.0, rupture_mesh_spacing=10.0) ] sites = SiteCollection([ test_data.SET1_CASE10_SITE1, test_data.SET1_CASE10_SITE2, test_data.SET1_CASE10_SITE3, test_data.SET1_CASE10_SITE4 ]) gsims = {const.TRT.ACTIVE_SHALLOW_CRUST: SadighEtAl1997()} truncation_level = 0 time_span = 1.0 imts = {test_data.IMT: test_data.SET1_CASE10_IMLS} curves = hazard_curves(sources, sites, imts, time_span, gsims, truncation_level) s1hc, s2hc, s3hc, s4hc = curves[test_data.IMT] assert_hazard_curve_is(self, s1hc, test_data.SET1_CASE10_SITE1_POES, tolerance=2e-3) assert_hazard_curve_is(self, s2hc, test_data.SET1_CASE10_SITE2_POES, tolerance=2e-3) assert_hazard_curve_is(self, s3hc, test_data.SET1_CASE10_SITE3_POES, tolerance=2e-3) assert_hazard_curve_is(self, s4hc, test_data.SET1_CASE10_SITE4_POES, tolerance=2e-3)
def test_rupture_close_to_south_pole(self): # data taken from real example and causing "surface's angles are not # right" error mfd = EvenlyDiscretizedMFD( min_mag=5., bin_width=0.1, occurrence_rates=[2.180e-07] ) nodal_plane_dist = PMF([(1., NodalPlane(135., 20., 90.))]) src = PointSource(source_id='1', name='pnt', tectonic_region_type='asc', mfd=mfd, rupture_mesh_spacing=1, magnitude_scaling_relationship=WC1994(), rupture_aspect_ratio=1., temporal_occurrence_model=PoissonTOM(50.), upper_seismogenic_depth=0, lower_seismogenic_depth=26, location=Point(-165.125, -83.600), nodal_plane_distribution=nodal_plane_dist, hypocenter_distribution=PMF([(1., 9.)])) ruptures = list(src.iter_ruptures()) self.assertEqual(len(ruptures), 1)
def __fromh5__(self, dic, attrs): self.source_id = attrs['source_id'] self.name = attrs['name'] self.tectonic_region_type = attrs['tectonic_region_type'] self.magnitude_scaling_relationship = SCALEREL[ attrs['magnitude_scaling_relationship']] npd = dic.pop('nodal_plane_distribution').value hdd = dic.pop('hypocenter_distribution').value mesh = dic.pop('mesh').value self.rupture_aspect_ratio = dic.pop('rupture_aspect_ratio').value self.lower_seismogenic_depth = dic.pop('lower_seismogenic_depth').value self.upper_seismogenic_depth = dic.pop('upper_seismogenic_depth').value [(mfd_kind, mfd)] = dic.items() self.nodal_plane_distribution = PMF([ (prob, NodalPlane(strike, dip, rake)) for prob, strike, dip, rake in npd]) self.hypocenter_distribution = PMF(hdd) self.mesh = Mesh(mesh['lon'], mesh['lat']) kw = {k: dset.value for k, dset in mfd.items()} kw['size'] = len(mesh) kw['kind'] = mfd_kind self.mfd = MultiMFD(**kw)
def test_areasource(self): nodalplane = NodalPlane(strike=0.0, dip=90.0, rake=0.0) src = AreaSource(source_id='src_1', name='area source', tectonic_region_type='Active Shallow Crust', mfd=TruncatedGRMFD(a_val=3.5, b_val=1.0, min_mag=5.0, max_mag=6.5, bin_width=0.1), nodal_plane_distribution=PMF([(1.0, nodalplane)]), hypocenter_distribution=PMF([(1.0, 5.0)]), upper_seismogenic_depth=0.0, lower_seismogenic_depth=10.0, magnitude_scaling_relationship=WC1994(), rupture_aspect_ratio=1.0, polygon=Polygon([ Point(-0.5, -0.5), Point(-0.5, 0.5), Point(0.5, 0.5), Point(0.5, -0.5) ]), area_discretization=9.0, rupture_mesh_spacing=1.0, temporal_occurrence_model=PoissonTOM(50.)) site = Site(location=Point(0.0, 0.0), vs30=800.0, vs30measured=True, z1pt0=500.0, z2pt5=2.0) gsims = {'Active Shallow Crust': BooreAtkinson2008()} imt = SA(period=0.1, damping=5.0) iml = 0.2 truncation_level = 3.0 n_epsilons = 3 mag_bin_width = 0.2 # in km dist_bin_width = 10.0 # in decimal degree coord_bin_width = 0.2 # compute disaggregation bin_edges, diss_matrix = disagg.disaggregation( [src], site, imt, iml, gsims, truncation_level, n_epsilons, mag_bin_width, dist_bin_width, coord_bin_width) mag_bins, dist_bins, lon_bins, lat_bins, eps_bins, trt_bins = bin_edges numpy.testing.assert_almost_equal( mag_bins, [5., 5.2, 5.4, 5.6, 5.8, 6., 6.2, 6.4, 6.6]) numpy.testing.assert_almost_equal( dist_bins, [0., 10., 20., 30., 40., 50., 60., 70., 80.]) numpy.testing.assert_almost_equal( lat_bins, [-0.6, -0.4, -0.2, 0., 0.2, 0.4, 0.6]) numpy.testing.assert_almost_equal( lon_bins, [-0.6, -0.4, -0.2, 0., 0.2, 0.4, 0.6]) numpy.testing.assert_almost_equal(eps_bins, [-3., -1., 1., 3.]) self.assertEqual(trt_bins, ['Active Shallow Crust']) expected_matrix = numpy.fromstring( codecs.decode( codecs.decode( b"""\ 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\ """, 'base64'), 'zip')).reshape((8, 8, 6, 6, 3, 1)) numpy.testing.assert_almost_equal(diss_matrix, expected_matrix)
def test_7_many_ruptures(self): source_id = name = 'test7-source' trt = TRT.VOLCANIC mag1 = 4.5 mag2 = 5.5 mag1_rate = 9e-3 mag2_rate = 9e-4 hypocenter1 = 9.0 hypocenter2 = 10.0 hypocenter1_weight = Decimal('0.8') hypocenter2_weight = Decimal('0.2') nodalplane1 = NodalPlane(strike=45, dip=90, rake=0) nodalplane2 = NodalPlane(strike=0, dip=45, rake=10) nodalplane1_weight = Decimal('0.3') nodalplane2_weight = Decimal('0.7') upper_seismogenic_depth = 2 lower_seismogenic_depth = 16 rupture_aspect_ratio = 2 rupture_mesh_spacing = 0.5 location = Point(0, 0) magnitude_scaling_relationship = PeerMSR() tom = PoissonTOM(time_span=50) mfd = EvenlyDiscretizedMFD(min_mag=mag1, bin_width=(mag2 - mag1), occurrence_rates=[mag1_rate, mag2_rate]) nodal_plane_distribution = PMF([(nodalplane1_weight, nodalplane1), (nodalplane2_weight, nodalplane2)]) hypocenter_distribution = PMF([(hypocenter1_weight, hypocenter1), (hypocenter2_weight, hypocenter2)]) point_source = PointSource( source_id, name, trt, mfd, rupture_mesh_spacing, magnitude_scaling_relationship, rupture_aspect_ratio, tom, upper_seismogenic_depth, lower_seismogenic_depth, location, nodal_plane_distribution, hypocenter_distribution) actual_ruptures = list(point_source.iter_ruptures()) self.assertEqual(len(actual_ruptures), point_source.count_ruptures()) expected_ruptures = { (mag1, nodalplane1.rake, hypocenter1): ( # probabilistic rupture's occurrence rate 9e-3 * 0.3 * 0.8, # rupture surface corners planar_surface_test_data.TEST_7_RUPTURE_1_CORNERS), (mag2, nodalplane1.rake, hypocenter1): (9e-4 * 0.3 * 0.8, planar_surface_test_data.TEST_7_RUPTURE_2_CORNERS), (mag1, nodalplane2.rake, hypocenter1): (9e-3 * 0.7 * 0.8, planar_surface_test_data.TEST_7_RUPTURE_3_CORNERS), (mag2, nodalplane2.rake, hypocenter1): (9e-4 * 0.7 * 0.8, planar_surface_test_data.TEST_7_RUPTURE_4_CORNERS), (mag1, nodalplane1.rake, hypocenter2): (9e-3 * 0.3 * 0.2, planar_surface_test_data.TEST_7_RUPTURE_5_CORNERS), (mag2, nodalplane1.rake, hypocenter2): (9e-4 * 0.3 * 0.2, planar_surface_test_data.TEST_7_RUPTURE_6_CORNERS), (mag1, nodalplane2.rake, hypocenter2): (9e-3 * 0.7 * 0.2, planar_surface_test_data.TEST_7_RUPTURE_7_CORNERS), (mag2, nodalplane2.rake, hypocenter2): (9e-4 * 0.7 * 0.2, planar_surface_test_data.TEST_7_RUPTURE_8_CORNERS) } for actual_rupture in actual_ruptures: expected_occurrence_rate, expected_corners = expected_ruptures[( actual_rupture.mag, actual_rupture.rake, actual_rupture.hypocenter.depth)] self.assertTrue( isinstance(actual_rupture, ParametricProbabilisticRupture)) self.assertEqual(actual_rupture.occurrence_rate, expected_occurrence_rate) self.assertIs(actual_rupture.temporal_occurrence_model, tom) self.assertEqual(actual_rupture.tectonic_region_type, trt) surface = actual_rupture.surface tl, tr, br, bl = expected_corners self.assertEqual(tl, surface.top_left) self.assertEqual(tr, surface.top_right) self.assertEqual(bl, surface.bottom_left) self.assertEqual(br, surface.bottom_right)
def test_areasource(self): nodalplane = NodalPlane(strike=0.0, dip=90.0, rake=0.0) src = AreaSource(source_id='src_1', name='area source', tectonic_region_type='Active Shallow Crust', mfd=TruncatedGRMFD(a_val=3.5, b_val=1.0, min_mag=5.0, max_mag=6.5, bin_width=0.1), nodal_plane_distribution=PMF([(1.0, nodalplane)]), hypocenter_distribution=PMF([(1.0, 5.0)]), upper_seismogenic_depth=0.0, lower_seismogenic_depth=10.0, magnitude_scaling_relationship=WC1994(), rupture_aspect_ratio=1.0, polygon=Polygon([ Point(-0.5, -0.5), Point(-0.5, 0.5), Point(0.5, 0.5), Point(0.5, -0.5) ]), area_discretization=9.0, rupture_mesh_spacing=1.0, temporal_occurrence_model=PoissonTOM(50.)) site = Site(location=Point(0.0, 0.0), vs30=800.0, vs30measured=True, z1pt0=500.0, z2pt5=2.0) gsims = {'Active Shallow Crust': BooreAtkinson2008()} imt = SA(period=0.1, damping=5.0) iml = 0.2 truncation_level = 3.0 n_epsilons = 3 mag_bin_width = 0.2 # in km dist_bin_width = 10.0 # in decimal degree coord_bin_width = 0.2 # compute disaggregation bin_edges, diss_matrix = disagg.disaggregation( [src], site, imt, iml, gsims, truncation_level, n_epsilons, mag_bin_width, dist_bin_width, coord_bin_width) mag_bins, dist_bins, lon_bins, lat_bins, eps_bins, trt_bins = bin_edges numpy.testing.assert_almost_equal( mag_bins, [5., 5.2, 5.4, 5.6, 5.8, 6., 6.2, 6.4, 6.6]) numpy.testing.assert_almost_equal( dist_bins, [0., 10., 20., 30., 40., 50., 60., 70., 80.]) numpy.testing.assert_almost_equal(lat_bins, [ -6.5544231e-01, -4.9158173e-01, -3.2772115e-01, -1.6386058e-01, 1.1102230e-16, 1.6386058e-01, 3.2772115e-01, 4.9158173e-01, 6.5544231e-01 ]) numpy.testing.assert_almost_equal(lon_bins, [ -6.5544231e-01, -4.9158173e-01, -3.2772115e-01, -1.6386058e-01, 1.1102230e-16, 1.6386058e-01, 3.2772115e-01, 4.9158173e-01, 6.5544231e-01 ]) numpy.testing.assert_almost_equal(eps_bins, [-3., -1., 1., 3.]) self.assertEqual(trt_bins, ['Active Shallow Crust']) self.assertEqual(diss_matrix.shape, (8, 8, 8, 8, 3, 1)) expected = [ 0.0245487, 0.0231275, 0.0210702, 0.0185196, 0.0157001, 0.0130175, 0.0107099, 0.0045489 ] numpy.testing.assert_almost_equal( diss_matrix.sum(axis=(1, 2, 3, 4, 5)), expected)
return boundary_lons, boundary_lats # define area source src = AreaSource( source_id='1', name='area', tectonic_region_type='Active Shallow Crust', mfd=TruncatedGRMFD(min_mag=5., max_mag=6.5, bin_width=0.2, a_val=3.45, b_val=0.98), rupture_mesh_spacing=2., magnitude_scaling_relationship=WC1994(), rupture_aspect_ratio=1., temporal_occurrence_model=PoissonTOM(50.), upper_seismogenic_depth=2., lower_seismogenic_depth=12., nodal_plane_distribution=PMF([(1, NodalPlane(strike=45, dip=30, rake=0))]), hypocenter_distribution=PMF([(1, 7.)]), polygon=Polygon([Point(133.5, -22.5), Point(133.5, -23.0), Point(130.75, -23.75), Point(130.75, -24.5), Point(133.5, -26.0), Point(133.5, -27.0), Point(130.75, -27.0), Point(128.977, -25.065), Point(128.425, -23.436), Point(126.082, -23.233), Point(125.669, -22.351), Point(125.4, -20.5), Point(125.75, -20.25), Point(126.7, -21.25), Point(128.5, -21.25), Point(129.25, -20.6), Point(130.0, -20.6), Point(130.9, -22.25), Point(133.0, -22.0), Point(133.5, -22.5)]), area_discretization=20. ) src = area_model # loop over ruptures, extract rupture surface boundary and magnitude min_lon, max_lon, min_lat, max_lat, m = get_map_projection(src)