
    Xf1                         d Z ddlZddlmZ  ej        de            G d d          Z G d de          Z G d	 d
e          ZdS )zDynamic Programming algorithms for general usage.

This module contains classes which implement Dynamic Programming
algorithms that can be used generally.
    N)BiopythonDeprecationWarningzThe 'Bio.HMM.DynamicProgramming' module is deprecated and will be removed in a future release of Biopython. Consider using the hmmlearn package instead.c                   0    e Zd ZdZd Zd Zd Zd Zd ZdS )AbstractDPAlgorithmsa  An abstract class to calculate forward and backward probabilities.

    This class should not be instantiated directly, but should be used
    through a derived class which implements proper scaling of variables.

    This class is just meant to encapsulate the basic forward and backward
    algorithms, and allow derived classes to deal with the problems of
    multiplying probabilities.

    Derived class of this must implement:

    - _forward_recursion -- Calculate the forward values in the recursion
      using some kind of technique for preventing underflow errors.
    - _backward_recursion -- Calculate the backward values in the recursion
      step using some technique to prevent underflow errors.

    c                 "    || _         || _        dS )zInitialize to calculate forward and backward probabilities.

        Arguments:
         - markov_model -- The current Markov model we are working with.
         - sequence -- A training sequence containing a set of emissions.

        N)_mm_seqselfmarkov_modelsequences      :lib/python3.11/site-packages/Bio/HMM/DynamicProgramming.py__init__zAbstractDPAlgorithms.__init__-   s      			    c                      t          d          )z0Calculate the forward recursion value (PRIVATE).Subclasses must implementNotImplementedErrorr
   	cur_statesequence_posforward_varss       r   _forward_recursionz'AbstractDPAlgorithms._forward_recursion8       !"=>>>r   c                    | j         j        }i }d||d         df<   t          dt          |                    D ]}d|||         df<   t          t          | j        j                            D ]'}|D ]"}|                     |||          }|||||f<   #(|d         }d}|D ]B}	||	t          | j        j                  dz
  f         }| j         j        |	|f         }
|||
z  z  }C||fS )a  Calculate sequence probability using the forward algorithm.

        This implements the forward algorithm, as described on p57-58 of
        Durbin et al.

        Returns:
         - A dictionary containing the forward variables. This has keys of the
           form (state letter, position in the training sequence), and values
           containing the calculated forward variable.
         - The calculated probability of the sequence.

           r   )r   state_alphabetrangelenr   	emissionsr   transition_prob)r
   state_lettersforward_varki
main_stateforward_valuefirst_stateseq_prob
state_itemtransition_values              r   forward_algorithmz&AbstractDPAlgorithms.forward_algorithm<   sB    / ./]1%r*+q#m,,-- 	4 	4A23Kq)2.//
 s49.//00 	A 	AA+ A A
 !% 7 7
A{ S S ,3@KQ0A $A&' 	9 	9J'S9L5M5MPQ5Q(RSM#x7[8QR(888HHH$$r   c                      t          d          )z1Calculate the backward recursion value (PRIVATE).r   r   r   s       r   _backward_recursionz(AbstractDPAlgorithms._backward_recursiont   r   r   c                    | j         j        }i }|d         }|D ];}| j         j        ||d         f         ||t          | j        j                  dz
  f<   <t          t          t          | j        j                  dz
                      }|                                 |D ]'}|D ]"}| 	                    |||          }|||||f<   #(|S )a  Calculate sequence probability using the backward algorithm.

        This implements the backward algorithm, as described on p58-59 of
        Durbin et al.

        Returns:
         - A dictionary containing the backwards variables. This has keys
           of the form (state letter, position in the training sequence),
           and values containing the calculated backward variable.

        r   r   )
r   r   r!   r   r   r    listr   reverser.   )	r
   r"   backward_varfirst_letterstateall_indexesr%   r&   backward_values	            r   backward_algorithmz'AbstractDPAlgorithms.backward_algorithmx   s    / $Q'" 	 	E(%q1A)BC %TY%8!9!9A!=>?? 5TY%8!9!9A!=>>?? 	C 	CA+ C C
 "&!9!9*a!V!V!-4BL*a1C r   N)	__name__
