Прежде всего, я предполагаю, что вы называете features
переменными и not the samples/observations
.В этом случае вы можете сделать что-то вроде следующего, создав функцию biplot
, которая показывает все на одном графике.В этом примере я использую данные диафрагмы:
Перед примером, пожалуйста, обратите внимание, что основная идея при использовании PCA в качестве инструмента для выбора функции заключается в выборе переменных в соответствии с величиной (от наибольшего к наименьшему по абсолютным значениям) их коэффициентов (нагрузок).См. Мой последний абзац после графика для получения более подробной информации.
PART1 : я объясняю, как проверить важность функций и как построить биплот.
ЧАСТЬ 2 : Я объясняю, как проверить важность функций и как сохранить их в фрейме данных Pandas, используя имена элементов.
ЧАСТЬ 1:
import numpy as np
import matplotlib.pyplot as plt
from sklearn import datasets
from sklearn.decomposition import PCA
import pandas as pd
from sklearn.preprocessing import StandardScaler
iris = datasets.load_iris()
X = iris.data
y = iris.target
#In general a good idea is to scale the data
scaler = StandardScaler()
scaler.fit(X)
X=scaler.transform(X)
pca = PCA()
x_new = pca.fit_transform(X)
def myplot(score,coeff,labels=None):
xs = score[:,0]
ys = score[:,1]
n = coeff.shape[0]
scalex = 1.0/(xs.max() - xs.min())
scaley = 1.0/(ys.max() - ys.min())
plt.scatter(xs * scalex,ys * scaley, c = y)
for i in range(n):
plt.arrow(0, 0, coeff[i,0], coeff[i,1],color = 'r',alpha = 0.5)
if labels is None:
plt.text(coeff[i,0]* 1.15, coeff[i,1] * 1.15, "Var"+str(i+1), color = 'g', ha = 'center', va = 'center')
else:
plt.text(coeff[i,0]* 1.15, coeff[i,1] * 1.15, labels[i], color = 'g', ha = 'center', va = 'center')
plt.xlim(-1,1)
plt.ylim(-1,1)
plt.xlabel("PC{}".format(1))
plt.ylabel("PC{}".format(2))
plt.grid()
#Call the function. Use only the 2 PCs.
myplot(x_new[:,0:2],np.transpose(pca.components_[0:2, :]))
plt.show()
Визуализируйте, что происходит, используя биплот
Теперь важность каждогоособенность отражается величиной соответствующих значений в собственных векторах (более высокая величина - более высокая важность)
Давайте сначала посмотрим, какую величину дисперсии объясняет каждый компьютер.
pca.explained_variance_ratio_
[0.72770452, 0.23030523, 0.03683832, 0.00515193]
PC1 explains 72%
и PC2 23%
.Вместе, если мы оставим только ПК1 и ПК2, они объяснят 95%
.
Теперь давайте найдем самые важные функции.
print(abs( pca.components_ ))
[[0.52237162 0.26335492 0.58125401 0.56561105]
[0.37231836 0.92555649 0.02109478 0.06541577]
[0.72101681 0.24203288 0.14089226 0.6338014 ]
[0.26199559 0.12413481 0.80115427 0.52354627]]
Здесь, pca.components_
имеет форму [n_components, n_features]
.Таким образом, взглянув на PC1
(Первый основной компонент), который является первой строкой: [0.52237162 0.26335492 0.58125401 0.56561105]]
, мы можем заключить, что feature 1, 3 and 4
(или Var 1, 3 и 4 в биплоте) являются наиболее важными.
Подводя итог, рассмотрим абсолютные значения компонент собственных векторов, соответствующих k наибольшим собственным значениям.В sklearn
компоненты отсортированы по explained_variance_
.Чем они больше этих абсолютных значений, тем больше конкретный признак вносит вклад в этот главный компонент.
ЧАСТЬ 2:
Важными признаками являются те, которые влияют больше на компоненты и, следовательно,, иметь большое абсолютное значение 7 баллов по компоненту.
Чтобы получить наиболее важные функции на ПК с именами и сохранить их в pandas dataframe useэто:
from sklearn.decomposition import PCA
import pandas as pd
import numpy as np
np.random.seed(0)
# 10 samples with 5 features
train_features = np.random.rand(10,5)
model = PCA(n_components=2).fit(train_features)
X_pc = model.transform(train_features)
# number of components
n_pcs= model.components_.shape[0]
# get the index of the most important feature on EACH component
# LIST COMPREHENSION HERE
most_important = [np.abs(model.components_[i]).argmax() for i in range(n_pcs)]
initial_feature_names = ['a','b','c','d','e']
# get the names
most_important_names = [initial_feature_names[most_important[i]] for i in range(n_pcs)]
# LIST COMPREHENSION HERE AGAIN
dic = {'PC{}'.format(i): most_important_names[i] for i in range(n_pcs)}
# build the dataframe
df = pd.DataFrame(dic.items())
Это печатает:
0 1
0 PC0 e
1 PC1 d
Так что на ПК1 функция с именем e
является наиболее важной, а на ПК2d
.