Conversation
The Stats module covers all moving/expanding statistics (count, sum, mean,
variance, stdDev, skew, kurt, min, max) but was missing median. This adds
Stats.movingMedian and Stats.expandingMedian to fill the gap.
Implementation uses a simple circular-buffer O(n*k log k) approach: for each
window position the window contents are sorted and the median is computed.
This is straightforward and correct for typical window sizes.
Also removes a stale TODO comment ('still to do: median, percentile') since
both median and quantile/percentile are already implemented.
Co-authored-by: Copilot <[email protected]>
9 tasks
dsyme
approved these changes
Mar 19, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
🤖 Repo Assist — filling a gap in the Stats moving/expanding window API.
Summary
The
Statsmodule provides a comprehensive set of moving and expanding window statistics — count, sum, mean, variance, stdDev, skew, kurt, min, max — but was missing median. This PR adds:Stats.movingMedian : int -> Series<'K,'V> -> Series<'K,float>— median over a rolling windowStats.expandingMedian : Series<'K,'V> -> Series<'K,float>— cumulative median over an expanding windowBoth functions follow the same conventions as the existing moving/expanding stats functions: they handle missing values, accept any numeric value type (via
toFloatconversion), and skip non-numeric/NaN values within the window.Implementation
A circular-buffer approach: for each window position the non-missing values are collected and sorted, and the median is computed. This is O(n·k log k) per series where k is the window size — straightforward and correct for typical use cases. No new dependencies are required.
For
movingMedian, the firstsize-1elements areMissing(incomplete window), consistent withmovingMean,movingVariance, etc.For
expandingMedian, all positions are present (using 1-element through full window), consistent withexpandingMean,expandingMin, etc.Also removes a stale
// TODO: still to do, possibly: median, percentilecomment (both were already implemented).Tests
Four new tests are added to
tests/Deedle.Tests/Stats.fs, following the same pattern as existing moving/expanding tests:Moving median works— sum of windowed medians matches oracle values for series with NaN, float, and intMoving median - first size-1 values are missing— confirms missing value count for incomplete window headExpanding median works— sum of cumulative medians matches oracle valuesTest Status
✅ All 68 Stats tests pass (
dotnet test tests/Deedle.Tests/Deedle.Tests.fsproj --filter "FullyQualifiedName~Stats")✅
dotnet build src/Deedle/Deedle.fsproj -c Release— 0 errors, 4 pre-existing warnings