def test_fault_trace_points(self): """ The fault trace must have at least two points. """ fault_trace = Line([Point(0.0, 0.0)]) self.assertRaises(ValueError, SimpleFaultSurface.check_fault_data, fault_trace, 0.0, 1.0, 90.0, 1.0)
def test_get_strike_1(self): p1 = Point(0.0, 0.0) p2 = Point(0.0635916966572, 0.0635916574897) surface = SimpleFaultSurface.from_fault_data(Line([p1, p2]), 1.0, 6.0, 89.9, 1.0) self.assertAlmostEquals(45.0, surface.get_strike(), delta=1e-4)
def test_get_dip_2(self): p1 = Point(0.0, 0.0) p2 = Point(0.0635916966572, 0.0635916574897) surface = SimpleFaultSurface.from_fault_data(Line([p1, p2]), 1.0, 6.0, 30.0, 1.0) self.assertAlmostEquals(30.0, surface.get_dip(), 1)
def test_get_dip_1(self): p1 = Point(0.0, 0.0) p2 = Point(0.0635916966572, 0.0635916574897) p3 = Point(0.0860747816618, 0.102533437776) surface = SimpleFaultSurface.from_fault_data(Line([p1, p2, p3]), 1.0, 6.0, 90.0, 1.0) self.assertAlmostEquals(90.0, surface.get_dip(), delta=1e-6)
def test_get_mesh_5(self): p1 = Point(179.9, 0.0) p2 = Point(180.0, 0.0) p3 = Point(-179.9, 0.0) fault = SimpleFaultSurface.from_fault_data(Line([p1, p2, p3]), 1.0, 6.0, 90.0, 1.0) self.assert_mesh_is(fault, test_data.TEST_5_MESH)
def test_get_mesh_4(self): p1 = Point(0.0, 0.0, 0.0) p2 = Point(0.0, 0.0359728811759, 0.0) p3 = Point(0.0190775080917, 0.0550503815182, 0.0) p4 = Point(0.03974514139, 0.0723925718856, 0.0) fault = SimpleFaultSurface.from_fault_data(Line([p1, p2, p3, p4]), 0.0, 4.0, 90.0, 1.0) self.assert_mesh_is(fault, test_data.TEST_4_MESH)
def test_get_mesh_2(self): p1 = Point(0.0, 0.0, 0.0) p2 = Point(0.0, 0.0359728811759, 0.0) p3 = Point(0.0190775080917, 0.0550503815182, 0.0) p4 = Point(0.03974514139, 0.0723925718856, 0.0) fault = SimpleFaultSurface.from_fault_data(Line([p1, p2, p3, p4]), 2.12132034356, 4.2426406871192848, 45.0, 1.0) self.assert_mesh_is(fault, test_data.TEST_2_MESH)
def test_dip_90_three_points(self): polygon = SimpleFaultSurface.surface_projection_from_fault_data( Line([Point(1, -20), Point(1, -20.2), Point(2, -19.7)]), dip=90, upper_seismogenic_depth=30, lower_seismogenic_depth=50, ) elons = [1, 1, 2] elats = [-20.2, -20., -19.7] numpy.testing.assert_allclose(polygon.lons, elons) numpy.testing.assert_allclose(polygon.lats, elats)
def test_dip_90_self_intersection(self): polygon = SimpleFaultSurface.surface_projection_from_fault_data( Line([Point(1, -2), Point(2, -1.9), Point(3, -2.1), Point(4, -2)]), dip=90, upper_seismogenic_depth=10, lower_seismogenic_depth=20, ) elons = [3., 1., 2., 4.] elats = [-2.1, -2., -1.9, -2.] numpy.testing.assert_allclose(polygon.lons, elons) numpy.testing.assert_allclose(polygon.lats, elats)
def from_fault_data(cls, edges, mesh_spacing): """ Create and return a fault surface using fault source data. :param edges: A list of at least two horizontal edges of the surface as instances of :class:`nhlib.geo.line.Line`. The list should be in top-to-bottom order (the shallowest edge first). :param mesh_spacing: Distance between two subsequent points in a mesh, in km. :returns: An instance of :class:`ComplexFaultSurface` created using that data. :raises ValueError: If requested mesh spacing is too big for the surface geometry (doesn't allow to put a single mesh cell along length and/or width). Uses :meth:`check_fault_data` for checking parameters. """ cls.check_fault_data(edges, mesh_spacing) mean_length = numpy.mean([edge.get_length() for edge in edges]) num_hor_points = int(round(mean_length / mesh_spacing)) + 1 if num_hor_points <= 1: raise ValueError( 'mesh spacing %.1f km is too big for mean length %.1f km' % (mesh_spacing, mean_length)) edges = [ edge.resample_to_num_points(num_hor_points).points for i, edge in enumerate(edges) ] vert_edges = [Line(v_edge) for v_edge in zip(*edges)] mean_width = numpy.mean([v_edge.get_length() for v_edge in vert_edges]) num_vert_points = int(round(mean_width / mesh_spacing)) + 1 if num_vert_points <= 1: raise ValueError( 'mesh spacing %.1f km is too big for mean width %.1f km' % (mesh_spacing, mean_width)) points = zip(*[ v_edge.resample_to_num_points(num_vert_points).points for v_edge in vert_edges ]) mesh = RectangularMesh.from_points_list(points) assert 1 not in mesh.shape return cls(mesh)
def test_dip_90_two_points(self): polygon = SimpleFaultSurface.surface_projection_from_fault_data( Line([Point(2, 2), Point(1, 1)]), dip=90, upper_seismogenic_depth=10, lower_seismogenic_depth=20, ) elons = [ 1.00003181, 0.99996821, 0.99996819, 1.99996819, 2.00003182, 2.00003181 ] elats = [ 0.99996822, 0.99996819, 1.00003178, 2.0000318, 2.0000318, 1.9999682 ] numpy.testing.assert_allclose(polygon.lons, elons) numpy.testing.assert_allclose(polygon.lats, elats)
def test_three_points(self): polygon = SimpleFaultSurface.surface_projection_from_fault_data( Line([Point(10, -20), Point(11, -20.2), Point(12, -19.7)]), dip=30, upper_seismogenic_depth=25.3, lower_seismogenic_depth=53.6, ) elons = [ 11.13560807, 10.1354272, 10.06374285, 12.06361991, 12.13515987 ] elats = [ -21.02520738, -20.82520794, -20.3895235, -20.08952368, -20.52520878 ] numpy.testing.assert_allclose(polygon.lons, elons) numpy.testing.assert_allclose(polygon.lats, elats)
def test_get_dip_5(self): p1 = Point(0.0, 0.0) p2 = Point(0.0, 0.0899322029395) p3 = Point(0.0899323137217, 0.0899320921571) p4 = Point(0.0899323137217, -1.10782376538e-07) surface = SimpleFaultSurface.from_fault_data(Line([p1, p2, p3, p4]), 0.0, 10.0, 45.0, 1.0) # fault contains three segments. the one in the middle is inclined # with dip of 45 degrees. other two are purely vertical (they are # perpendicular to the middle one). the middle segment is rectangle # and the side ones are parallelograms. area of those parallelograms # is area of middle segment times sine of their acute angle. mid_area = 1.0 mid_dip = pi / 4 # 45 degree side_area = sin(mid_dip) * mid_area side_dip = pi / 2 # 90 degree expected_dip = degrees( atan2((mid_area * sin(mid_dip) + 2 * (side_area * sin(side_dip))) / 3.0, (mid_area * cos(mid_dip) + 2 * (side_area * cos(side_dip))) / 3.0)) self.assertAlmostEquals(surface.get_dip(), expected_dip, delta=1e-3)
def test_fault_trace_on_surface(self): fault_trace = Line([Point(0.0, 0.0, 1.0), Point(1.0, 1.0, 0.0)]) self.assertRaises(ValueError, SimpleFaultSurface.check_fault_data, fault_trace, 0.0, 1.0, 90.0, 1.0)
def setUp(self): self.fault_trace = Line([Point(0.0, 0.0), Point(1.0, 1.0)])
def test_get_strike_along_meridian(self): line = Line([Point(0, 0), Point(1e-5, 1e-3), Point(0, 2e-3)]) surface = SimpleFaultSurface.from_fault_data(line, 1.0, 6.0, 89.9, 0.1) self.assertAlmostEquals(0, surface.get_strike(), delta=6e-2)