• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

mmschlk / shapiq / 18495492809

14 Oct 2025 11:48AM UTC coverage: 93.524% (-0.3%) from 93.845%
18495492809

Pull #448

github

web-flow
Merge 51d18599d into 7891f9e4a
Pull Request #448: adapted release workflow

4925 of 5266 relevant lines covered (93.52%)

0.94 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

85.71
/src/shapiq/explainer/tabular.py
1
"""Tabular Explainer class for the shapiq package."""
2

3
from __future__ import annotations
1✔
4

5
from typing import TYPE_CHECKING, Any, Literal
1✔
6
from warnings import warn
1✔
7

8
from overrides import overrides
1✔
9

10
from shapiq.explainer.base import Explainer
1✔
11
from shapiq.game_theory.indices import is_empty_value_the_baseline
1✔
12

13
from .configuration import setup_approximator
1✔
14
from .custom_types import ExplainerIndices
1✔
15

16
if TYPE_CHECKING:
1✔
17
    import numpy as np
×
18

19
    from shapiq.approximator.base import Approximator
×
20
    from shapiq.imputer.base import Imputer
×
21
    from shapiq.interaction_values import InteractionValues
×
22
    from shapiq.typing import Model
×
23

24

25
TabularExplainerApproximators = Literal["spex", "montecarlo", "svarm", "permutation", "regression"]
1✔
26
TabularExplainerImputers = Literal["marginal", "baseline", "conditional"]
1✔
27
TabularExplainerIndices = ExplainerIndices
1✔
28

29

30
class TabularExplainer(Explainer):
1✔
31
    """The tabular explainer as the main interface for the shapiq package.
32

33
    The ``TabularExplainer`` class is the main interface for the ``shapiq`` package and tabular
34
    data. It can be used to explain the predictions of any model by estimating the Shapley
35
    interaction values.
36

37
    Attributes:
38
        index: Type of Shapley interaction index to use.
39
        data: A background data to use for the explainer.
40

41
    Properties:
42
        baseline_value: A baseline value of the explainer.
43

44
    """
45

46
    def __init__(
1✔
47
        self,
48
        model: Model,
49
        data: np.ndarray,
50
        *,
51
        class_index: int | None = None,
52
        imputer: Imputer | TabularExplainerImputers = "marginal",
53
        approximator: Literal["auto"] | TabularExplainerApproximators | Approximator = "auto",
54
        index: TabularExplainerIndices = "k-SII",
55
        max_order: int = 2,
56
        random_state: int | None = None,
57
        verbose: bool = False,
58
        **kwargs: Any,
59
    ) -> None:
60
        """Initializes the TabularExplainer.
61

62
        Args:
63
            model: The model to be explained as a callable function expecting data points as input
64
                and returning 1-dimensional predictions.
65

66
            data: A background dataset to be used for imputation.
67

68
            class_index: The class index of the model to explain. Defaults to ``None``, which will
69
                set the class index to ``1`` per default for classification models and is ignored
70
                for regression models.
71

72
            imputer: Either an :class:`~shapiq.games.imputer.Imputer` as implemented in the
73
                :mod:`~shapiq.games.imputer` module, or a literal string from
74
                ``["marginal", "baseline", "conditional"]``. Defaults to ``"marginal"``, which
75
                initializes the default
76
                :class:`~shapiq.games.imputer.marginal_imputer.MarginalImputer` with its default
77
                parameters or as provided in ``kwargs``.
78

79
            approximator: An :class:`~shapiq.approximator.Approximator` object to use for the
80
                explainer or a literal string from
81
                ``["auto", "spex", "montecarlo", "svarm", "permutation"]``. Defaults to ``"auto"``
82
                which will automatically choose the approximator based on the number of features and
83
                the desired index.
84
                    - for index ``"SV"``: :class:`~shapiq.approximator.KernelSHAP`
85
                    - for index ``"SII"`` or ``"k-SII"``: :class:`~shapiq.approximator.KernelSHAPIQ`
86
                    - for index ``"FSII"``: :class:`~shapiq.approximator.RegressionFSII`
87
                    - for index ``"FBII"``: :class:`~shapiq.approximator.RegressionFBII`
88
                    - for index ``"STII"``: :class:`~shapiq.approximator.SVARMIQ`
89

90
            index: The index to explain the model with. Defaults to ``"k-SII"`` which computes the
91
                k-Shapley Interaction Index. If ``max_order`` is set to 1, this corresponds to the
92
                Shapley value (``index="SV"``). Options are:
93
                    - ``"SV"``: Shapley value
94
                    - ``"k-SII"``: k-Shapley Interaction Index
95
                    - ``"FSII"``: Faithful Shapley Interaction Index
96
                    - ``"FBII"``: Faithful Banzhaf Interaction Index (becomes ``BV`` for order 1)
97
                    - ``"STII"``: Shapley Taylor Interaction Index
98
                    - ``"SII"``: Shapley Interaction Index
99

100
            max_order: The maximum interaction order to be computed. Defaults to ``2``. Set to
101
                ``1`` for no interactions (single feature importance).
102

103
            random_state: The random state to initialize Imputer and Approximator with. Defaults to
104
                ``None``.
105

106
            verbose: Whether to show a progress bar during the computation. Defaults to ``False``.
107

108
            **kwargs: Additional keyword-only arguments passed to the imputers implemented in
109
                :mod:`~shapiq.games.imputer`.
110
        """
111
        from shapiq.imputer import (
1✔
112
            BaselineImputer,
113
            ConditionalImputer,
114
            MarginalImputer,
115
            TabPFNImputer,
116
        )
117

118
        super().__init__(model, data, class_index, index=index, max_order=max_order)
1✔
119

120
        # get class for self
121
        class_name = self.__class__.__name__
1✔
122
        if self._model_type == "tabpfn" and class_name == "TabularExplainer":
1✔
123
            warn(
1✔
124
                "You are using a TabPFN model with the ``shapiq.TabularExplainer`` directly. This "
125
                "is not recommended as it uses missing value imputation and not contextualization. "
126
                "Consider using the ``shapiq.TabPFNExplainer`` instead. For more information see "
127
                "the documentation and the example notebooks.",
128
                stacklevel=2,
129
            )
130

131
        if imputer == "marginal":
1✔
132
            self.imputer = MarginalImputer(
1✔
133
                self.predict,
134
                self._data,
135
                random_state=random_state,
136
                **kwargs,
137
            )
138
        elif imputer == "conditional":
1✔
139
            self.imputer = ConditionalImputer(
1✔
140
                self.predict,
141
                self._data,
142
                random_state=random_state,
143
                **kwargs,
144
            )
145
        elif imputer == "baseline":
1✔
146
            self.imputer = BaselineImputer(
1✔
147
                self.predict,
148
                self._data,
149
                random_state=random_state,
150
                **kwargs,
151
            )
152
        elif isinstance(
1✔
153
            imputer, MarginalImputer | ConditionalImputer | BaselineImputer | TabPFNImputer
154
        ):
155
            self.imputer = imputer
1✔
156
        else:
157
            msg = (
×
158
                f"Invalid imputer {imputer}. "
159
                f'Must be one of ["marginal", "baseline", "conditional"], or a valid Imputer '
160
                f"object."
161
            )
162
            raise ValueError(msg)
×
163
        self._n_features: int = self._data.shape[1]
1✔
164
        self.imputer.verbose = verbose  # set the verbose flag for the imputer
1✔
165

166
        self.approximator = setup_approximator(
1✔
167
            approximator, self._index, self._max_order, self._n_features, random_state
168
        )
169

170
    @overrides
1✔
171
    def explain_function(
1✔
172
        self,
173
        x: np.ndarray,
174
        budget: int,
175
        *,
176
        random_state: int | None = None,
177
    ) -> InteractionValues:
178
        """Explains the model's predictions.
179

180
        Args:
181
            x: The data point to explain as a 2-dimensional array with shape
182
                (1, n_features).
183

184
            budget: The budget to use for the approximation. It indicates how many coalitions are
185
                sampled, thus high values indicate more accurate approximations, but induce higher
186
                computational costs.
187

188
            random_state: The random state to re-initialize Imputer and Approximator with.
189
                Defaults to ``None``, which will not set a random state.
190

191
        Returns:
192
            An object of class :class:`~shapiq.interaction_values.InteractionValues` containing
193
            the computed interaction values.
194
        """
195
        self.set_random_state(random_state)
1✔
196

197
        # initialize the imputer with the explanation point
198
        self.imputer.fit(x)
1✔
199

200
        # explain
201
        interaction_values = self.approximator(budget=budget, game=self.imputer)
1✔
202
        interaction_values.baseline_value = self.baseline_value
1✔
203
        # Adjust the Baseline Value if the empty value is the baseline
204
        if is_empty_value_the_baseline(interaction_values.index):
1✔
205
            interaction_values[()] = interaction_values.baseline_value
1✔
206
        return interaction_values
1✔
207

208
    @property
1✔
209
    def baseline_value(self) -> float:
1✔
210
        """Returns the baseline value of the explainer."""
211
        return self.imputer.empty_prediction
1✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc