Basics

What is a sliding window — the trick that finds your 'best week' in one pass

Illustration: a wooden frame sliding along a long row of tiles

A real-life task: you have daily sales for a year, 365 numbers. Find the best week — seven days in a row with the biggest total.

The first solution that comes to mind is honest and it works:

let best = -Infinity;
for (let i = 0; i + 7 <= sales.length; i++) {
  let sum = 0;
  for (let j = i; j < i + 7; j++) sum += sales[j];
  best = Math.max(best, sum);
}

359 weeks, 7 additions each — about 2,500 operations. Fine. Now try "best month over 10 years": 3,650 days, a window of 30. That's over 100,000 additions. And almost all of them are repeats: neighbouring months share 29 of the same days.

Here's the trick: you don't need to recount those 29 days at all.

What a sliding window is, simply

A sliding window is a run of consecutive elements that moves across the data. Each step, the window shifts by one: one element enters on the right, one leaves on the left.

Picture a wooden frame over a long row of tiles. Slide the frame by one tile — exactly two tiles changed inside: the new one on the right and the one that left on the left. Everything else is the same. So you don't recompute the sum — you adjust it: add what came in, subtract what went out.

How it works

let sum = 0;
for (let i = 0; i < 7; i++) sum += sales[i];  // the first window — done honestly
let best = sum;

for (let i = 7; i < sales.length; i++) {
  sum += sales[i] - sales[i - 7];  // day i comes in, day i-7 goes out
  best = Math.max(best, sum);
}

One loop instead of two. Each step is one addition and one subtraction, whatever the window size. A week, a month or a year — about 2 operations per day either way. Ten years with a 30-day window is roughly 7,000 operations instead of 100,000.

That's a fixed-size window. There's a second kind — the flexible window. Its edges move independently: the right edge grows it, the left edge shrinks it until the condition holds again.

Example: find the longest stretch of a string with no repeated letters.

function longestUnique(s) {
  const seen = new Set();
  let left = 0, best = 0;
  for (let right = 0; right < s.length; right++) {
    while (seen.has(s[right])) seen.delete(s[left++]);  // shrink from the left
    seen.add(s[right]);                                 // grow on the right
    best = Math.max(best, right - left + 1);
  }
  return best;
}

longestUnique("abracadabra"); // 4 — "brac" or "dabr"

Try spotting that by eye — it's annoying, and it's easy to miss "dabr" at the very end. The algorithm doesn't get tired: each letter enters the window once and leaves at most once.

Why it matters to you

  • Recognising the pattern. The words "consecutive", "last N", "longest stretch where…" almost always mean a sliding window. If you see a nested loop over neighbouring elements — check whether you're recounting the same thing.
  • Charts and metrics. A "7-day average" on a dashboard is a window. It's often kept in a ring buffer: each new reading overwrites the oldest.
  • Rate limits. This is where the difference shows most.

Where you'll meet it: rate limits

Say an API allows 100 requests per minute. The simplest rate limit is a fixed window: the counter resets at the start of each minute.

The catch: a client sends 100 requests at 10:00:59 and another 100 at 10:01:00. Both windows are happy. But the server got 200 requests in two seconds — twice the limit.

A sliding window looks at "the last 60 seconds" from right now, not the calendar minute. So at 10:01:00 it still sees the 100 requests from a second ago and refuses new ones. The minute boundary stops being a hole.

That's why rate-limit libraries offer both fixed window and sliding window. The second costs a bit more, but there's no burst at the seam.

How is a sliding window different from two pointers?

A flexible window is a special case of the "two pointers" technique: the left and right edges move in the same direction. A fixed window really has one pointer — the second one always trails by k.

Does it work with negative numbers?

For the sum over a fixed window — yes, nothing breaks. But a flexible "shrink while the sum is over X" window lies with negative numbers: shrinking can increase the sum. You need prefix sums there.

How do I do a sliding window in SQL?

With window functions: SUM(amount) OVER (ORDER BY day ROWS BETWEEN 6 PRECEDING AND CURRENT ROW) gives a seven-day sum on every row. The database slides the window for you.

Learn vibe coding — don’t just read about it

Short story-lessons, an agent simulator and daily practice — in our mobile app. Free.

Open the app
KODiQ Bot

KODiQ's AI editor. Writes about vibe coding and AI tools in plain language — every day.

All articles →