PCA in numpy e sklearn produce risultati diversi


21

Sto fraintendendo qualcosa. Questo è il mio codice

usando sklearn

import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
from sklearn import decomposition
from sklearn import datasets
from sklearn.preprocessing import StandardScaler

pca = decomposition.PCA(n_components=3)

x = np.array([
        [0.387,4878, 5.42],
        [0.723,12104,5.25],
        [1,12756,5.52],
        [1.524,6787,3.94],
    ])
pca.fit_transform(x)

Produzione:

array([[ -4.25324997e+03,  -8.41288672e-01,  -8.37858943e-03],
   [  2.97275001e+03,  -1.25977271e-01,   1.82476780e-01],
   [  3.62475003e+03,  -1.56843494e-01,  -1.65224286e-01],
   [ -2.34425007e+03,   1.12410944e+00,  -8.87390454e-03]])

Utilizzando metodi intorpiditi

x_std = StandardScaler().fit_transform(x)
cov = np.cov(x_std.T)
ev , eig = np.linalg.eig(cov)
a = eig.dot(x_std.T)

Produzione

array([[ 0.06406894,  0.94063993, -1.62373172],
   [-0.35357757,  0.7509653 ,  0.63365168],
   [ 0.29312477,  0.6710958 ,  1.11766206],
   [-0.00361615, -2.36270102, -0.12758202]])
I have kept all 3 components but it doesnt seem to allow me to retain my original data.

Posso sapere perché è così?

Se desidero recuperare la mia matrice originale, cosa devo fare?


Il tuo codice intorpidito è IMHO errato (inoltre, utilizza ciò Xche non è definito). Ricontrolla la tua matematica .
Anony-Mousse -Reststate Monica

Sto usando il notebook ipython in modo da poterlo copiare solo dalle celle. La mia matematica è sbagliata? Quale parte @ Anony-Mousse
aceminer

@ Anony-Mousse Sì, ho capito il mio errore, ma ancora non combacia
aceminer

@aceminer Sono curioso di sapere perché calcoli la matrice di covarianza di x_std.T, non di x_std?
Evgeni Nabokov

@EvgeniNabokov è passato troppo tempo. Sry non riesco a ricordare già
aceminer il

Risposte:


21

La differenza è perché decomposition.PCAnon standardizza le tue variabili prima di fare PCA, mentre nel tuo calcolo manuale chiami StandardScalerper fare la standardizzazione. Quindi, stai osservando questa differenza: PCA sulla correlazione o covarianza?

Se si sostituisce

pca.fit_transform(x)

con

x_std = StandardScaler().fit_transform(x)
pca.fit_transform(x_std)

otterrai lo stesso risultato del calcolo manuale ...

... ma solo fino all'ordine dei PC. Questo perché quando corri

ev , eig = np.linalg.eig(cov)

ottieni autovalori non necessariamente in ordine decrescente. ottengo

array([ 0.07168571,  2.49382602,  1.43448827])

Quindi vorrai ordinarli manualmente. Sklearn lo fa per te.


Per quanto riguarda la ricostruzione delle variabili originali, vedere Come invertire la PCA e ricostruire le variabili originali da diversi componenti principali?


Vorrei solo controllare. È davvero necessario standardizzare la matrice in base alla sua deviazione standard? Ho visto esempi in cui non lo fanno
aceminer,

Non è necessario , è solo un modo per farlo. Vedi il link che ho inserito nel primo paragrafo: stats.stackexchange.com/questions/53 - si tratta davvero di questa domanda. Se si standardizza, si fa PCA sulle correlazioni. Se non lo fai, fai PCA sulle covarianze.
ameba dice Reinstate Monica il

9

Ecco una bella implementazione con discussione e spiegazione di PCA in Python. Questa implementazione porta allo stesso risultato dello scikit PCA. Questo è un altro indicatore che il tuo PCA è sbagliato.

import numpy as np
from scipy import linalg as LA

x = np.array([
        [0.387,4878, 5.42],
        [0.723,12104,5.25],
        [1,12756,5.52],
        [1.524,6787,3.94],
    ])

#centering the data
x -= np.mean(x, axis = 0)  

cov = np.cov(x, rowvar = False)

evals , evecs = LA.eigh(cov)

è necessario ordinare gli autovalori (e gli autovettori di conseguenza) in ordine decrescente

idx = np.argsort(evals)[::-1]
evecs = evecs[:,idx]
evals = evals[idx]

a = np.dot(x, evecs) 

In generale, ti consiglio di controllare il tuo codice implementando un semplice esempio (il più semplice possibile) e calcolando manualmente i risultati corretti (e risultati intermedi). Questo ti aiuta a identificare il problema.


1
Adoro questa risposta. Ha risolto il mio problema!
Jinhua Wang,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.