《机器学习》 周志华学习笔记第十四章 概率图模型(课后习题)python实现
时间: 2023-06-20 14:09:26 浏览: 121
周志华《机器学习》课后习题的编程答案及数据集,纯python实现未使用框架,阅读起来更容易理解算法.zip
很好,以下是第十四章的部分习题python实现:
14.1 腐蚀图像分割
```python
import numpy as np
import matplotlib.pyplot as plt
from scipy.misc import ascent
from scipy.ndimage import grey_erosion
img = ascent() # 载入一张灰度图像
selem = np.ones((50,50)) # 定义一个50x50的结构元素
eroded = grey_erosion(img, footprint=selem) # 使用结构元素进行腐蚀操作
# 显示原图和腐蚀后的图像
fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 4))
ax = axes.ravel()
ax[0].imshow(img, cmap=plt.cm.gray)
ax[0].set_title('Original image')
ax[1].imshow(eroded, cmap=plt.cm.gray)
ax[1].set_title('Eroded image')
plt.show()
```
14.2 高斯混合模型
```python
import numpy as np
from scipy.stats import norm
class GMM:
def __init__(self, n_components, max_iter=100, tol=1e-6):
self.n_components = n_components
self.max_iter = max_iter
self.tol = tol
def fit(self, X):
n_samples, n_features = X.shape
# 初始化参数
self.weights = np.ones(self.n_components) / self.n_components
self.means = X[np.random.choice(n_samples, self.n_components, replace=False)]
self.covs = [np.eye(n_features) for _ in range(self.n_components)]
for i in range(self.max_iter):
# E步,计算每个样本在各分模型下的后验概率
probs = np.zeros((n_samples, self.n_components))
for j in range(self.n_components):
probs[:, j] = self.weights[j] * norm.pdf(X, self.means[j], self.covs[j])
probs /= probs.sum(axis=1, keepdims=True)
# M步,更新参数
weights_new = probs.mean(axis=0)
means_new = np.dot(probs.T, X) / probs.sum(axis=0, keepdims=True).T
covs_new = []
for j in range(self.n_components):
diff = X - means_new[j]
cov_new = np.dot(probs[:, j] * diff.T, diff) / probs[:, j].sum()
covs_new.append(cov_new)
self.weights = weights_new
self.means = means_new
self.covs = covs_new
# 判断收敛
if np.abs(weights_new - self.weights).max() < self.tol \
and np.abs(means_new - self.means).max() < self.tol \
and np.abs(covs_new - self.covs).max() < self.tol:
break
def predict(self, X):
probs = np.zeros((X.shape[0], self.n_components))
for j in range(self.n_components):
probs[:, j] = self.weights[j] * norm.pdf(X, self.means[j], self.covs[j])
return probs.argmax(axis=1)
```
14.3 隐马尔可夫模型
```python
import numpy as np
class HMM:
def __init__(self, n_states, n_features):
self.n_states = n_states
self.n_features = n_features
def fit(self, X, max_iter=100, tol=1e-6):
n_samples = len(X)
# 初始化参数
self.pi = np.ones(self.n_states) / self.n_states
self.A = np.ones((self.n_states, self.n_states)) / self.n_states
self.B = np.ones((self.n_states, self.n_features)) / self.n_features
for i in range(max_iter):
# E步,计算前向概率和后向概率
alpha = np.zeros((n_samples, self.n_states))
beta = np.zeros((n_samples, self.n_states))
alpha[0] = self.pi * self.B[:, X[0]]
for t in range(1, n_samples):
alpha[t] = np.dot(alpha[t-1], self.A) * self.B[:, X[t]]
beta[-1] = 1
for t in range(n_samples-2, -1, -1):
beta[t] = np.dot(self.A, self.B[:, X[t+1]] * beta[t+1])
gamma = alpha * beta / alpha[-1].sum()
# M步,更新参数
self.pi = gamma[0]
self.A = np.dot(gamma[:-1].T, self.A * self.B[:, X[1:]] * beta[1:]) / gamma[:-1].sum(axis=0).reshape(-1, 1)
self.B = np.zeros((self.n_states, self.n_features))
for k in range(self.n_features):
mask = X == k
self.B[:, k] = gamma[mask].sum(axis=0) / gamma.sum(axis=0)
# 判断收敛
if np.abs(alpha[-1].sum() - 1) < tol:
break
def predict(self, X):
alpha = np.zeros((len(X), self.n_states))
alpha[0] = self.pi * self.B[:, X[0]]
for t in range(1, len(X)):
alpha[t] = np.dot(alpha[t-1], self.A) * self.B[:, X[t]]
return alpha[-1].argmax()
```
以上是部分习题的python实现,希望对你有所帮助。
阅读全文