1.流形學習的概念
流形學習方法(Manifold Learning),簡稱流形學習,自2000年在著名的科學雜志《Science》被首次提出以來,已成為資訊科學領域的研究熱點。在理論和應用上,流形學習方法都具有重要的研究意義。
假設資料是均勻采樣于一個高維歐氏空間中的低維流形,流形學習就是從高維采樣資料中恢複低維流形結構,即找到高維空間中的低維流形,并求出相應的嵌入映射,以實作維數約簡或者資料可視化。它是從觀測到的現象中去尋找事物的本質,找到産生資料的内在規律。
以上選自百度百科
簡單地了解,流形學習方法可以用來對高維資料降維,如果将次元降到2維或3維,我們就能将原始資料可視化,進而對資料的分布有直覺的了解,發現一些可能存在的規律。
2.流形學習的分類
可以将流形學習方法分為線性的和非線性的兩種,線性的流形學習方法如我們熟知的主成份分析(PCA),非線性的流形學習方法如等距映射(Isomap)、拉普拉斯特征映射(Laplacian eigenmaps,LE)、局部線性嵌入(Locally-linear embedding,LLE)。
當然,流形學習方法不止這些,因學識尚淺,在此我就不展開了,對于它們的原理,也不是一篇文章就能說明白的。對各種流形學習方法的介紹,網上有一篇不錯的讀物(原作已找不到): 流形學習 (Manifold Learning)
3.高維資料降維與可視化
對于資料降維,有一張圖檔總結得很好(同樣,我不知道原始出處):

圖中基本上包括了大多數流形學習方法,不過這裡面沒有t-SNE,相比于其他算法,t-SNE算是比較新的一種方法,也是效果比較好的一種方法。t-SNE是深度學習大牛Hinton和lvdmaaten(他的弟子?)在2008年提出的,lvdmaaten對t-SNE有個首頁介紹:tsne,包括論文以及各種程式設計語言的實作。
接下來是一個小實驗,對MNIST資料集降維和可視化,采用了十多種算法,算法在sklearn裡都已內建,畫圖工具采用matplotlib。大部分實驗内容都是參考sklearn這裡的example,稍微做了些修改。
Matlab使用者可以使用lvdmaaten提供的工具箱: drtoolbox
- 加載資料
MNIST資料從sklearn內建的datasets子產品擷取,代碼如下,為了後面觀察起來更明顯,我這裡隻選取
n_class=5
,也就是0~4這5種digits。每張圖檔的大小是8*8,展開後就是64維。
digits = datasets.load_digits(n_class=)
X = digits.data
y = digits.target
print X.shape
n_img_per_row =
img = np.zeros(( * n_img_per_row, * n_img_per_row))
for i in range(n_img_per_row):
ix = * i +
for j in range(n_img_per_row):
iy = * j +
img[ix:ix + , iy:iy + ] = X[i * n_img_per_row + j].reshape((, ))
plt.imshow(img, cmap=plt.cm.binary)
plt.title('A selection from the 64-dimensional digits dataset')
運作代碼,獲得X的大小是(901,64),也就是901個樣本。下圖顯示了部分樣本:
- 降維
以t-SNE為例子,代碼如下,n_components設定為3,也就是将64維降到3維,init設定embedding的初始化方式,可選random或者pca,這裡用pca,比起random init會更stable一些。
print("Computing t-SNE embedding")
tsne = manifold.TSNE(n_components=, init='pca', random_state=)
t0 = time()
X_tsne = tsne.fit_transform(X)
plot_embedding_2d(X_tsne[:,:],"t-SNE 2D")
plot_embedding_3d(X_tsne,"t-SNE 3D (time %.2fs)" %(time() - t0))
降維後得到X_ tsne,大小是(901,3),plot_ embedding_ 2d()将前2維資料可視化,plot_ embedding_ 3d()将3維資料可視化。
函數plot_ embedding_ 3d定義如下:
def plot_embedding_3d(X, title=None):
#坐标縮放到[0,1]區間
x_min, x_max = np.min(X,axis=), np.max(X,axis=)
X = (X - x_min) / (x_max - x_min)
#降維後的坐标為(X[i, 0], X[i, 1],X[i,2]),在該位置畫出對應的digits
fig = plt.figure()
ax = fig.add_subplot(, , , projection='3d')
for i in range(X.shape[]):
ax.text(X[i, ], X[i, ], X[i,],str(digits.target[i]),
color=plt.cm.Set1(y[i] / ),
fontdict={'weight': 'bold', 'size': })
if title is not None:
plt.title(title)
- 看看效果
十多種算法,結果各有好壞,總體上t-SNE表現最優,但它的計算複雜度也是最高的。下面給出PCA、LDA、t-SNE的結果:
- 代碼擷取
MachineLearning/ManifoldLearning/DimensionalityReduction_DataVisualizing
轉載請注明出處:http://blog.csdn.net/u012162613/article/details/45920827