这个问题可能很简单,但我从卡尔曼滤波器得到了一个奇怪的结果。让我们考虑最简单的状态空间模型,即随机游走加噪声:
在 Python 中使用 Kalman EM,我尝试估计转换和观察方差。
首先,我想估计“observation_covariance”并假设“transition_covariance”是已知的:
kf = KalmanFilter(
transition_matrices=[1.], observation_matrices=Data['x'],
transition_covariance=[1.], initial_state_mean=3,
initial_state_covariance=[1.],
em_vars=['observation_covariance']
)
kf = kf.em(Data['y'])
结果是.
其次,我做相反的事情,即我估计“transition_covariance”并假设“observation_covariance”是已知的:
kf = KalmanFilter(
transition_matrices=[1.], observation_matrices=Data['x'],
observation_covariance=[1.], initial_state_mean=3,
initial_state_covariance=[1.],
em_vars=['transition_covariance']
)
kf = kf.em(Data['y'])
结果是,这远非!
接下来,我假设“transition_covariance”和“observation_covariance”都是未知的:
kf = KalmanFilter(
transition_matrices=[1.], observation_matrices=Data['x'],
initial_state_mean=3, initial_state_covariance=[1.],
em_vars=['transition_covariance', 'observation_covariance']
)
kf = kf.em(Data['y'])
结果是“observation_covariance”= 0.77 和“transition_covariance”= 0.0002。
我做错了什么?那些估计的方差不应该接近吗?
我使用的所有代码如下:
#%%
import pandas as pd
import scipy as sp
import numpy as np
import matplotlib.pyplot as plt
import pylab as pl
from pykalman import KalmanFilter
N_data = 3000
Data = pd.DataFrame(columns=['NoiseTrs', 'NoiseObs', 'x', 'y'], index=range(N_data))
Data['NoiseTrs'] = np.random.normal(loc=0.0, scale=1.0, size=N_data)
Data['NoiseObs'] = np.random.normal(loc=0.0, scale=1.0, size=N_data)
# random walk
x_f_v = 3 # first value for the simulation
for i in range(N_data):
if i == 0:
Data.loc[i, 'x'] = x_f_v
else:
Data.loc[i, 'x'] = Data.loc[i - 1, 'x'] + Data.loc[i, 'NoiseTrs']
# plt.plot(Data['x'])
# plt.show()
Data['y'] = Data['x'] + Data['NoiseObs']
# plt.plot(Data[['x', 'y']])
# plt.show()
F = [1.] # transition matrix
H = Data['x'].values.reshape(N_data,1,1).astype(float) # observation matrix
Q = [1.] # transition noise
R = [1.] # observation noise
#%%
init_state_mean = [3.]
init_state_cov = [1.]
kf = KalmanFilter(
transition_matrices=F,
observation_matrices=H,
# transition_covariance=Q,
# observation_covariance=R,
initial_state_mean=init_state_mean,
initial_state_covariance=init_state_cov,
em_vars=['transition_covariance', 'observation_covariance']
# em_vars=['observation_covariance']
# em_vars=['transition_covariance']
)
kf = kf.em(Data['y'].values.astype(float))
print("observation_covariance R :", kf.observation_covariance)
print("transition_covariance Q :", kf.transition_covariance)
```