
    1i,b                        d Z ddlZddlZddlZddlZddlmZ ddlm	Z	 ddlm
Z
 ddlmZ ddlmZmZ dd	lmZ dd
lmZ ddlmZmZ ddlmZmZmZmZmZ ddlmZ g dZ  eddd          e          Zdddddddddddddeej                 de deej                 de!de de d e"d!eeeej        f                  d"eej#        j$                 d#e%d$e"d%eeeej        f         ej        f         fd&Z&ddddd'd(d)dd*deej                 de deej                 de!d+e!d,ee          d-ee          d"eej#        j$                 d%ej        fd.Z'dej        d!ej        d/e de d e"d%ej        fd0Z(d1 Z) ej*        d2d3gd4dd56          d7             Z+ ej*        d8d9gd:dd6          d;             Z, ej*        d<d=gd>dd6          d?             Z-d@ Z. ej*        dAdBgdCdd6          dD             Z/ ej*        dEdFgdGdd6          dH             Z0dS )Iz^
Beat and tempo
==============
.. autosummary::
   :toctree: generated/

   beat_track
   plp
    N   )cache)core)onset)util)	tempogramfourier_tempogram)tempo)ParameterError)moved	vectorize)AnyCallableOptionalTupleUnion)_FloatLike_co)
beat_trackr
   plpzlibrosa.beat.tempoz0.10.0z1.0)
moved_fromversionversion_removedi"V  i   g      ^@d   Tframes)ysronset_envelope
hop_length	start_bpm	tightnesstrimbpmpriorunitssparser   r   r   r   r   r    r!   r"   r#   r$   r%   returnc                 x   |3| t          d          t          j        | ||t          j                  }|
r#|j        dk    rt          d|j         d          |                                sb|
rdt          j        g t                    fS t          j	        |j
        dd	         t          
          t          j        |t                    fS |t          |||||          }t          j        |          }t!          j        ||j        t%          |j                            }t'          ||t          |          |z  ||          }|
