Permutation Importance: Score Drops: Fit on training rows, Shuffle validation columns, Compare repeated drops

Measure Held-Out Permutation Importance Without Refitting Your Model

Use scikit-learn to measure score drops after shuffling validation features, then interpret negative values, repeats and correlated inputs carefully.

Permutation importance asks a narrow question: how much does this fitted model’s score change when one input column is shuffled? Run it on held-out validation rows to examine reliance on features outside the training data. Do not refit the model after each shuffle: that would answer a different question about training with altered inputs.

The official scikit-learn inspection guide describes the method, its dependence on the chosen score and its limitations with correlated features. Importance is model-specific evidence, not proof that a feature causes an outcome.

Separate fitting, evaluation and inspection

Fit the estimator on training rows only, then evaluate it on validation rows before interpreting its importances. A poor model can ignore an informative input, so low importance does not establish that the input is intrinsically useless. First compare predictive performance with a sensible baseline; our DummyClassifier baseline tutorial explains that separate check for classification.

The example below uses generated regression data so it does not require personal records or a downloaded dataset. It creates one informative feature and three noise features, fits a Ridge model and inspects its validation predictions. Use a disposable environment with NumPy and scikit-learn installed, and save the Python block as a script.

Run the inspection on the same validation rows

import numpy as np
from sklearn.inspection import permutation_importance
from sklearn.linear_model import Ridge
from sklearn.model_selection import train_test_split

rng = np.random.default_rng(42)
X = rng.normal(size=(400, 4))
y = 5 * X[:, 0] + rng.normal(scale=0.5, size=400)
names = ["signal", "noise_a", "noise_b", "noise_c"]
X_train, X_val, y_train, y_val = train_test_split(
    X, y, test_size=0.3, random_state=42
)
model = Ridge(alpha=1.0).fit(X_train, y_train)
print(f"Validation R2: {model.score(X_val, y_val):.3f}")
result = permutation_importance(
    model, X_val, y_val, scoring="r2",
    n_repeats=20, random_state=42, n_jobs=1
)
for j in np.argsort(result.importances_mean)[::-1]:
    print(
        f"{names[j]}: drop={result.importances_mean[j]:.3f}, "
        f"repeat_sd={result.importances_std[j]:.3f}"
    )
assert result.importances_mean[0] == result.importances_mean.max()

The assertion checks a property of this deliberately constructed example; it is not a rule to apply to arbitrary datasets. The fixed seeds make the split and permutations reproducible for a given software environment. They do not establish stability across different samples, model choices or library versions.

Read the score drop in the correct units

For each feature, the method subtracts the average shuffled score from the original score. A positive result means the score fell when the column was shuffled. A value near zero means little change for this fitted model on these rows. A negative value means the shuffled score was better on average; it is not automatically a bug or proof of a harmful feature.

Here the scorer is R-squared, so the displayed drop is in score units, not a percentage of importance. Values need not sum to one. Avoid labelling a drop as a percentage of predictions explained. If you choose another scorer, interpret that scorer’s units and direction; do not compare raw magnitudes from unrelated metrics.

The reported standard deviation describes variation across repeated shuffles of this dataset. It is not a confidence interval for future populations, and twenty repeats do not create twenty independent validation datasets.

Handle correlations and leakage before deleting inputs

If two columns carry similar information, the model can still use one when the other is shuffled. Both can therefore receive modest individual importance despite being useful together. Inspect feature relationships and validate any proposed removal by retraining and evaluating a separate candidate model; do not delete columns solely because a sorted importance table places them last.

Shuffling also cannot repair data leakage. An input containing information from after the predicted event may look extremely important for the wrong reason. Respect time order, customer grouping and preprocessing boundaries when making the original split. For operational decisions, examine multiple appropriate splits and relevant subgroup performance rather than relying on one ranking.

Inspection checklist and short FAQ

  • Keep feature names in exactly the same order as the model inputs.
  • Record the validation score, metric, random seed and repeat count.
  • Retain an untouched final test set if validation findings guide model changes.
  • Inspect correlations and data timing before making feature-removal decisions.

Should I fit again inside the permutation loop? No. This method measures reliance of an already-fitted estimator.

Can I use training rows instead? The API allows it, but that does not establish contribution to unseen-data performance. Held-out rows better address the generalisation question.

This tutorial is for educational use. Test carefully before production use. The site owner is not responsible for misuse, damage, data loss or production issues. Keep sensitive datasets out of public notebooks and use approved local access controls.

Leave a Reply

Your email address will not be published. Required fields are marked *