Source code for fracspy.mtinversion.greensfunction

import numpy as np


[docs] def collect_source_angles(x, y, z, recs): #, nc=3): r"""Angles between sources and receivers Compute angles between sources in a regular 3-dimensional grid and receivers Parameters ---------- x : :obj:`numpy.ndarray` X-axis y : :obj:`numpy.ndarray` Y-axis z : :obj:`numpy.ndarray` Z-axis recs : :obj:`numpy.ndarray` Receiver locations of size :math:`3 \times n_r` Returns ------- cosine_sourceangles : :obj:`numpy.ndarray` Cosine source angles of size :math:`3 \times n_r \times n_x \times n_y \times n_z` dists : :obj:`numpy.ndarray` Distances of size :math:`\times n_r \times n_x \times n_y \times n_z` Notes ----- This routine computes the cosine source angles and distances between any pair of sources and receivers. Cosine source angles are defined as follows: .. math:: cos(\theta_x) = (x_s - x_r) / d \\ cos(\theta_y) = (y_s - y_r) / d \\ cos(\theta_z) = (z_s - z_r) / d \\ where :math:`d=\sqrt{(x_s - x_r)^2+(y_s - y_r)^2+(z_s - z_r)^2+}` are the distances. """ # Define dimensions nc = 3 nr = recs.shape[1] nx, ny, nz = len(x), len(y), len(z) # Initialise angle and distance tables cosine_sourceangles = np.zeros([nc, nr, nx, ny, nz]) dists = np.zeros([nr, nx, ny, nz]) for irec in range(nr): # Separate receiver into x-,y-,z-components rx, ry, rz = recs[0, irec], recs[1, irec], recs[2, irec] # Create regular grid of source coordinates s_locs_x, s_locs_y, s_locs_z = np.meshgrid(x, y, z, indexing='ij') # Compute pair-wise and total distances delta_x = s_locs_x - rx delta_y = s_locs_y - ry delta_z = s_locs_z - rz total_distance = np.sqrt(delta_x ** 2 + delta_y ** 2 + delta_z ** 2) # Assign distances for a given receiver to distance table dists[irec] = total_distance # Remove rec loc from total distance table rl = np.argwhere(total_distance == 0) if len(rl) > 0: # Temporarily set total_distance to 999 for rec loc total_distance[rl[0][0], rl[0][1], rl[0][2]] = 999 # Compute cosines of source angles cosine_sourceangles[0, irec] = delta_x / total_distance cosine_sourceangles[1, irec] = delta_y / total_distance cosine_sourceangles[2, irec] = delta_z / total_distance if len(rl) > 0: # Put correct source angle for receiver location cosine_sourceangles[:, irec, rl[0][0], rl[0][1], rl[0][2]] = 0 return cosine_sourceangles, dists
[docs] def pwave_greens_comp( cosine_sourceangles, dists, src_idx, vel, MT_comp_dict, comp_idx, omega_p, ): r"""Particle velocity component of the P-wave Green's function Compute Green's function for a given-component (x, y, or z) of the P-wave between a source and a set of receivers Parameters ---------- cosine_sourceangles : :obj:`numpy.ndarray` Cosine source angles of size :math:`3 \times n_r \times n_x \times n_y \times n_z` dists : :obj:`numpy.ndarray` Distances of size :math:`\times n_r \times n_x \times n_y \times n_z` src_idx : :obj:`numpy.ndarray` Source location indices (relative to x, y, and z axes) vel : :obj:`numpy.ndarray` Velocity model MT_comp_dict : :obj:`dict` Dictionary containing Moment Tensor parameters comp_idx : :obj:`int` Index of component at receiver side omega_p : :obj:`float` Peak frequency of the given wave Returns ------- G_z : :obj:`numpy.ndarray` Green's functions of size :math:`6 \times n_r` Notes ----- This method computes the amplitudes of a given component of the particle velocity Green's functions associated to the first P-wave arrival, assuming a known source location based on the far-field particle velocity expression from a moment tensor source in a homogeneous full space (eq. 4.29, [1]_): .. math:: v_i^P = j \omega_P \left( \frac{\gamma_i\gamma_p\gamma_q}{4\pi\rho\alpha^3} \frac{1}{r} \right) M_{pq} where: - :math:`v` is the particle velocity measurements (seismic data) at the arrival of the wave, in other words the P-wave peak amplitudes; - :math:`M` is the moment tensor; - :math:`\theta` describes whether we are utilising the P-wave information; - :math:`i` describes the i-component of the data, aligning with the below p,q definitions; - :math:`p` describes the first index of the moment tensor element; - :math:`q` describes the second index of the moment tensor element; - :math:`\omega_P` is the peak frequency of the given wave; - :math:`\gamma_{i/p/q}` is the take-off angle in the z/p/q-th direction (for a ray between the source and receiver); - :math:`r` is the distance between source and receiver; - :math:`\alpha` is the average velocity (currently we assume a homogeneous velocity); - :math:`\rho` is the average density; .. [1] Aki, K., and Richards, P. G. "Quantitative Seismology", University Science Books, 2002. """ nr = cosine_sourceangles.shape[1] # Extract cosine source angle and distance at selected source location dist_sloc = dists[:, src_idx[0], src_idx[1], src_idx[2]] cosine_src = cosine_sourceangles[:, :, src_idx[0], src_idx[1], src_idx[2]] # Compute common scalar all_scaler = omega_p / (4 * np.pi * np.mean(vel) ** 3) # Compute P-wave Green's function (z-component) G_z = np.zeros([6, nr]) for cmp_dict in MT_comp_dict: for irec in range(nr): el_indic = cmp_dict['elementID'] p_idx, q_idx = cmp_dict['pq'] cosine_src_elements = cosine_src[comp_idx, irec] * cosine_src[p_idx, irec] * cosine_src[q_idx, irec] G_z[el_indic, irec] = all_scaler * cosine_src_elements * dist_sloc[irec] ** -1 return G_z
[docs] def mt_pwave_greens_comp( n_xyz, cosine_sourceangles, dists, vel, MT_comp_dict, comp_idx, omega_p, ): r"""Particle velocity component of the P-wave Green's functions within a volumetric source grid for all moment tensor components Compute Green's functions for a given-component (x, y, or z) of the P-wave between sources defined in a regular 3-dimensional grid and a set of receivers Parameters ---------- n_xyz : :obj:`tuple` Number of grid points in X-, Y-, and Z-axes for the source area cosine_sourceangles : :obj:`numpy.ndarray` Cosine source angles of size :math:`3 \times n_r \times n_x \times n_y \times n_z` dists : :obj:`numpy.ndarray` Distances of size :math:`\times n_r \times n_x \times n_y \times n_z` vel : :obj:`numpy.ndarray` Velocity model MT_comp_dict : :obj:`dict` Dictionary containing Moment Tensor parameters comp_idx : :obj:`int` Index of component at receiver side omega_p : :obj:`float` Peak frequency of the given wave Returns ------- Gc : :obj:`numpy.ndarray` Green's functions of size :math:`6 \times n_r \times n_x \times n_y \times n_z` for a given component Notes ----- This method computes the amplitudes of a given component of the particle velocity Green's functions associated to the first P-wave arrival, for a uniform grid of source location based on the far-field particle velocity expression from a moment tensor source in a homogeneous full space for all of the 6 different moment tensor components. """ nx, ny, nz = n_xyz nr = cosine_sourceangles.shape[1] # Compute Green's functions Gc = np.zeros([6, nr, nx, ny, nz]) for ix in range(nx): for iy in range(ny): for iz in range(nz): Gc[:, :, ix, iy, iz] = pwave_greens_comp(cosine_sourceangles, dists, [ix, iy, iz], vel, MT_comp_dict, comp_idx=comp_idx, omega_p=omega_p) return Gc
[docs] def mt_pwave_greens_multicomp( n_xyz, cosine_sourceangles, dists, vel, MT_comp_dict, omega_p, ): r"""Particle velocity components of the P-wave Green's functions within a volumetric source grid for all moment tensor components Compute Green's functions for the 3-components (x, y, and z) of the P-wave between sources defined in a regular 3-dimensional grid and a set of receivers Parameters ---------- n_xyz : :obj:`tuple` Number of grid points in X-, Y-, and Z-axes for the source area cosine_sourceangles : :obj:`numpy.ndarray` Cosine source angles of size :math:`3 \times n_r \times n_x \times n_y \times n_z` dists : :obj:`numpy.ndarray` Distances of size :math:`\times n_r \times n_x \times n_y \times n_z` vel : :obj:`numpy.ndarray` Velocity model MT_comp_dict : :obj:`dict` Dictionary containing Moment Tensor parameters omega_p : :obj:`float` Peak frequency of the given wave Returns ------- Gx : :obj:`numpy.ndarray` x-component Green's functions of size :math:`6 \times n_r \times n_x \times n_y \times n_z` Gy : :obj:`numpy.ndarray` y-component Green's functions of size :math:`6 \times n_r \times n_x \times n_y \times n_z` Gz : :obj:`numpy.ndarray` z-component Green's functions of size :math:`6 \times n_r \times n_x \times n_y \times n_z` Notes ----- This method computes the amplitudes of the 3-component particle velocity Green's functions associated to the first P-wave arrival, for a uniform grid of source location based on the far-field particle velocity expression from a moment tensor source in a homogeneous full space for all of the 6 different moment tensor components. """ nx, ny, nz = n_xyz nr = cosine_sourceangles.shape[1] # Compute Green's functions Gx = np.zeros([6, nr, nx, ny, nz]) Gy = np.zeros([6, nr, nx, ny, nz]) Gz = np.zeros([6, nr, nx, ny, nz]) for ix in range(nx): for iy in range(ny): for iz in range(nz): Gx[:, :, ix, iy, iz] = pwave_greens_comp(cosine_sourceangles, dists, [ix, iy, iz], vel, MT_comp_dict, comp_idx=0, omega_p=omega_p) Gy[:, :, ix, iy, iz] = pwave_greens_comp(cosine_sourceangles, dists, [ix, iy, iz], vel, MT_comp_dict, comp_idx=1, omega_p=omega_p) Gz[:, :, ix, iy, iz] = pwave_greens_comp(cosine_sourceangles, dists, [ix, iy, iz], vel, MT_comp_dict, comp_idx=2, omega_p=omega_p) return Gx, Gy, Gz