rjt          j        |          }|	dk    rnO|	dk    r|t+          j        ||          fS |	dk    r|t+          j        |||          fS t          d|	           ||fS )a  Dynamic programming beat tracker.

    Beats are detected in three stages, following the method of [#]_:

      1. Measure onset strength
      2. Estimate tempo from onset correlation
      3. Pick peaks in onset strength approximately consistent with estimated
         tempo

    .. [#] Ellis, Daniel PW. "Beat tracking by dynamic programming."
           Journal of New Music Research 36.1 (2007): 51-60.
           http://labrosa.ee.columbia.edu/projects/beattrack/

    Parameters
    ----------
    y : np.ndarray [shape=(..., n)] or None
        audio time series

    sr : number > 0 [scalar]
        sampling rate of ``y``

    onset_envelope : np.ndarray [shape=(..., m)] or None
        (optional) pre-computed onset strength envelope.

    hop_length : int > 0 [scalar]
        number of audio samples between successive ``onset_envelope`` values

    start_bpm : float > 0 [scalar]
        initial guess for the tempo estimator (in beats per minute)

    tightness : float [scalar]
        tightness of beat distribution around tempo

    trim : bool [scalar]
        trim leading/trailing beats with weak onsets

    bpm : float [scalar] or np.ndarray [shape=(...)]
        (optional) If provided, use ``bpm`` as the tempo instead of
        estimating it from ``onsets``.

        If multichannel, tempo estimates can be provided for all channels.

        Tempo estimates may also be time-varying, in which case the shape
        of ``bpm`` should match that of ``onset_envelope``, i.e.,
        one estimate provided for each frame.

    prior : scipy.stats.rv_continuous [optional]
        An optional prior distribution over tempo.
        If provided, ``start_bpm`` will be ignored.

    units : {'frames', 'samples', 'time'}
        The units to encode detected beat events in.
        By default, 'frames' are used.

    sparse : bool
        If ``True`` (default), detections are returned as an array of frames,
        samples, or time indices (as specified by ``units=``).

        If ``False``, detections are encoded as a dense boolean array where
        ``beats[..., n]`` is true if there's a beat at frame index ``n``.

        .. note:: multi-channel input is only supported when ``sparse=False``.

    Returns
    -------
    tempo : float [scalar, non-negative] or np.ndarray
        estimated global tempo (in beats per minute)

        If multi-channel and ``bpm`` is not provided, a separate
        tempo will be returned for each channel
    beats : np.ndarray
        estimated beat event locations.

        If `sparse=True` (default), beat locations are given in the specified units
        (default is frame indices).

        If `sparse=False` (required for multichannel input), beat events are
        indicated by a boolean for each frame.
    .. note::
        If no onset strength could be detected, beat_tracker estimates 0 BPM
        and returns an empty list.

    Raises
    ------
    ParameterError
        if neither ``y`` nor ``onset_envelope`` are provided,
        or if ``units`` is not one of 'frames', 'samples', or 'time'

    See Also
    --------
    librosa.onset.onset_strength

    Examples
    --------
    Track beats using time series input

    >>> y, sr = librosa.load(librosa.ex('choice'), duration=10)

    >>> tempo, beats = librosa.beat.beat_track(y=y, sr=sr)
    >>> tempo
    135.99917763157896

    Print the frames corresponding to beats

    >>> beats
    array([  3,  21,  40,  59,  78,  96, 116, 135, 154, 173, 192, 211,
           230, 249, 268, 287, 306, 325, 344, 363])

    Or print them as timestamps

    >>> librosa.frames_to_time(beats, sr=sr)
    array([0.07 , 0.488, 0.929, 1.37 , 1.811, 2.229, 2.694, 3.135,
           3.576, 4.017, 4.458, 4.899, 5.341, 5.782, 6.223, 6.664,
           7.105, 7.546, 7.988, 8.429])

    Output beat detections as a boolean array instead of frame indices
    >>> tempo, beats_dense = librosa.beat.beat_track(y=y, sr=sr, sparse=False)
    >>> beats_dense
    array([False, False, False,  True, False, False, False, False,
       False, False, False, False, False, False, False, False,
       False, False, False, False, ..., False, False,  True,
       False, False, False, False, False, False, False, False,
       False, False, False, False, False, False, False, False,
       False])

    Track beats using a pre-computed onset envelope

    >>> onset_env = librosa.onset.onset_strength(y=y, sr=sr,
    ...                                          aggregate=np.median)
    >>> tempo, beats = librosa.beat.beat_track(onset_envelope=onset_env,
    ...                                        sr=sr)
    >>> tempo
    135.99917763157896
    >>> beats
    array([  3,  21,  40,  59,  78,  96, 116, 135, 154, 173, 192, 211,
           230, 249, 268, 287, 306, 325, 344, 363])

    Plot the beat events against the onset strength envelope

    >>> import matplotlib.pyplot as plt
    >>> hop_length = 512
    >>> fig, ax = plt.subplots(nrows=2, sharex=True)
    >>> times = librosa.times_like(onset_env, sr=sr, hop_length=hop_length)
    >>> M = librosa.feature.melspectrogram(y=y, sr=sr, hop_length=hop_length)
    >>> librosa.display.specshow(librosa.power_to_db(M, ref=np.max),
    ...                          y_axis='mel', x_axis='time', hop_length=hop_length,
    ...                          ax=ax[0])
    >>> ax[0].label_outer()
    >>> ax[0].set(title='Mel spectrogram')
    >>> ax[1].plot(times, librosa.util.normalize(onset_env),
    ...          label='Onset strength')
    >>> ax[1].vlines(times[beats], 0, 1, alpha=0.5, color='r',
    ...            linestyle='--', label='Beats')
    >>> ax[1].legend()
    Nz$y or onset_envelope must be providedr   r   r   	aggregater   z'sparse=True (default) does not support zK-dimensional inputs. Either set sparse=False or convert the signal to mono.        dtypeshaper,   )r   r   r   r   r#   ndimaxesr   samples)r   time)r   r   zInvalid unit type: )r   r   onset_strengthnpmedianr1   anyarrayintzerosr/   float
zeros_likebool_tempo
atleast_1dr   	expand_torange__beat_trackerflatnonzeror   frames_to_samplesframes_to_time)r   r   r   r   r   r    r!   r"   r#   r$   r%   _bpmbpm_expandedbeatss                 J/var/www/html/speakWrite/venv/lib/python3.11/site-packages/librosa/beat.pyr   r   %   s   T 9 !GHHH-B:
 
 
  K.%** J!&J J J K K 	K
  ? 	?"C00011H>#7#<EJJJM.===? ? {)!
 
 
 =D>$'5':',TY'7'79 9 9L
 ><rZ9OQZ\`aaE 
@u%%Hi/*MMMNNf__,UzbQQQRR !>u!>!>???<    i     i,  )r   r   r   r   
win_length	tempo_min	tempo_maxr#   rM   rN   rO   c                 B   |"t          j        | ||t          j                  }||||k    rt	          d| d|           t          ||||          }t          j        |||          }	|d|d|	|k     ddf<   |d|d|	|k    ddf<   t          j	        |	|j
        d	
          }	t          j        dt          j        |          z            }
||
|                    |	          z  }
|
                    d	d          }d||
|k     <   |t          j        |          dz  t          j        |                    d	d                    z   z  }t          j        |d||j        d                   }t          j        |dd|          }t          j        |d          S )a  Predominant local pulse (PLP) estimation. [#]_

    The PLP method analyzes the onset strength envelope in the frequency domain
    to find a locally stable tempo for each frame.  These local periodicities
    are used to synthesize local half-waves, which are combined such that peaks
    coincide with rhythmically salient frames (e.g. onset events on a musical time grid).
    The local maxima of the pulse curve can be taken as estimated beat positions.

    This method may be preferred over the dynamic programming method of `beat_track`
    when the tempo is expected to vary significantly over time.  Additionally,
    since `plp` does not require the entire signal to make predictions, it may be
    preferable when beat-tracking long recordings in a streaming setting.

    .. [#] Grosche, P., & Muller, M. (2011).
        "Extracting predominant local pulse information from music recordings."
        IEEE Transactions on Audio, Speech, and Language Processing, 19(6), 1688-1701.

    Parameters
    ----------
    y : np.ndarray [shape=(..., n)] or None
        audio time series. Multi-channel is supported.

    sr : number > 0 [scalar]
        sampling rate of ``y``

    onset_envelope : np.ndarray [shape=(..., n)] or None
        (optional) pre-computed onset strength envelope

    hop_length : int > 0 [scalar]
        number of audio samples between successive ``onset_envelope`` values

    win_length : int > 0 [scalar]
        number of frames to use for tempogram analysis.
        By default, 384 frames (at ``sr=22050`` and ``hop_length=512``) corresponds
        to about 8.9 seconds.

    tempo_min, tempo_max : numbers > 0 [scalar], optional
        Minimum and maximum permissible tempo values.  ``tempo_max`` must be at least
        ``tempo_min``.

        Set either (or both) to `None` to disable this constraint.

    prior : scipy.stats.rv_continuous [optional]
        A prior distribution over tempo (in beats per minute).
        By default, a uniform prior over ``[tempo_min, tempo_max]`` is used.

    Returns
    -------
    pulse : np.ndarray, shape=[(..., n)]
        The estimated pulse curve.  Maxima correspond to rhythmically salient
        points of time.

        If input is multi-channel, one pulse curve per channel is computed.

    See Also
    --------
    beat_track
    librosa.onset.onset_strength
    librosa.feature.fourier_tempogram

    Examples
    --------
    Visualize the PLP compared to an onset strength envelope.
    Both are normalized here to make comparison easier.

    >>> y, sr = librosa.load(librosa.ex('brahms'))
    >>> onset_env = librosa.onset.onset_strength(y=y, sr=sr)
    >>> pulse = librosa.beat.plp(onset_envelope=onset_env, sr=sr)
    >>> # Or compute pulse with an alternate prior, like log-normal
    >>> import scipy.stats
    >>> prior = scipy.stats.lognorm(loc=np.log(120), scale=120, s=1)
    >>> pulse_lognorm = librosa.beat.plp(onset_envelope=onset_env, sr=sr,
    ...                                  prior=prior)
    >>> melspec = librosa.feature.melspectrogram(y=y, sr=sr)

    >>> import matplotlib.pyplot as plt
    >>> fig, ax = plt.subplots(nrows=3, sharex=True)
    >>> librosa.display.specshow(librosa.power_to_db(melspec,
    ...                                              ref=np.max),
    ...                          x_axis='time', y_axis='mel', ax=ax[0])
    >>> ax[0].set(title='Mel spectrogram')
    >>> ax[0].label_outer()
    >>> ax[1].plot(librosa.times_like(onset_env),
    ...          librosa.util.normalize(onset_env),
    ...          label='Onset strength')
    >>> ax[1].plot(librosa.times_like(pulse),
    ...          librosa.util.normalize(pulse),
    ...          label='Predominant local pulse (PLP)')
    >>> ax[1].set(title='Uniform tempo prior [30, 300]')
    >>> ax[1].label_outer()
    >>> ax[2].plot(librosa.times_like(onset_env),
    ...          librosa.util.normalize(onset_env),
    ...          label='Onset strength')
    >>> ax[2].plot(librosa.times_like(pulse_lognorm),
    ...          librosa.util.normalize(pulse_lognorm),
    ...          label='Predominant local pulse (PLP)')
    >>> ax[2].set(title='Log-normal tempo prior, mean=120', xlim=[5, 20])
    >>> ax[2].legend()

    PLP local maxima can be used as estimates of beat positions.

    >>> tempo, beats = librosa.beat.beat_track(onset_envelope=onset_env)
    >>> beats_plp = np.flatnonzero(librosa.util.localmax(pulse))
    >>> import matplotlib.pyplot as plt
    >>> fig, ax = plt.subplots(nrows=2, sharex=True, sharey=True)
    >>> times = librosa.times_like(onset_env, sr=sr)
    >>> ax[0].plot(times, librosa.util.normalize(onset_env),
    ...          label='Onset strength')
    >>> ax[0].vlines(times[beats], 0, 1, alpha=0.5, color='r',
    ...            linestyle='--', label='Beats')
    >>> ax[0].legend()
    >>> ax[0].set(title='librosa.beat.beat_track')
    >>> ax[0].label_outer()
    >>> # Limit the plot to a 15-second window
    >>> times = librosa.times_like(pulse, sr=sr)
    >>> ax[1].plot(times, librosa.util.normalize(pulse),
    ...          label='PLP')
    >>> ax[1].vlines(times[beats_plp], 0, 1, alpha=0.5, color='r',
    ...            linestyle='--', label='PLP Beats')
    >>> ax[1].legend()
    >>> ax[1].set(title='librosa.beat.plp', xlim=[5, 20])
    >>> ax[1].xaxis.set_major_formatter(librosa.display.TimeFormatter())
    Nr(   z
tempo_max=z must be larger than tempo_min=)r   r   r   rM   )r   r   rM   r   .r0   g    .AT)axiskeepdims      ?r   r-   )r   n_fftlengthrR   )r   r5   r6   r7   r   r	   r   fourier_tempo_frequenciesr   rA   r1   log1pabslogpdfmaxtinyistftr/   clip	normalize)r   r   r   r   rM   rN   rO   r#   ftgramtempo_frequenciesftmagpeak_valuespulses                rJ   r   r     s   N -B:
 
 
 !69	;Q;QNNN9NN
 
 	

 %	  F 6*   89s%	11114589s%	111145 '8v{QSTTT HS26&>>)**E/000))d)33K"#F5; di3&

T
0R0R)S)SSSF J1J~7KB7O  E
 GE1dE**E >%b))))rK   
frame_ratec                 *   t          j        |dk              rt          d| d          |dk    rt          d          |j        d         d| j        d         fvrt          d|j         d| j                   t          j        |d	z  |z            }t          t          |           |          }t          |||          \  }}t          |          }	t          j	        | t          
          }
t          ||	|
           t          ||
|          }
|
S )a[  Tracks beats in an onset strength envelope.

    Parameters
    ----------
    onset_envelope : np.ndarray [shape=(..., n,)]
        onset strength envelope
    bpm : float [scalar] or np.ndarray [shape=(...)]
        tempo estimate
    frame_rate : float [scalar]
        frame rate of the spectrogram (sr / hop_length, frames per second)
    tightness : float [scalar, positive]
        how closely do we adhere to bpm?
    trim : bool [scalar]
        trim leading/trailing beats with weak onsets?

    Returns
    -------
    beats : np.ndarray [shape=(n,)]
        frame numbers of beat events
    r   zbpm=z must be strictly positivez#tightness must be strictly positiver-   r   zInvalid bpm shape=z% does not match onset envelope shape=g      N@r+   )r6   r8   r   r/   round__beat_local_score__normalize_onsets__beat_track_dp__last_beatr=   r>   __dp_backtrack__trim_beats)r   r"   rf   r    r!   frames_per_beat
localscorebacklinkcumscoretailrI   s              rJ   rC   rC     s,   . 
vcQh ECCCCCDDDA~~BCCC y}Q 4R 8999x#)xxbpbvxxyyy hzD03677O $$6~$F$FXXJ )_iPPHh x  DM.555E8T5))) %Z==ELrK   c                 f    |                      ddd          }| |t          j        |           z   z  S )z2Normalize onset strength by its standard deviationr   r-   T)ddofrR   rS   )stdr   r]   )onsetsnorms     rJ   rj   rj     s3    ::12:55DTDIf---..rK   z(void(float32[:], float32[:], float32[:])z(void(float64[:], float64[:], float64[:])z(t),(n)->(t)F)nopythonr   c           
      >   t          |           }t          |          dk    rt          j        dt          j        |d          |d         dz             dz  |d         z  dz  z            }t          |          }t	          t          |                     D ]p}d||<   t	          t          d||dz  z   |z
  dz             t          ||dz  z   |                    D ]*}||xx         ||         | ||dz  z   |z
           z  z  cc<   +qd S t          |          t          |           k    rt	          t          |                     D ]}t          j        dt          j        ||          ||         dz             dz  ||         z  dz  z            }dt          ||                   z  dz   }d||<   t	          t          d||dz  z   |z
  dz             t          ||dz  z   |                    D ]*}||xx         ||         | ||dz  z   |z
           z  z  cc<   +d S d S )Nr   g      r   g      @@   r*   )lenr6   exparangerB   r\   minr:   )r   ro   rp   NwindowKiks           rJ   ri   ri     sy    	NA
?q   	?1+=*=q?QTU?U V VY] ]`opq`r rwxxxyyKKs>**++ 	I 	IAJqM 3q!a1f*q.1"455s1qAv:q7I7IJJ I I1^A1HaK-H!HHI		I 	I 
_		^!4!4	4	4 s>**++ 	L 	LAVDBIq/A.A?STCUXYCY$Z$Z]a$adstudv$v{|#||}}FC*+++a/AJqM3q!a1f*q.1"455s1qAv:q7I7IJJ L L1^AQJN-K!KKL 
5	4	L 	LrK   z;void(float32[:], float32[:], float32, int32[:], float32[:])z;void(float64[:], float64[:], float32, int32[:], float64[:])z(t),(n),()->(t),(t)c           
      l   d|                                  z  }d}d|d<   | d         |d<   t          t          |          dk              }t          |           D ]\  }}	t          j         }
d}t          |t	          j        |||z           dz            z
  |d|||z           z  z
  dz
  d          D ]X}|dk     r nO||         |t	          j        ||z
            t	          j        |||z                     z
  dz  z  z
  }||
k    r|}
|}Y|dk    r	|	|
z   ||<   n|	||<   |r|	|k     rd||<   |||<   d}dS )	z&Core dynamic program for beat trackingg{Gz?Tr-   r   r   r{   FN)	r\   r:   r|   	enumerater6   infrB   rh   log)rp   ro   r    rq   rr   score_thresh
first_beattvr   score_i
best_scorebeat_locationlocscores                 rJ   rk   rk   (  s    *..***L JHQKQ-HQK 
S!!A%	&	&B
++  
7vX
 RXob1f&=&ABBBAO\^ab\bLcHcDcfgDgilmm 	$ 	$CQwwSMIC26/Z\_`Z`JaCbCb1bef0f$ffEz!!"
 # A!J.HQKK "HQK  	'L00HQKK'HQKJJ7 rK   z+void(float32[:], bool_[:], bool_, bool_[:])z+void(float64[:], bool_[:], bool_, bool_[:])z(t),(t),()->(t)c                    ||dd<   t          j        d          }t          j        | |         |          t          |          dz  t          |           t          |          dz  z            }|rd|dz                                  dz  z  }nd}d}| |         |k    rd||<   |dz  }| |         |k    t          |           dz
  }| |         |k    rd||<   |dz  }| |         |k    dS )	zCRemove spurious leading and trailing beats from the detection arrayN   r{   rT   r*   r   Fr   )r6   hanningconvolver|   mean)rp   rI   r!   beats_trimmedw
smooth_boe	thresholdns           rJ   rn   rn   [  s    M!!! 	
1A Z.223q6619S__SQRVVUVY=V3VWJ  JM//11367			 	
A
Q-9
$
$ a	Q Q-9
$
$ 	J!A
Q-9
$
$ a	Q Q-9
$
$ 	DrK   c                 p   t          j        | d           }t          j                            | |          }t          j                            |d          }dt          j                            |          z  }t          j        | j        dd         t                    }t          | |||           |S )z/Identify the position of the last detected beatr-   rW   )datamaskrT   Nr.   )r   localmaxr6   mamasked_arrayr7   getdataemptyr/   r:   __last_beat_selector)rr   r   masked_scoresmedians
thresholdsrs   s         rJ   rl   rl     s     M(,,,,DE&&H4&@@Mell=rl22Gru}}W---J 8(."-S999D4T:::KrK   z-void(float32[:], bool_[:], float32, int64[:])z-void(float64[:], bool_[:], float64, int64[:])z(t),(t),()->()c                     t          |           dz
  }||d<   |dk    r(||         s| |         |k    r||d<   dS |dz  }|dk    &dS dS )zmVectorized helper to identify the last valid beat position:

    cumscore[n] > threshold and not mask[n]
    r   r   N)r|   )rr   r   r   outr   s        rJ   r   r     sj     	HACF
q&&Aw 	8A;)33CFEFA q&&&&&&rK   zvoid(int32[:], int32, bool_[:])zvoid(int64[:], int64, bool_[:])z(t),()->(t)c                 @    |}|dk    rd||<   | |         }|dk    dS dS )z>Populate the beat indicator array from a sequence of backlinksr   TN )	backlinksrs   rI   r   s       rJ   rm   rm     s7     	A
q&&aaL q&&&&&&rK   )1__doc__numpyr6   scipyscipy.statsnumba_cacher    r   r   r   featurer   r	   r
   r?   util.exceptionsr   util.decoratorsr   r   typingr   r   r   r   r   _typingr   __all__ndarrayr<   r:   r>   statsrv_continuousstrr   r   rC   rj   guvectorizeri   rk   rn   rl   r   rm   r   rK   rJ   <module>r      s                                      1 1 1 1 1 1 1 1 $ $ $ $ $ $ + + + + + + - - - - - - - - 8 8 8 8 8 8 8 8 8 8 8 8 8 8 " " " " " "
(
(
( 	X-xQVWWW
	 	 #+/6:15] ] ]
] 	] RZ(	]
 ] ] ] ] 
%rz12	3] EK-.] ] ] 5
*+RZ78] ] ] ]D #+/!#!$15z* z* z*
z* 	z* RZ(	z*
 z* z* z* z* EK-.z* Zz* z* z* z*z3J3%'Z3=B3OT3\`3Z3 3 3 3n/ / / 66	
 	U$ $ $L L$ $LD II	
 	T# # #) )# #)X 55
   	 	 	<   ;;	
 	T
 
 
 
 
  --	
 	T
 
 
 
 
  rK   