隐马尔可夫模型

隐马尔科夫模型(Hidden Markov Model,以下简称HMM)是比较经典的机器学习模型了,它在语言识别,自然语言处理,模式识别等领域得到广泛的应用。
当然,随着目前深度学习的崛起,尤其是RNN,LSTM等神经网络序列模型的火热,HMM的地位有所下降。

使用HMM模型时我们的问题一般有这两个特征:

1)我们的问题是基于序列的,比如时间序列,或者状态序列。

2)我们的问题中有两类数据,一类序列数据是可以观测到的,即观测序列;而另一类数据是不能观察到的,即隐藏状态序列,简称状态序列。

states = ('Healthy', 'Fever')
 
observations = ('normal', 'cold', 'dizzy')
 
start_probability = {'Healthy': 0.6, 'Fever': 0.4}
 
transition_probability = {
    'Healthy': {'Healthy': 0.7, 'Fever': 0.3},
    'Fever': {'Healthy': 0.4, 'Fever': 0.6},
}
 
emission_probability = {
    'Healthy': {'normal': 0.5, 'cold': 0.4, 'dizzy': 0.1},
    'Fever': {'normal': 0.1, 'cold': 0.3, 'dizzy': 0.6},
}

在这里插入图片描述

class HMM:

    def __init__(self, A, B, pi):
        self.A = A
        self.B = B
        self.pi = pi

    def generate_index_map(lables):
        index_label = {}
        label_index = {}
        i = 0
        for l in lables:
            index_label[i] = l
            label_index[l] = i
            i += 1
        return label_index, index_label

    states_label_index, states_index_label = generate_index_map(states)
    observations_label_index, observations_index_label = generate_index_map(observations)

    def convert_observations_to_index(observations, label_index):
        list = []
        for o in observations:
            list.append(label_index[o])
        return list

    def convert_map_to_vector(map, label_index):
        v = np.empty(len(map), dtype=float)
        for e in map:
            v[label_index[e]] = map[e]
        return v

    def convert_map_to_matrix(map, label_index1, label_index2):
        m = np.empty((len(label_index1), len(label_index2)), dtype=float)
        for line in map:
            for col in map[line]:
                m[label_index1[line]][label_index2[col]] = map[line][col]
        return m

    A = convert_map_to_matrix(transition_probability, states_label_index, states_label_index)
    B = convert_map_to_matrix(emission_probability, states_label_index, observations_label_index)
    observations_index = convert_observations_to_index(observations, observations_label_index)
    pi = convert_map_to_vector(start_probability, states_label_index)

HMM的三个问题
现在有几个问题:

       1,知道HMM的参数 λ = (A, B, π) 和观测序列O = {o1,o2, ..., oT} ,如何计算模型 λ 下观测序列O出现的概率P(O | λ)。

       2,HMM的参数如何确定?

             比如:对于刚才的中文分词的小例子。

                  初始概率分布π好确定:是不是终结词的概率各是0.5。

                  观测矩阵B也好确定:1/65535嘛

             但状态转移矩阵怎么确定?我怎么知道下个词是终结词的概率是多少?



       3,知道HMM的参数 λ = (A, B, π) 和观测序列O = {o1,o2, ..., oT},如何计算给定观测序列条件概率P(I|O,  λ )最大的状态序列I,即:

             对于中文分词,我想到底如何分的词。

  上面三个问题:

       第一个问题被称为:概率计算问题。

                 解决办法:前向-后向算法(一种动态规划算法)。

       第二个问题被称为:学习问题。

                 解决办法:如果状态序列已知,那用最大似然估计就好了,但HMM的状态序列未知,即含有隐变量,所以要使用Baum-welch算法(其实其本质就是EM算法)。

       第三个问题被称为:预测问题/解码问题。

                 解决办法:Viterbi算法(一种动态规划算法)。

概率计算问题
该问题有两种解决办法:
1,直接/暴力算法。2,前向算法/后向算法。

前向算法:

def _forward(self, obs_seq):
    N = self.A.shape[0]
    T = len(obs_seq)
 
    F = np.zeros((N,T))
    F[:,0] = self.pi * self.B[:, obs_seq[0]]
 
    for t in range(1, T):
        for n in range(N):
            F[n,t] = np.dot(F[:,t-1], (self.A[:,n])) * self.B[n, obs_seq[t]]
 
    return F

参考博客:https://blog.csdn.net/xueyingxue001/article/details/52396494?utm_medium=distribute.pc_relevant.none-task-blog-BlogCommendFromMachineLearnPai2-1.pc_relevant_is_cache&depth_1-utm_source=distribute.pc_relevant.none-task-blog-BlogCommendFromMachineLearnPai2-1.pc_relevant_is_cache

http://www.hankcs.com/ml/hidden-markov-model.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值