When the state-space model is not linear-Gaussian, the posterior p(zn|Xn) has no closed form. A particle filter represents it by L samples with weights wn(l) ∝ p(xn|zn(l)). To move to the next step it draws L new particles from the mixture Σl wn(l) p(zn+1|zn(l)) (pick a parent by its weight, then move it by the dynamics) and weights them by the new observation. The lower left panel shows one such step, as in Figure 13.23 of Bishop (2006).
Linear-Gaussian model: zn = 0.95 zn−1 + N(0, 0.5), xn = zn + noise, z1 ~ N(0, 1); here the Kalman filter is exact. Nonlinear growth model (Kitagawa 1996; Gordon, Salmond and Smith 1993): zn = z/2 + 25z/(1 + z2) + 8 cos(1.2n) + N(0, 10) with z = zn−1, xn = zn2/20 + noise, z1 ~ N(0, 5); since x depends on z2, p(x|z) has two bumps at ±√(20x) (green ticks in the top panel). 50 time steps; seeded random numbers, so a class sees the same pictures.
code/ch13_sequential_data.py (functions pf_simulate, particle_filter, pf_kalman; Figure 13.23) and the checks in code/checks_ch13.py. Passing JSRandom(seed) reproduces this page's data and particles; preset 1 is panel (a) of our Figure 13.23.