Skip to content

Commit 7811d67

Browse files
committed
Add effective sample size to Population
1 parent 7e02c91 commit 7811d67

File tree

1 file changed

+27
-0
lines changed

1 file changed

+27
-0
lines changed

src/Control/Monad/Bayes/Population.hs

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,8 @@ module Control.Monad.Bayes.Population
2626
resampleSystematic,
2727
stratified,
2828
resampleStratified,
29+
onlyBelowEffectiveSampleSize,
30+
effectiveSampleSize,
2931
extractEvidence,
3032
pushEvidence,
3133
proper,
@@ -206,6 +208,31 @@ resampleMultinomial ::
206208
PopulationT m a
207209
resampleMultinomial = resampleGeneric multinomial
208210

211+
-- | Only use the given resampler when the effective sample size is below a certain threshold
212+
onlyBelowEffectiveSampleSize ::
213+
(MonadDistribution m) =>
214+
-- | The threshold under which the effective sample size must fall before the resampler is used.
215+
-- For example, this may be half of the number of particles.
216+
Double ->
217+
-- | The resampler to user under the threshold
218+
((MonadDistribution m) => PopulationT m a -> PopulationT m a) ->
219+
-- | The new resampler
220+
(PopulationT m a -> PopulationT m a)
221+
onlyBelowEffectiveSampleSize threshold resampler pop = do
222+
ess <- lift $ effectiveSampleSize pop
223+
if ess < threshold then resampler pop else pop
224+
225+
-- | Compute the effective sample size of a population from the weights.
226+
--
227+
-- See https://en.wikipedia.org/wiki/Design_effect#Effective_sample_size
228+
effectiveSampleSize :: (Functor m) => PopulationT m a -> m Double
229+
effectiveSampleSize = fmap (effectiveSampleSizeKish . map (exp . ln . snd)) . runPopulationT
230+
where
231+
effectiveSampleSizeKish :: [Double] -> Double
232+
effectiveSampleSizeKish weights = square (Data.List.sum weights) / Data.List.sum (square <$> weights)
233+
square :: Double -> Double
234+
square x = x * x
235+
209236
-- | Separate the sum of weights into the 'WeightedT' transformer.
210237
-- Weights are normalized after this operation.
211238
extractEvidence ::

0 commit comments

Comments
 (0)