__module____qualname____doc__r   r   r,   r.   r7    r   r   r   r      sj         $	 	 	? ? ?6% 6% 6%p? ? ?0 0 0 0 0r   r   c                   *    e Zd ZdZd Zd Zd Zd ZdS )ScaledDPAlgorithmsa  Implement forward and backward algorithms using a rescaling approach.

    This scales the f and b variables, so that they remain within a
    manageable numerical interval during calculations. This approach is
    described in Durbin et al. on p 78.

    This approach is a little more straightforward then log transformation
    but may still give underflow errors for some types of models. In these
    cases, the LogDPAlgorithms class should be used.
    c                 L    t                               | ||           i | _        dS )a  Initialize the scaled approach to calculating probabilities.

        Arguments:
         - markov_model -- The current Markov model we are working with.
         - sequence -- A TrainingSequence object that must have a
           set of emissions to work with.

        N)r   r   	_s_valuesr	   s      r   r   zScaledDPAlgorithms.__init__   s'     	%%dL(CCCr   c                    | j         j        }d}|D ]v}| j         j        || j        j        |         f         }d}| j                             |          D ]+}|||dz
  f         }	| j         j        ||f         }
||	|
z  z  },|||z  z  }w|S )a  Calculate the next scaling variable for a sequence position (PRIVATE).

        This utilizes the approach of choosing s values such that the
        sum of all of the scaled f values is equal to 1.

        Arguments:
         - seq_pos -- The current position we are at in the sequence.
         - previous_vars -- All of the forward or backward variables
           calculated so far.

        Returns:
         - The calculated scaling variable for the sequence item.

        r   r   )r   r   emission_probr   r    transitions_fromr!   )r
   seq_posprevious_varsr"   s_valuer&   emissiontrans_and_var_sumsecond_state	var_valuetrans_values              r   _calculate_s_valuez%ScaledDPAlgorithms._calculate_s_value   s      / ' 	4 	4Jx-TY09:H
 !" $ 9 9* E E = =)<1*EF	 #h6j7QR!Y%<<!!x"333GGr   c                 f   || j         vr|                     ||          | j         |<   | j        j        |         }| j        j        ||f         }|| j         |         z  }d}d}| j                            |          D ]-}	d}||	|dz
  f         }
| j        j        |	|f         }||
|z  z  }.|r||z  S dS )aD  Calculate the value of the forward recursion (PRIVATE).

        Arguments:
         - cur_state -- The letter of the state we are calculating the
           forward variable for.
         - sequence_pos -- The position we are at in the training seq.
         - forward_vars -- The current set of forward variables

        r   r   N)r@   rL   r   r    r   rB   rC   r!   )r
   r   r   r   
seq_lettercur_emission_probscale_emission_probstate_pos_sumhave_transitionrI   prev_forwardcur_trans_probs               r   r   z%ScaledDPAlgorithms._forward_recursion   s     t~--+/+B+Bl, ,DN<(
 Y(6
 H2Iz3JK/$.2NN  H55i@@ 		; 		;LO (|a7G(HIL "X5|Y6OPN\N::MM  	&664r   c                 h   || j         vr|                     ||          | j         |<   d}d}| j                            |          D ]Y}d}| j        j        |dz            }| j        j        ||f         }|||dz   f         }	| j        j        ||f         }
|||	z  |
z  z  }Z|r|| j         |         z  S dS )aG  Calculate the value of the backward recursion (PRIVATE).

        Arguments:
         - cur_state -- The letter of the state we are calculating the
           forward variable for.
         - sequence_pos -- The position we are at in the training seq.
         - backward_vars -- The current set of backward variables

        r   r   N)r@   rL   r   rC   r   r    rB   r!   )r
   r   r   backward_varsrQ   rR   rI   rN   rO   prev_backwardcur_transition_probs              r   r.   z&ScaledDPAlgorithms._backward_recursion  s     t~--+/+B+Bm, ,DN<(
  H55i@@ 	U 	ULO,\A-=>J $ 6	:7N O *<9I*JKM #'(":I|;T"U.>ATTTMM  	 4>,#??? 4r   N)r8   r9   r:   r;   r   rL   r   r.   r<   r   r   r>   r>      s\        	 	  & & &P* * *X) ) ) ) )r   r>   c                       e Zd ZdZd ZdS )LogDPAlgorithmszImplement forward and backward algorithms using a log approach.

    This uses the approach of calculating the sum of log probabilities
    using a lookup table for common values.

    XXX This is not implemented yet!
    c                      t          d          )zInitialize the class.zHaven't coded this yet...r   r	   s      r   r   zLogDPAlgorithms.__init__M  r   r   N)r8   r9   r:   r;   r   r<   r   r   rZ   rZ   D  s-         ? ? ? ? ?r   rZ   )r;   warningsBior   warnr   r>   rZ   r<   r   r   <module>r_      s      + + + + + +    	  N N N N N N N NbV V V V V- V V Vr? ? ? ? ?* ? ? ? ? ?r   