def __init__(self, classifier: "CLASSIFIER_TYPE", num_neurons: int | None = None) -> None:
        """
        Create a `FunctionallyEquivalentExtraction` instance.

        :param classifier: A trained ART classifier.
        :param num_neurons: The number of neurons in the first dense layer.
        """
        super().__init__(estimator=classifier)
        self.num_neurons = num_neurons
        self.num_classes = classifier.nb_classes
        self.num_features = int(np.prod(classifier.input_shape))

        self.vector_u = np.random.normal(0, 1, (1, self.num_features)).astype(dtype=NUMPY_DTYPE)
        self.vector_v = np.random.normal(0, 1, (1, self.num_features)).astype(dtype=NUMPY_DTYPE)

        self.critical_points: list[np.ndarray] = []

        self.w_0: np.ndarray | None = None  # Weight matrix of first dense layer
        self.b_0: np.ndarray | None = None  # Bias vector of first dense layer
        self.w_1: np.ndarray | None = None  # Weight matrix of second dense layer
        self.b_1: np.ndarray | None = None  # Bias vector of second dense layer

        Create a `FunctionallyEquivalentExtraction` instance.

        :param classifier: A trained ART classifier.
        :param num_neurons: The number of neurons in the first dense layer.
        
art/attacks/extraction/functionally_equivalent_extraction.py