예제 #1
0
def vespagram_backazimuth(st,
                          s,
                          bazmin,
                          bazmax,
                          bazsteps,
                          winlen,
                          stat='power',
                          n=1):
    '''
    Calculates the vespagram for a seismic array over a given range of backazimuths, for a single scalar slowness, using the statistic specified.

    The chosen statistic is calculated as a function of time (in s) and backazimuth (in deg). This may be:-

    * 'amplitude' - the raw amplitude of the linear or nth root stack at each time and slowness step;
    * 'power' - the power in the linear or nth root beam calculated over a time window (length winlen) around each time step for each slowness;
    * 'F' - the F-statistic of the beam calculated over a time window (length winlen) around each time step for each slowness.

    Parameters
    ----------
    st : ObsPy Stream object
        Stream of SAC format seismograms for the seismic array, length K = no. of stations in array
    s : float
        Magnitude of the slowness vector, in s/km
    bazmin  : float
        Minimum backazimuth, in degrees
    bazmax  : float
        Maximum backazimuth, in degrees
    bazsteps  : int
        Integer number of steps between bazmin and bazmax for which to calculate the vespagram
    winlen : int
        Length of Hann window over which to calculate the power.
    stat : string
        Statistic to use for plotting the vespagram, either 'amplitude', 'power', or 'F'
        
    Returns
    -------
    vespagram_data : NumPy array
        Array of values for the chosen statistic at each backazimuth and time step. Dimensions: bazsteps*len(tr) for traces tr in st.
    '''

    if stat == 'amplitude':
        vespagram_data = np.array([
            nth_root_stack(st, s, baz, n)
            for baz in np.linspace(bazmin, bazmax, bazsteps)
        ])
    elif stat == 'power':
        vespagram_data = np.array([
            n_power_vespa(st, s, baz, n, winlen)
            for baz in np.linspace(bazmin, bazmax, bazsteps)
        ])
    elif stat == 'F':
        vespagram_data = np.array([
            f_vespa(st, s, baz, winlen)
            for baz in np.linspace(bazmin, bazmax, bazsteps)
        ])
    else:
        raise AssertionError(
            "'stat' argument must be one of 'amplitude', 'power' or 'F'")

    return vespagram_data
예제 #2
0
def vespagram(st, smin, smax, ssteps, baz, winlen, stat='power', n=1):
    '''
    Calculates the vespagram for a seismic array over a given slowness range, for a single backazimuth, using the statistic specified.

    The chosen statistic is calculated as a function of time (in s) and slowness (in s/km). This may be:-

    * 'amplitude' - the raw amplitude of the linear or nth root stack at each time and slowness step;
    * 'power' - the power in the linear or nth root beam calculated over a time window (length winlen) around each time step for each slowness;
    * 'F' - the F-statistic of the beam calculated over a time window (length winlen) around each time step for each slowness.

    Parameters
    ----------
    st : ObsPy Stream object
        Stream of SAC format seismograms for the seismic array, length K = no. of stations in array
    smin  : float
        Minimum magnitude of slowness vector, in s / km
    smax  : float
        Maximum magnitude of slowness vector, in s / km
    ssteps  : int
        Integer number of steps between smin and smax for which to calculate the vespagram
    baz : float
        Backazimuth of slowness vector, (i.e. angle from North back to epicentre of event)
    winlen : int
        Length of Hann window over which to calculate the power.
    stat : string
        Statistic to use for plotting the vespagram, either 'amplitude', 'power', or 'F'
        
    Returns
    -------
    vespagram_data : NumPy array
        Array of values for the chosen statistic at each slowness and time step. Dimensions: ssteps*len(tr) for traces tr in st.
    '''

    assert stat == 'amplitude' or stat == 'power' or stat == 'F', "'stat' argument must be one of 'amplitude', 'power' or 'F'"

    vespagram_data = np.array([])

    try:
        if stat == 'amplitude':
            vespagram_data = np.array([
                nth_root_stack(st, s, baz, n)
                for s in np.linspace(smin, smax, ssteps)
            ])
        elif stat == 'power':
            vespagram_data = np.array([
                n_power_vespa(st, s, baz, n, winlen)
                for s in np.linspace(smin, smax, ssteps)
            ])
        elif stat == 'F':
            vespagram_data = np.array([
                f_vespa(st, s, baz, winlen)
                for s in np.linspace(smin, smax, ssteps)
            ])
    except AssertionError as err:
        raise err

    return vespagram_data
