CountsOutlierDetector (COD) detects outliers with multidimensional histograms while keeping explanations readable. Instead of analyzing every feature simultaneously, it examines feature subspaces up to six dimensions, avoiding sparsity and interpretability problems associated with high-dimensional histograms. section 13.3.3
COD’s detection logic emphasizes limited subspaces and count-based interpretation:
- Analyzes one-feature subspaces, then pairs, triples, and progressively larger subspaces through six dimensions. section 13.3.3
- Declines to examine dimensionalities that lack enough records to support reliable analysis. section 13.3.3
- Uses histogram-bin counts to identify sparse combinations; a low Height with a high Diameter, for example, can be described directly. section 13.3.3
- Bridges univariate detectors and all-feature multivariate detectors, while accepting that rare high-dimensional patterns may remain undetected. section 13.3.3 section 15.2.2
Abalone and KDD Cup applications
On the abalone data, COD can be configured with three bins, a six-dimensional maximum, and a threshold, then run with fit_predict. get_most_flagged_rows identifies prominent records, while explain_row shows the sparse subspaces contributing to a score. A two-dimensional explanation can place a row in a sparse Diameter–Viscera_weight cell; a three-dimensional explanation can similarly expose unusual combinations. On the KDD Cup data, COD provides an interpretable multivariate comparison for the row receiving the highest Isolation Forest score, including a pair whose values are individually common but jointly occurred only 18 times. section 13.3.3 section 15.2.2
Listing 13.12 Executing COD on the abalone dataset
import pandas as pd
import numpy as np
from sklearn.datasets import fetch_openml
data = fetch_openml('abalone', version=1, parser='auto') #1
df = pd.DataFrame(data.data, columns=data.feature_names)
print(df.head())
det = CountsOutlierDetector(n_bins=3, max_dimensions=6, threshold=0.25,
verbose=True) #2
results = det.fit_predict(df)
print(det.get_most_flagged_rows().head()) #3
most_flagged = int(det.get_most_flagged_rows().index[0])
det.explain_row(most_flagged) #4
Use the executable abalone example to inspect configuration, prediction, ranking, and row-level explanation. section 13.3.3
