zoukankan      html  css  js  c++  java
  • HMM 前向后向算法(转)

    最近研究NLP颇感兴趣,但由于比较懒,所以只好找来网上别人的比较好的博客,备份一下,也方便自己以后方便查找(其实,一般是不会再回过头来看的,嘿嘿 -_-!!)

    代码自己重新写了一遍,所以就不把原文代码贴过来了。

    1. 前向算法(摘自http://www.cnblogs.com/kaituorensheng/archive/2012/12/01/2797230.html)

    隐马模型的评估问题即,在已知一个观察序列O=O1O2...OT,和模型μ=(A,B,π}的条件下,观察序列O的概率,即P(O|μ}

                       

          如果穷尽所有的状态组合,即S1S1...S1, S1S1...S2, S1S1...S3, ..., S3S3...S3。这样的话t1时刻有N个状态,t2时刻有N个状态...tT时刻有N个状态,这样的话一共有N*N*...*N= NT种组合,时间复杂度为O(NT),计算时,就会出现“指数爆炸”,当T很大时,简直无法计算这个值。为解决这一问题,Baum提出了前向算法。

          归纳过程

          首先引入前向变量αt(i):在时间t时刻,HMM输出序列为O1O2...OT,在第t时刻位于状态si的概率。

          当T=1时,输出序列为O1,此时计算概率为P(O1|μ):假设有三个状态(如下图)1、2、3,输出序列为O1,有三种可能一是状态1发出,二是从状态2发出,三是从状态3发出。另外从状态1发出观察值O1得概率为b1(O1),从状态2发出观察值O1得概率为b2(O1),从状态3发出观察值O1得概率为b3(O1)。因此可以算出

         P(O1|μ)= π1*b1(O1)+π2*b2(O1) +  π3*b3(O1)= α1(1) + α1(2) + α1(3)

                                         

          当T=2时,输出序列为O1O2,此时计算概率为P(O1O2|μ):假设有三个状态(如下图)1、2、3,输出序列为O1,有三种可能一是状态1发出,二是从状态2发出,三是从状态3发出。另外从状态1发出观察值O2得概率为b1(O2),从状态2发出观察值O2得概率为b2(O2),从状态3发出观察值O2得概率为b3(O2)。

          要是从状态1发出观察值O2,可能从第一时刻的1、2或3状态装换过来,要是从状态1转换过来,概率为α1(1)*a11*b1(O2),要是从状态2转换过来,概率为α1(2)*a21*b1(O2),要是从状态3转换过来,概率为α1(3)*a31*b1(O2),因此

         P(O1O2,q2=s1|μ)= α1(1)*a11*b1(O2)  + α1(2)*a21*b1(O2) + α1(3)*a31*b1(O2)=α2(1)

                                         

          同理:P(O1O2,q2=s1|μ)= α1(1)*a12*b2(O2)  + α1(2)*a22*b2(O2) + α1(3)*a32*b2(O2)=α2(2)

                   P(O1O2,q2=s1|μ)= α1(1)*a13*b1(O2)  + α1(2)*a23*b3(O2) + α1(3)*a33*b3(O2)=α2(3)

         所以:P(O1O2|μ)=P(O1O2,q2=s1|μ)+ P(O1O2,q2=s1|μ)+ P(O1O2,q2=s1|μ)

                                 =α2(1) + α2(2) + α2(3)

          以此类推。。。

          前向算法

           step1 初始化:α1(i) = πi*bi(O1), 1≤i≤N

           step2 归纳计算:

                               

           step3 终结:

                          P(O|μ)=

          时间复杂度

          计算某时刻的某个状态的前向变量需要看前一时刻的N个状态,此时时间复杂度为O(N),每个时刻有N个状态,此时时间复杂度为N*O(N)=O(N2),又有T个时刻,所以时间复杂度为T*O(N2)=O(N2T)。

          程序例证

           

            前向算法计算P(O|M):

            step1:α1(1) =π1*b1(red)=0.2*0.5=0.1          α1(2)=π2*b2(red)==0.4*0.4= 0.16          α1(3)=π3*b3(red)==0.4*0.7=0.21

            step2:α2(1)=α1(1)*a11*b1(white) + α1(2)*a21*b1(white) + α1(3)*a31*b1(white)

                         ...

            step3:P(O|M) = α3(1)+α3(2)+α3(3)

    2. 后向算法(摘自http://www.cnblogs.com/kaituorensheng/archive/2012/12/03/2800489.html)

    对于HMM的评估问题,利用动态规划可以用前向算法,从前到后算出前向变量;也可以采用后向算法,从后到前算出后向变量。

    先介绍后向变量βt(i):给定模型μ=(A,B,π),并且在时间 时刻t 状态为s的前提下,输出序列为Ot+1Ot+2...OT的概率,即

                                        βt(i)=P(Ot+1Ot+2...OT|qt=si,μ)

    归纳过程

        假设仍然有3个状态

                      

        当t=T时,按照定义:时间t  状态q输出为OT+1......的概率,从T+1开始的输出是不存在的(因为T时刻是终止终止状态),即T之后是空,是个必然事件,因此βt(i)=1,1≤1≤N

        当t=T-1时,

                              

                     βT-1(i)=P(OT|qT-1=si,μ) = ai1*b1(OT)*βT(1)  +  ai2*b2(OT)*βT(2)  +  ai3*b3(OT)*βT(3)

          ......

        当t=1时,

           β1(1)=P(O2O3...OT|q2=s1,μ) = a11*b1(O2)*β2(1) + a12*b2(O2)*β2(2) + a13*b3(O2)*β2(3)

           β1(2)=P(O2O3...OT|q2=s1,μ) = a21*b1(O2)*β2(1) + a22*b2(O2)*β2(2) + a23*b3(O2)*β2(3)

           β1(3)=P(O2O3...OT|q2=s1,μ) = a31*b1(O2)*β2(1) + a32*b2(O2)*β2(2) + a33*b3(O2)*β2(3)

           P(O1O2...OT|μ) =    

                                 =   

                                 =  

    后向算法

        step1 初始化:βT(i)=1, 1≤1≤N

        step2 归纳计算:

                           1≤t≤T-1, 1≤i≤N

        step3 求终结和:

                       P(O|μ)=  

    时间复杂度

        计算某时刻在某个状态下的后向变量需要看后一时刻的N个状态,此时时间复杂度为O(N),每个时刻有N个状态,此时时间复杂度为N*O(N)=O(N2),又有T个时刻,所以时间复杂度为T*O(N2)=O(N2T)。

    程序例证

                  

    后向算法

        计算P(O|M):

        step1:β4(1) = 1          β4(2) = 1          β4(3) = 1

        step2:β3(1) = β4(1)*a11*b1(white) + β4(2)*a12*b2(white) + β4(3)*a13*b3(white)

                         ...

        step3:P(O|M) = π11(1)*b1(O1) + π21(2)*b2(O1) + π31(3)*b3(O1)

    3.前向-后向算法(摘自http://www.cnblogs.com/kaituorensheng/archive/2012/12/05/2803182.html)

    重新回顾:

        前向变量αt(i):在时刻t,在已知模型μ=(A,B,π)的条件下,状态处于si,输出序列为O102...Ot,前向变量为αt(i)

        后向变量βt(i):在时刻t,在已知模型μ=(A,B,π)和状态处于si的条件下,输出序列为Ot+1Ot+2...OT,后向变量为βt(i)

    公式推导:

        P(O,qt=si|μ) = P(O1O2...OT, qt=si|μ)

                             =P(O1O2...Ot, qt=si,Ot+1Ot+2...OT|μ)

                             =P(O1O2...Ot, qt=si|μ) * P(Ot+1Ot+2...OT|O1O2...Ot, qt=si,μ)

                             =P(O1O2...Ot, qt=si|μ) * P(Ot+1Ot+2...OT|qt=si,μ)

                             =αt(i) *  βt(i)

         P(O|μ)=

    案例分析:

        

          分析:

            P(q4=s3|O,M) =  P(q4=s3, O|M)/P(O|M)

                                = P(O,q4=s3|M)/P(O|M)

                                = α4(3) *  β4(3)/  

  • 相关阅读:
    在SQLite中使用索引优化查询速度
    SQLite支持的SQL数据操作
    left (outer) join , right (outer) join, full (outer) join, (inner) join, cross join 区别
    深入理解Android内存管理原理(六)
    Merge Sorted Array
    Sort Colors
    Construct Binary Tree from Preorder and Inorder Traversal
    Binary Tree Postorder Traversal
    Symmetric Tree
    Rotate Image
  • 原文地址:https://www.cnblogs.com/sjjsxl/p/6285629.html
Copyright © 2011-2022 走看看