예제 #3
0
def vespagram(st, smin, smax, ssteps, baz, winlen, stat='power', n=1):
    '''
    Calculates the vespagram for a seismic array over a given slowness range, for a single backazimuth, using the statistic specified.

    The chosen statistic is calculated as a function of time (in s) and slowness (in s/km). This may be:-

    * 'amplitude' - the raw amplitude of the linear or nth root stack at each time and slowness step;
    * 'power' - the power in the linear or nth root beam calculated over a time window (length winlen) around each time step for each slowness;
    * 'F' - the F-statistic of the beam calculated over a time window (length winlen) around each time step for each slowness.

    Parameters
    ----------
    st : ObsPy Stream object
        Stream of SAC format seismograms for the seismic array, length K = no. of stations in array
    smin  : float
        Minimum magnitude of slowness vector, in s / km
    smax  : float
        Maximum magnitude of slowness vector, in s / km
    ssteps  : int
        Integer number of steps between smin and smax for which to calculate the vespagram
    baz : float
        Backazimuth of slowness vector, (i.e. angle from North back to epicentre of event)
    winlen : int
        Length of Hann window over which to calculate the power.
    stat : string
        Statistic to use for plotting the vespagram, either 'amplitude', 'power', or 'F'
        
    Returns
    -------
    vespagram_data : NumPy array
        Array of values for the chosen statistic at each slowness and time step. Dimensions: ssteps*len(tr) for traces tr in st.
    '''
    
    assert stat == 'amplitude' or stat == 'power' or stat == 'F', "'stat' argument must be one of 'amplitude', 'power' or 'F'" 
    
    vespagram_data = np.array([])    
    
    try:
        if stat == 'amplitude':
            vespagram_data = np.array([nth_root_stack(st, s, baz, n) for s in np.linspace(smin, smax, ssteps)])
        elif stat == 'power':
            vespagram_data = np.array([n_power_vespa(st, s, baz, n, winlen) for s in np.linspace(smin, smax, ssteps)])
        elif stat == 'F':
            vespagram_data = np.array([f_vespa(st, s, baz, winlen) for s in np.linspace(smin, smax, ssteps)])
    except AssertionError as err:
        raise err

    return vespagram_data
예제 #4
0
def vespagram_backazimuth(st, s, bazmin, bazmax, bazsteps, winlen, stat='power', n=1):
    '''
    Calculates the vespagram for a seismic array over a given range of backazimuths, for a single scalar slowness, using the statistic specified.

    The chosen statistic is calculated as a function of time (in s) and backazimuth (in deg). This may be:-

    * 'amplitude' - the raw amplitude of the linear or nth root stack at each time and slowness step;
    * 'power' - the power in the linear or nth root beam calculated over a time window (length winlen) around each time step for each slowness;
    * 'F' - the F-statistic of the beam calculated over a time window (length winlen) around each time step for each slowness.

    Parameters
    ----------
    st : ObsPy Stream object
        Stream of SAC format seismograms for the seismic array, length K = no. of stations in array
    s : float
        Magnitude of the slowness vector, in s/km
    bazmin  : float
        Minimum backazimuth, in degrees
    bazmax  : float
        Maximum backazimuth, in degrees
    bazsteps  : int
        Integer number of steps between bazmin and bazmax for which to calculate the vespagram
    winlen : int
        Length of Hann window over which to calculate the power.
    stat : string
        Statistic to use for plotting the vespagram, either 'amplitude', 'power', or 'F'
        
    Returns
    -------
    vespagram_data : NumPy array
        Array of values for the chosen statistic at each backazimuth and time step. Dimensions: bazsteps*len(tr) for traces tr in st.
    '''
    
    if stat == 'amplitude':
        vespagram_data = np.array([nth_root_stack(st, s, baz, n) for baz in np.linspace(bazmin, bazmax, bazsteps)])
    elif stat == 'power':
        vespagram_data = np.array([n_power_vespa(st, s, baz, n, winlen) for baz in np.linspace(bazmin, bazmax, bazsteps)])
    elif stat == 'F':
        vespagram_data = np.array([f_vespa(st, s, baz, winlen) for baz in np.linspace(bazmin, bazmax,bazsteps)])
    else:
        raise AssertionError("'stat' argument must be one of 'amplitude', 'power' or 'F'")
        
    return vespagram_data
