Skip to content

Instantly share code, notes, and snippets.

@Guillermogsjc
Created February 6, 2019 16:45
Show Gist options
  • Save Guillermogsjc/19c290a209f9795219c3c9613d9b2334 to your computer and use it in GitHub Desktop.
Save Guillermogsjc/19c290a209f9795219c3c9613d9b2334 to your computer and use it in GitHub Desktop.
Scikit-learn KernelPCA override to solve gamma hyperparameter ambiguation
from sklearn.decomposition import KernelPCA
from sklearn.metrics.pairwise import pairwise_kernels
import numpy as np
from scipy import linalg
class OverrideKernelPCA(KernelPCA):
""" Trying to solve the issue with an override
https://github.com/scikit-learn/scikit-learn/issues/13099"""
def __init__(self, inverse_gamma=None, **kwargs):
super().__init__(**kwargs)
self.inverse_gamma = inverse_gamma
def _get_kernel(self, X, Y=None, inverse=False):
if callable(self.kernel):
params = self.kernel_params or {}
else:
if inverse:
gamma_val = self.inverse_gamma
else:
gamma_val = self.gamma
params = {"gamma": gamma_val,
"degree": self.degree,
"coef0": self.coef0}
print(params, X.shape)
return pairwise_kernels(X, Y, metric=self.kernel,
filter_params=True, n_jobs=self.n_jobs,
**params)
def _fit_inverse_transform(self, X_transformed, X):
if hasattr(X, "tocsr"):
raise NotImplementedError("Inverse transform not implemented for "
"sparse matrices!")
n_samples = X_transformed.shape[0]
K = self._get_kernel(X_transformed, inverse=True)
K.flat[::n_samples + 1] += self.alpha
self.dual_coef_ = linalg.solve(K, X, sym_pos=True, overwrite_a=True)
self.X_transformed_fit_ = X_transformed
def inverse_transform(self, X):
"""Transform X back to original space.
Parameters
----------
X : array-like, shape (n_samples, n_components)
Returns
-------
X_new : array-like, shape (n_samples, n_features)
References
----------
"Learning to Find Pre-Images", G BakIr et al, 2004.
"""
if not self.fit_inverse_transform:
raise NotFittedError("The fit_inverse_transform parameter was not"
" set to True when instantiating and hence "
"the inverse transform is not available.")
K = self._get_kernel(X, self.X_transformed_fit_, inverse=True)
return np.dot(K, self.dual_coef_)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment