diff --git a/api-reference.mdx b/api-reference.mdx index 471a08b..3ea7248 100644 --- a/api-reference.mdx +++ b/api-reference.mdx @@ -1,6 +1,6 @@ --- title: "API reference" -description: "Public FPDE classes, functions, parameters, and result objects" +description: "Reference for FPDE engine, prototype helpers, explanation functions, metrics, plotting helpers, and result objects exported from fpde." --- Import the public package as `fpde`. @@ -268,6 +268,172 @@ perturbation_curves( Computes deletion and insertion curves for one attribution vector. Features are ranked by signed positive attribution in descending order. +## Plotting helpers + +The plotting helpers are exported from `fpde` and visualize FPDE attributions, prototype similarities, and perturbation curves with matplotlib. +They require the optional `plot` extra: + +```bash +python -m pip install "fpde[plot]" +``` + +Each function returns the matplotlib `Axes` it draws on and does not call `plt.show()` or save files. +Pass an existing `ax=` to draw into a subplot, or omit it to create a new figure. + +### `plot_attributions` + +```python +plot_attributions( + attributions, + *, + feature_names=None, + top_k=20, + normalize=False, + sort=True, + ax=None, + title=None, +) +``` + +Plots a signed horizontal bar chart for a 1D attribution vector or an `FPDEExplanation`. +Positive values support the target class; negative values support the rival class. +Use `top_k` to limit the number of features and `normalize=True` to L1-normalize the displayed values. + +### `plot_attribution_waterfall` + +```python +plot_attribution_waterfall( + attributions, + *, + feature_names=None, + top_k=10, + base_value=0.0, + ax=None, + title=None, +) +``` + +Plots a cumulative local explanation from `base_value` to `base_value + sum(attributions)`. +Hidden features (outside `top_k`) are grouped into one `other features` bar. + +### `plot_attribution_summary` + +```python +plot_attribution_summary( + attributions, + *, + feature_values=None, + feature_names=None, + top_k=20, + ax=None, + title=None, + cmap="coolwarm", +) +``` + +Plots a batch attribution matrix as a per-feature distribution, ordered by mean absolute attribution. +Pass `feature_values` with the same shape as `attributions` to color points by the original feature value. + +### `plot_attribution_image` + +```python +plot_attribution_image( + attributions, + shape=None, + *, + ax=None, + title=None, + cmap="coolwarm", + colorbar=True, + symmetric=True, +) +``` + +Plots an attribution vector as a 2D heatmap. +Pass `shape=(height, width)` for flat image vectors; `shape` is optional for already-2D arrays. + +### `plot_perturbation_curves` + +```python +plot_perturbation_curves(curves, *, ax=None, title=None) +``` + +Plots the deletion and insertion probability curves returned by `perturbation_curves`. +`curves` must contain `fractions`, `deletion_prob`, and `insertion_prob`. + +### `plot_local_contributions` + +```python +plot_local_contributions( + feature_names, + contributions, + values=None, + *, + top_k=10, + sort_by="abs", + ax=None, + title=None, + xlabel="Contribution", + show_values=True, + zero_line=True, +) +``` + +Plots a signed local contribution bar chart from feature names and one attribution vector. +Pass `values` to label each bar with the corresponding feature value. + +### `prepare_local_contribution_data` + +```python +prepare_local_contribution_data( + feature_names, + contributions, + values=None, + *, + top_k=10, + sort_by="abs", +) +``` + +Returns a list of row dictionaries (`feature`, `display_name`, `contribution`, `abs_contribution`, `direction`, `direction_label`) suitable for rendering FPDE local attributions in a custom UI. + +### `plot_prototype_similarity_distribution` + +```python +plot_prototype_similarity_distribution( + X, + target_prototype, + *, + rival_prototype=None, + x=None, + metric="cosine", + bins=30, + ax=None, + title=None, +) +``` + +Plots the distribution of similarities from rows in `X` to the target prototype. +Pass `rival_prototype` to overlay the rival distribution and `x` to mark the explained sample. +`metric` is `"cosine"` or `"negative_euclidean"`. + +## `fpde.plots` namespace + +`fpde.plots` provides a compact matplotlib API for FPDE contribution arrays inspired by SHAP's plotting layout. +Pass `show=False` to receive an `Axes` without displaying, then save with `ax.figure.savefig(...)`. + +```python +from fpde.plots import FPDEPlotExplanation, bar, beeswarm, scatter, waterfall +``` + +| Function | Description | +| --- | --- | +| `FPDEPlotExplanation` | Lightweight container with `values`, `base_values`, `data`, `feature_names`, `output_names`, and `predictions`. | +| `bar` | Plots local or global contribution importance. A 1D vector is treated as one local explanation; a 2D matrix is summarized by feature importance. | +| `beeswarm` | Plots per-sample contributions grouped by feature. Points are colored by feature value when `data` is provided. | +| `scatter` | Plots one feature's original value against its FPDE contribution. `feature` may be an integer index or a name from `feature_names`. | +| `waterfall` | Plots one contribution vector from `base_value` to `prediction`. Hidden features are grouped into `other features`. | + ## Result objects | Object | Contains | diff --git a/examples.mdx b/examples.mdx index 65bde4d..3651efb 100644 --- a/examples.mdx +++ b/examples.mdx @@ -1,6 +1,6 @@ --- title: "Examples" -description: "Common FPDE usage patterns for single samples, batches, and lambda selection" +description: "FPDE usage patterns for single samples, batches, lambda selection, grid search, prototype helpers, and matplotlib visualization." --- Use `FPDEEngine` for most workflows. @@ -99,3 +99,111 @@ print(explanation.evidence) ``` For repeated work, prefer `FPDEEngine`. + +## Visualize explanations + +The plotting helpers exported from `fpde` and the compact `fpde.plots` namespace render FPDE attributions, prototype similarities, and perturbation curves with matplotlib. +Install the optional `plot` extra first: + +```bash +python -m pip install "fpde[plot]" +``` + +Each helper returns a matplotlib `Axes` you can save or arrange in a subplot. + +### Local attribution bar and waterfall + +Use `plot_attributions` for a signed bar chart of one explanation, and `plot_attribution_waterfall` for a cumulative view. + +```python +from fpde import plot_attributions, plot_attribution_waterfall + +attributions, details = engine.explain_one(X_test[0], lambda_hyb=0.5) + +plot_attributions( + attributions, + feature_names=feature_names, + top_k=10, + title="Top FPDE contributions", +) + +plot_attribution_waterfall( + attributions, + feature_names=feature_names, + title="Cumulative FPDE evidence", +) +``` + +### Batch summary with `beeswarm` + +Use `fpde.plots.beeswarm` to summarize per-sample contributions across a batch, colored by feature value. + +```python +from fpde.plots import FPDEPlotExplanation, beeswarm + +batch_attributions = engine.explain_matrix(X_test[:50], lambda_hyb=0.5) +plot_exp = FPDEPlotExplanation( + values=batch_attributions, + data=X_test[:50], + feature_names=feature_names, +) + +ax = beeswarm(plot_exp, show=False, title="FPDE contribution summary") +ax.figure.savefig("fpde_beeswarm.png", dpi=150, bbox_inches="tight") +``` + +### Prototype similarity distribution + +Use `plot_prototype_similarity_distribution` to see how the explained sample sits between the target and rival prototypes. + +```python +import numpy as np +from fpde import plot_prototype_similarity_distribution + +target_idx = np.where(engine.prototype_labels == details["target_label"])[0][0] +rival_idx = np.where(engine.prototype_labels == details["rival_label"])[0][0] + +plot_prototype_similarity_distribution( + X_train, + target_prototype=engine.prototypes[target_idx], + rival_prototype=engine.prototypes[rival_idx], + x=X_test[0], + title="Prototype similarity distribution", +) +``` + +### Attribution heatmap for image features + +When features form an image, reshape the attribution vector with `plot_attribution_image`. + +```python +from fpde import plot_attribution_image + +plot_attribution_image( + attributions, + shape=(28, 28), + title="FPDE pixel attributions", +) +``` + +### Perturbation curves + +After computing deletion and insertion curves, visualize them with `plot_perturbation_curves`. + +```python +from fpde import perturbation_curves, plot_perturbation_curves + +curves = perturbation_curves( + model, + X_test[0], + attributions, + details["target_label"], + baseline=engine.baseline, +) + +plot_perturbation_curves(curves, title="Deletion vs. insertion") +``` + +### Full notebook + +For an end-to-end walkthrough covering bar, waterfall, beeswarm, similarity, image, and perturbation plots on the breast cancer dataset, see [`examples/plot_fpde_example.ipynb`](https://github.com/fpde-xai/fpde/blob/main/examples/plot_fpde_example.ipynb) in the FPDE repository. diff --git a/index.mdx b/index.mdx index f7e459d..d0894ec 100644 --- a/index.mdx +++ b/index.mdx @@ -1,6 +1,6 @@ --- title: "Introduction" -description: "Explain classification results with prototype-contrast feature attribution" +description: "FPDE is a Python package for prototype-contrast feature attribution that explains scikit-learn classifiers with per-feature contributions." --- Feature Prototype Direction Explainer (FPDE) is a Python package for prototype-contrast feature attribution. @@ -17,6 +17,7 @@ Use FPDE when you need a lightweight, post-hoc explanation method for tabular-st - Search Diff, Cos, and Hyb-FPDE candidate settings. - Select `lambda_hyb` with held-out deletion and insertion validation. - Compute deletion and insertion perturbation curves for an attribution vector. +- Plot attribution bars, cumulative waterfalls, contribution summaries, attribution heatmaps, prototype similarity distributions, and perturbation curves. ## How FPDE explains a prediction @@ -52,6 +53,12 @@ The package depends on NumPy and scikit-learn. python -m pip install fpde ``` +To use the plotting helpers, install the optional `plot` extra, which adds matplotlib: + +```bash +python -m pip install "fpde[plot]" +``` + ## Project links - [Repository](https://github.com/fpde-xai/fpde) diff --git a/quickstart.mdx b/quickstart.mdx index 99f7e58..54c1b1c 100644 --- a/quickstart.mdx +++ b/quickstart.mdx @@ -1,6 +1,6 @@ --- title: "Quickstart" -description: "Install FPDE and explain one scikit-learn classification result" +description: "Install FPDE from PyPI, fit an engine on training data, and explain one scikit-learn classifier prediction with Hyb-FPDE attributions." --- This guide trains a scikit-learn classifier, fits an FPDE engine on the training data, and explains one test sample. @@ -24,6 +24,12 @@ Before you begin, install: ```bash python -m pip install fpde ``` + + To use the optional plotting helpers, install the `plot` extra, which adds matplotlib: + + ```bash + python -m pip install "fpde[plot]" + ``` Train a classifier on the same feature space you want to explain.