예제 #5
0
def f_vespagram_theoretical_arrivals(st, origin, smin, smax, ssteps, baz,
                                     winlen):
    '''
    Plots the F-stat vespagram for a seismic array over a given slowness range, for a single backazimuth, using the statistic specified. Also plots theoretical arrival times and slownesses for each phase.

    The chosen statistic is plotted as a function of time (in s) and slowness (in s/km). This may be:-
                                                                 
    * 'amplitude' - the raw amplitude of the linear or nth root stack at each time and slowness step;
    * 'power' - the power in the linear or nth root beam calculated over a time window (length winlen) around each time step for each slowness;
    * 'F' - the F-statistic of the beam calculated over a time window (length winlen) around each time step for each slowness.

    Parameters
    ----------
    st : ObsPy Stream object
        Stream of SAC format seismograms for the seismic array, length K = no. of stations in array
    origin : ObsPy Origin object
        Origin of the event in question. Should contain the origin time of the earthquake and if necessary the depth and location.
    smin  : float
        Minimum magnitude of slowness vector, in s / km
    smax  : float
        Maximum magnitude of slowness vector, in s / km
    ssteps  : int
        Integer number of steps between smin and smax for which to calculate the vespagram
    baz : float
        Backazimuth of slowness vector, (i.e. angle from North back to epicentre of event)
    winlen : int
        Length of Hann window over which to calculate the power.
    stat : string
        Statistic to use for plotting the vespagram, either 'amplitude', 'power', or 'F'
    display: string
        Option for plotting: either 'contourf' for filled contour plot, or 'contour' for contour plot. See matplotlib documentation for more details.
    '''

    starttime = st[0].stats.starttime
    tt_model = TauPyModel()

    # Arrivals are calculated from the information in origin.
    delta = locations2degrees(
        origin.latitude, origin.longitude, st[0].stats.sac.stla,
        st[0].stats.sac.stlo)  # Distance in degrees from source to receiver
    arrivals = tt_model.get_travel_times(origin.depth / 1000., delta)

    arrival_names = [arrival.name for arrival in arrivals]
    arrival_times = [
        origin.time + arrival.time - starttime for arrival in arrivals
    ]
    arrival_slowness = [
        arrival.ray_param_sec_degree / G_KM_DEG for arrival in arrivals
    ]

    plt.figure(figsize=(16, 8))

    vespagram = np.array(
        [f_vespa(st, s, baz, winlen) for s in np.linspace(smin, smax, ssteps)])
    label = 'F'
    timestring = str(st[0].stats.starttime.datetime)
    title = timestring + ": " + label + " Vespagram"

    plt.contourf(st[0].times(), np.linspace(smin, smax, ssteps),
                 vespagram[:, :])

    cb = plt.colorbar()
    cb.set_label(label)

    # Plot predicted arrivals
    plt.scatter(arrival_times, arrival_slowness, c='cyan', s=200, marker='+')

    plt.xlabel("Time (s)")
    plt.xlim(min(st[0].times()), max(st[0].times()))
    plt.ylim(smin, smax)

    # Thanks, Stack Overflow: http://stackoverflow.com/questions/5147112/matplotlib-how-to-put-individual-tags-for-a-scatter-plot
    for label, x, y in zip(arrival_names, arrival_times, arrival_slowness):
        plt.annotate(label,
                     xy=(x, y),
                     xytext=(-20, 20),
                     textcoords='offset points',
                     ha='right',
                     va='bottom',
                     bbox=dict(boxstyle='round,pad=0.5',
                               fc='yellow',
                               alpha=0.5),
                     arrowprops=dict(arrowstyle='->',
                                     connectionstyle='arc3,rad=0'))

    plt.ylabel("Slowness (s / km)")
    plt.title(title)
예제 #6
0
def f_vespagram_theoretical_arrivals(st, origin, smin, smax, ssteps, baz, winlen):
    '''
    Plots the F-stat vespagram for a seismic array over a given slowness range, for a single backazimuth, using the statistic specified. Also plots theoretical arrival times and slownesses for each phase.

    The chosen statistic is plotted as a function of time (in s) and slowness (in s/km). This may be:-
                                                                 
    * 'amplitude' - the raw amplitude of the linear or nth root stack at each time and slowness step;
    * 'power' - the power in the linear or nth root beam calculated over a time window (length winlen) around each time step for each slowness;
    * 'F' - the F-statistic of the beam calculated over a time window (length winlen) around each time step for each slowness.

    Parameters
    ----------
    st : ObsPy Stream object
        Stream of SAC format seismograms for the seismic array, length K = no. of stations in array
    origin : ObsPy Origin object
        Origin of the event in question. Should contain the origin time of the earthquake and if necessary the depth and location.
    smin  : float
        Minimum magnitude of slowness vector, in s / km
    smax  : float
        Maximum magnitude of slowness vector, in s / km
    ssteps  : int
        Integer number of steps between smin and smax for which to calculate the vespagram
    baz : float
        Backazimuth of slowness vector, (i.e. angle from North back to epicentre of event)
    winlen : int
        Length of Hann window over which to calculate the power.
    stat : string
        Statistic to use for plotting the vespagram, either 'amplitude', 'power', or 'F'
    display: string
        Option for plotting: either 'contourf' for filled contour plot, or 'contour' for contour plot. See matplotlib documentation for more details.
    '''
    
    starttime = st[0].stats.starttime
    tt_model = TauPyModel()
    
    # Arrivals are calculated from the information in origin.
    delta = locations2degrees(origin.latitude, origin.longitude, st[0].stats.sac.stla, st[0].stats.sac.stlo) # Distance in degrees from source to receiver
    arrivals = tt_model.get_travel_times(origin.depth/1000., delta)
    
    arrival_names = [arrival.name for arrival in arrivals]
    arrival_times = [origin.time + arrival.time - starttime for arrival in arrivals]
    arrival_slowness = [arrival.ray_param_sec_degree/G_KM_DEG for arrival in arrivals]
    
    plt.figure(figsize=(16, 8))

    vespagram = np.array([f_vespa(st, s, baz, winlen) for s in np.linspace(smin, smax, ssteps)])
    label = 'F'
    timestring = str(st[0].stats.starttime.datetime)
    title = timestring + ": " + label + " Vespagram"
    
    plt.contourf(st[0].times(), np.linspace(smin, smax, ssteps), vespagram[:, :])
    
    cb = plt.colorbar()
    cb.set_label(label)
    
    # Plot predicted arrivals
    plt.scatter(arrival_times, arrival_slowness, c='cyan', s=200, marker='+')
    
    plt.xlabel("Time (s)")
    plt.xlim(min(st[0].times()), max(st[0].times()))
    plt.ylim(smin, smax)
    
    # Thanks, Stack Overflow: http://stackoverflow.com/questions/5147112/matplotlib-how-to-put-individual-tags-for-a-scatter-plot
    for label, x, y in zip(arrival_names, arrival_times, arrival_slowness):
        plt.annotate(label, xy=(x, y), xytext=(-20, 20), textcoords='offset points', ha='right', va='bottom', 
                     bbox=dict(boxstyle='round,pad=0.5', fc='yellow', alpha=0.5), 
                     arrowprops=dict(arrowstyle='->', connectionstyle='arc3,rad=0'))
        
    plt.ylabel("Slowness (s / km)")
    plt.title(title)