← All cheatsheets
Data Scientist · #052 · September 13, 2026 · 1 min read

What is cross-validation and which KFold variant should you use?

Why one train/test split lies, the 5-fold loop, StratifiedKFold vs GroupKFold vs TimeSeriesSplit, and the leakage rule Pipeline solves for free: cross-validation on one page.

Get the free PDF

One page, print-ready, free to share. No signup needed.

Download the PDF

It scored 94% once. Your accuracy was one lucky split, and cross-validation is how you find out what the model actually does. One page. The print-ready A4 PDF is at the bottom.

Why

  • One split: one lucky draw.
  • k folds: k honest scores.
  • Report mean ± std, not the best fold.

The honest five lines

from sklearn.pipeline import make_pipeline
pipe = make_pipeline(StandardScaler(),
                     LogisticRegression())
scores = cross_val_score(pipe, X, y,
           cv=StratifiedKFold(5, shuffle=True))
print(scores.mean(), scores.std())

Scaling lives inside the pipeline, so every fold learns preprocessing from its own train side only. Scale before the split instead, and the test rows have already whispered their mean to the model.

Variants

  • StratifiedKFold: keeps the class ratio in every fold.
  • GroupKFold: the same user never lands on both sides.
  • TimeSeriesSplit: for anything dated.

Leakage

  • Scale inside the folds, never before the split.
  • Impute inside the folds too, same rule.
  • Pipeline() does it right for free.

Numbers

  • k = 5: the default.
  • k = 10: small datasets.
  • Leave-one-out: tiny data only.

The trap: the wrong splitter

Your dataPlain KFold doesUse
95/5 class imbalancefolds with zero positivesStratifiedKFold
many rows per usersame user on both sidesGroupKFold
timestampstrains on the futureTimeSeriesSplit

The GroupKFold one is the interview favorite: leaking a user across the split inflates scores and nobody notices until production.

Frequently asked questions

Why is one train/test split not enough?
Because the score depends on which rows landed in the test set: one split is one lucky (or unlucky) draw. K-fold cross-validation trains and tests k times on different partitions, giving k scores. Report the mean and the standard deviation, not the best fold: 0.81 ± 0.06 is an honest claim, 0.94 measured once is an anecdote.
When should you use StratifiedKFold, GroupKFold or TimeSeriesSplit?
StratifiedKFold when classes are imbalanced, so every fold keeps the class ratio and no fold ends up with zero positives. GroupKFold when several rows belong to the same user or entity, so the same user never appears on both sides of a split. TimeSeriesSplit for anything dated, so the model never trains on the future to predict the past.
How does cross-validation cause data leakage and how do you avoid it?
Leakage happens when preprocessing is fit on the full dataset before splitting: the scaler has already seen the test rows' statistics. Fit scaling, imputation and encoding inside each fold, on that fold's training side only. A sklearn Pipeline passed to cross_val_score does exactly that automatically.
How many folds should you use?
k=5 is the default trade-off between variance and compute. Go to k=10 on small datasets, and leave-one-out only on tiny ones. If the standard deviation across folds is huge, the finding is not the mean score, it is that the model is unstable.

Get the free PDF

One page, print-ready, free to share. No signup needed.

Download the PDF

More cheatsheets