????????在主成分分析法(PCA)中,我們對降維算法PCA做了總結(jié)。這里我們就對另外一種經(jīng)典的降維方法線性判別分析(Linear Discriminant Analysis, 以下簡稱LDA)做一個總結(jié)。LDA在模式識別領域(比如人臉識別,艦艇識別等圖形圖像識別領域)中有非常廣泛的應用,因此我們有必要了解下它的算法原理。
在學習LDA之前,有必要將其自然語言處理領域的LDA區(qū)別開來,在自然語言處理領域, LDA是隱含狄利克雷分布(Latent Dirichlet Allocation,簡稱LDA),他是一種處理文檔的主題模型。我們本文只討論線性判別分析,因此后面所有的LDA均指線性判別分析。
目錄
一、LDA思想
二、LDA算法原理
(一)瑞利商和廣義瑞利商
1、瑞利商
2、廣義瑞利商
(二)二類LDA原理?
(三)多類LDA原理?
三、LDA算法流程?
四、LDA與PCA比較?
(一)LDA vs PCA??
(二)用scikit-learn分別對PCA和LDA進行比較?
1、對scikit-learn中LDA類概述
2、降維實例
五、LDA算法總結(jié)
六、實例?
(一)python實現(xiàn)
(二)sklearn實現(xiàn)
(三)LDA實現(xiàn)iris 數(shù)據(jù)
(四)手機價格分類實例
一、LDA思想
????????LDA屬于機器學習中的監(jiān)督學習算法,常用來做特征提取、數(shù)據(jù)降維和任務分類。LDA算法與PCA算法都是常用的降維技術(shù)。兩者最大的區(qū)別在于:LDA是一種監(jiān)督學習的降維技術(shù),也就是說它的數(shù)據(jù)集的每個樣本是有類別輸出的;而PCA是不考慮樣本類別輸出的無監(jiān)督降維技術(shù)。LDA的思想可以用一句話概括:“投影后類內(nèi)方差最小,類間方差最大”(即我們要將數(shù)據(jù)在低維度上進行投影,投影后希望每一種類別數(shù)據(jù)的投影點盡可能的接近,而不同類別的數(shù)據(jù)的類別中心之間的距離盡可能的大。)
????????可能還是有點抽象,我們先看看最簡單的情況。假設我們有兩類數(shù)據(jù)分別為紅色和藍色,如下圖所示,這些數(shù)據(jù)特征是二維的,我們希望將這些數(shù)據(jù)投影到一維的一條直線,讓每一種類別數(shù)據(jù)的投影點盡可能的接近,而紅色和藍色數(shù)據(jù)中心之間的距離盡可能的大。
????????上圖中提供的兩種投影方式,哪一種能更好的滿足我們的標準呢?從直觀上可以看出,右圖要比左圖的投影效果好,因為右圖的紅色數(shù)據(jù)和藍色數(shù)據(jù)各點之間較為集中,且兩個類別之間的距離明顯。左圖則在邊界處數(shù)據(jù)混雜。
????????當然在實際應用中,我們的數(shù)據(jù)是多個類別的,我們的原始數(shù)據(jù)一般也是超過二維的,投影后的也一般不是直線,而是一個低維的超平面。?
二、LDA算法原理
????????在我們將上面直觀的內(nèi)容轉(zhuǎn)化為可以度量的問題之前,我們先了解些必要的數(shù)學基礎知識,這些在后面講解具體LDA原理時會用到。
(一)瑞利商和廣義瑞利商
1、瑞利商
我們首先來看看瑞利商的定義。瑞利商是指這樣的函數(shù)R(A,x):
2、廣義瑞利商
廣義瑞利商是指這樣的函數(shù)R(A,B,x):
(二)二類LDA原理?
????????現(xiàn)在我們回到LDA的原理上,我們在第一節(jié)說講到了LDA希望投影后希望同一種類別數(shù)據(jù)的投影點盡可能的接近,而不同類別的數(shù)據(jù)的類別中心之間的距離盡可能的大,但是這只是一個感官的度量?,F(xiàn)在我們首先從比較簡單的二類LDA入手,嚴謹?shù)姆治鯨DA的原理。?
(三)多類LDA原理?
三、LDA算法流程?
????????以上就是使用LDA進行降維的算法流程。實際上LDA除了可以用于降維以外,還可以用于分類。一個常見的LDA分類基本思想是假設各個類別的樣本數(shù)據(jù)符合高斯分布,這樣利用LDA進行投影后,可以利用極大似然估計計算各個類別投影數(shù)據(jù)的均值和方差,進而得到該類別高斯分布的概率密度函數(shù)。當一個新的樣本到來后,我們可以將它投影,然后將投影后的樣本特征分別帶入各個類別的高斯分布概率密度函數(shù),計算它屬于這個類別的概率,最大的概率對應的類別即為預測類別。
四、LDA與PCA比較?
(一)LDA vs PCA??
????????LDA用于降維,和PCA有很多相同,也有很多不同的地方,因此值得好好的比較一下兩者的降維異同點。
(二)用scikit-learn分別對PCA和LDA進行比較?
1、對scikit-learn中LDA類概述
????????在scikit-learn中, LDA類是sklearn.discriminant_analysis.LinearDiscriminantAnalysis。那既可以用于分類又可以用于降維。當然,應用場景最多的還是降維。和PCA類似,LDA降維基本也不用調(diào)參,只需要指定降維到的維數(shù)即可。
2、降維實例
????????在前面我們講到,PCA和LDA都可以用于降維。兩者沒有絕對的優(yōu)劣之分,使用兩者的原則實際取決于數(shù)據(jù)的分布。由于LDA可以利用類別信息,因此某些時候比完全無監(jiān)督的PCA會更好。下面我們舉一個LDA降維可能更優(yōu)的例子。?
?我們首先生成三類三維特征的數(shù)據(jù),代碼如下:
import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
from sklearn.datasets import make_blobs, make_classification
# 生成三類三維特征的數(shù)據(jù)
X, y = make_classification(n_samples=1000, n_features=3, n_redundant=0, n_classes=3, n_informative=2,
n_clusters_per_class=1, class_sep=0.5, random_state=10)
fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')
# ax = Axes3D(fig, rect=[0, 0, 1, 1], elev=30, azim=20)
ax.scatter(X[:, 0], X[:, 1], X[:, 2], marker='o', c=y)
plt.show()
我們看看最初的三維數(shù)據(jù)的分布情況:
?首先我們看看使用PCA降維到二維的情況,注意PCA無法使用類別信息來降維,代碼如下:
from sklearn.decomposition import PCA
pca = PCA(n_components=2)
pca.fit(X)
print(pca.explained_variance_ratio_)
print(pca.explained_variance_)
X_new = pca.transform(X)
plt.scatter(X_new[:, 0], X_new[:, 1], marker='o', c=y)
plt.show()
?在輸出中,PCA找到的兩個主成分方差比和方差如下:
[0.43377069 0.3716351 ]
[1.21083449 1.0373882 ]
輸出的降維效果圖如下:
由于PCA沒有利用類別信息,我們可以看到降維后,樣本特征和類別的信息關(guān)聯(lián)幾乎完全丟失。
現(xiàn)在我們再看看使用LDA的效果,代碼如下:
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis
lda = LinearDiscriminantAnalysis(n_components=2)
lda.fit(X, y)
X_new = lda.transform(X)
plt.scatter(X_new[:, 0], X_new[:, 1], marker='o', c=y)
plt.show()
我們這里對LinearDiscriminantAnalysis類的參數(shù)做一個基本的總結(jié)。
1.參數(shù)解釋
solver:字符串,可選參數(shù)。指定求解超平面矩陣的方法??蛇x方法有
(1) ‘svd’:奇異值分解(默認)。不需要計算協(xié)方差矩陣,因此對于具有大規(guī)模特征的數(shù)據(jù),推薦使用該方法,該方法既可用于分類也可用于降維。
(2) ‘lsqr’:最小二乘,結(jié)合shrinkage參數(shù)。該方法僅可用于分類。
(3) ‘eigen’:特征值分解,結(jié)合shrinkage參數(shù)。特征值不多的時候推薦使用該方法,該方法既可用于分類也可用于降維。
shrinkage:字符串或者浮點數(shù),可選參數(shù)。正則化參數(shù),增強LDA分類的泛化能力(僅做降維時可不考慮此參數(shù))。
(1) None:不正則化(默認)。
(2) ‘a(chǎn)uto’:算法自動決定是否正則化。
(3) [0,1]之間的浮點數(shù):指定值。
shrinkage參數(shù)僅在solver參數(shù)選擇’lsqr’和’eigen’時有用。
priors:數(shù)組,可選參數(shù)。數(shù)組中的元素依次指定了每個類別的先驗概率,默認為None,即每個類相等。降維時一般不需要關(guān)注這個參數(shù)。
n_components:整數(shù),可選參數(shù)。指定降維時降到的維度,該整數(shù)必須小于等于min(分類類別數(shù)-1,特征數(shù)),默認為None,即min(分類類別數(shù)-1,特征數(shù))。
store_covariance:布爾值,可選參數(shù)。額外計算每個類別的協(xié)方差矩陣,僅在solver參數(shù)選擇’svd’時有效,默認為False不計算。
tol:浮點數(shù),可選參數(shù)。指定’svd’中秩估計的閾值。默認值為0.0001。
2.屬性解釋
coef_:數(shù)組,shape (特征數(shù),) or (分類數(shù), 特征數(shù))。權(quán)重向量。
intercept_:數(shù)組,shape (特征數(shù),) 。截距項。
covariance_:數(shù)組,shape (特征數(shù), 特征數(shù)) 。適用于所有類別的協(xié)方差矩陣。
explained_variance_ratio_:數(shù)組,shape (n_components,) 。每一個維度解釋的方差占比(原文Percentage of variance explained by each of the selected components)。
means_:數(shù)組,shape (分類數(shù), 特征數(shù)) 。類均值。
priors_:數(shù)組,shape (分類數(shù),) 。類先驗概率(加起來等于1)。
scalings_:數(shù)組,shape (rank秩, 分類數(shù)-1) 。每個高斯分布的方差σ(原文Scaling of the features in the space spanned by the class centroids)。
xbar_:數(shù)組,shape (特征數(shù),) 。整體均值。
classes_:數(shù)組,shape (分類數(shù),) 。去重的分類標簽Unique class labels,即分哪幾類。
3.方法解釋
decision_function(self, X):
預測置信度分數(shù)。置信度分數(shù)是樣本到(分類)超平面的帶符號的距離。
參數(shù): X: shape(樣本數(shù)量, 特征數(shù))
返回值:數(shù)組,二分類——shape(樣本數(shù),),多分類——shape(樣本數(shù), 分類數(shù))
fit(self, X, y):
訓練模型
fit_transform(self, X, y=None, **fit_params):
訓練模型同時將X轉(zhuǎn)換為新維度的標準化數(shù)據(jù)。
參數(shù):X,y
返回值:數(shù)組,shape(樣本數(shù)量, 新特征數(shù))
transform(self, X):
X轉(zhuǎn)換為標準化數(shù)據(jù)。
參數(shù):X
返回值:數(shù)組,shape(樣本數(shù)量, 維數(shù))
get_params(self, deep=True):
以字典返回LDA模型的參數(shù)值,比如solver、priors等。參數(shù)deep默認為True,還會返回包含的子模型的參數(shù)值。
predict(self, X):
根據(jù)模型的訓練,返回預測值。
參數(shù):X: shape(樣本數(shù)量, 特征數(shù))
返回值:數(shù)組,shape [樣本數(shù)]
score(self, X, y, sample_weight=None):
根據(jù)給定的測試數(shù)據(jù)X和分類標簽y返回預測正確的平均準確率。可以用于性能度量,返回模型的準確率,參數(shù)為x_test,y_test。
參數(shù):X,y
返回值:浮點數(shù)
predict_log_proba(self, X):
返回X中每一個樣本預測為各個分類的對數(shù)概率
參數(shù): X
返回值:數(shù)組,shape(樣本數(shù), 分類數(shù))
predict_proba(self, X):
返回X中每一個樣本預測為各個分類的概率
參數(shù): X
返回值:數(shù)組,shape(樣本數(shù), 分類數(shù))
?輸出的效果圖如下:
可以看出降維后樣本特征和類別信息之間的關(guān)系得以保留。
一般來說,如果我們的數(shù)據(jù)是有類別標簽的,那么優(yōu)先選擇LDA去嘗試降維;當然也可以使用PCA做很小幅度的降維去消去噪聲,然后再使用LDA降維。如果沒有類別標簽,那么肯定PCA是最先考慮的一個選擇了。
五、LDA算法總結(jié)
?????????LDA算法既可以用來降維,又可以用來分類,但是目前來說,主要還是用于降維。在我們進行圖像識別圖像識別相關(guān)的數(shù)據(jù)分析時,LDA是一個有力的工具。下面總結(jié)下LDA算法的優(yōu)缺點。
????????LDA算法的主要優(yōu)點有:
????????LDA算法的主要缺點有:?
六、實例?
(一)python實現(xiàn)
import numpy as np
from sklearn.datasets import load_iris
import matplotlib.pyplot as plt
def LDA(data, target, n_dim):
"""
:param data: (n_samples, n_features)
:param target: data class
:param n_dim: target dimension
:return: (n_samples, n_dims)
"""
clusters = np.unique(target)
if n_dim > len(clusters) - 1:
print("K is too much")
print("please input again")
exit(0)
# within_class scatter matrix
Sw = np.zeros((data.shape[1], data.shape[1]))
for i in clusters:
datai = data[target == i]
datai = datai - datai.mean(0)
Swi = np.mat(datai).T * np.mat(datai)
Sw += Swi
# between_class scatter matrix
SB = np.zeros((data.shape[1], data.shape[1]))
u = data.mean(0) # 所有樣本的平均值
for i in clusters:
Ni = data[target == i].shape[0]
ui = data[target == i].mean(0) # 某個類別的平均值
SBi = Ni * np.mat(ui - u).T * np.mat(ui - u)
SB += SBi
S = np.linalg.inv(Sw) * SB
eigVals, eigVects = np.linalg.eig(S) # 求特征值,特征向量
eigValInd = np.argsort(eigVals)
eigValInd = eigValInd[:(-n_dim - 1):-1]
w = eigVects[:, eigValInd]
data_ndim = np.dot(data, w)
return data_ndim
if __name__ == '__main__':
iris = load_iris()
X = iris.data
Y = iris.target
target_names = iris.target_names
X_r2 = LDA(X, Y, 2)
colors = ['navy', 'turquoise', 'darkorange']
for color, i, target_name in zip(colors, [0, 1, 2], target_names):
plt.scatter(X_r2[Y == i, 0], X_r2[Y == i, 1], alpha=.8, color=color,
label=target_name)
plt.legend(loc='best', shadow=False, scatterpoints=1)
plt.title('LDA of IRIS dataset by Python')
plt.show()
??
(二)sklearn實現(xiàn)
import matplotlib.pyplot as plt
from sklearn import datasets
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis
iris = datasets.load_iris()
X = iris.data
Y = iris.target
target_names = iris.target_names
lda = LinearDiscriminantAnalysis(n_components=2)
X_r2 = lda.fit(X, Y).transform(X)
colors = ['navy', 'turquoise', 'darkorange']
for color, i, target_name in zip(colors, [0, 1, 2], target_names):
plt.scatter(X_r2[Y == i, 0], X_r2[Y == i, 1], alpha=.8, color=color,
label=target_name)
plt.legend(loc='best', shadow=False, scatterpoints=1)
plt.title('LDA of IRIS dataset by sklearn')
plt.show()
?
(三)LDA實現(xiàn)iris 數(shù)據(jù)
首先,iris數(shù)據(jù)集可以去該博主的GitHub下載
?下面我們分析導入的數(shù)據(jù)集,代碼如下:
import pandas as pd
import numpy as np
from matplotlib import pyplot as plt
from sklearn.preprocessing import LabelEncoder
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis as LDA
feature_dict = {i: label for i, label in zip(range(4), ("Sepal.Length", "Sepal.Width", "Petal.Length", "Petal.Width",))}
# print(feature_dict) # {0: 'Sepal.Length', 1: 'Sepal.Width', 2: 'Petal.Length', 3: 'Petal.Width'}
df = pd.read_csv('iris.csv', sep=',')
df.columns = ["Number"] + [l for i, l in sorted(feature_dict.items())] + ['Species']
# to drop the empty line at file-end
df.dropna(how='all', inplace=True)
# print(df.tail()) # 打印數(shù)據(jù)的后五個,和 .head() 是對應的
下面我們把數(shù)據(jù)分成data和label,如下形式:
X = df[["Sepal.Length", "Sepal.Width", "Petal.Length", "Petal.Width"]].values
y = df['Species'].values
enc = LabelEncoder()
label_encoder = enc.fit(y)
y = label_encoder.transform(y) + 1
這樣我們對label進行分類,其中{1: 'Setosa', ? 2: 'Versicolor',?? 3: 'Virginica'},分類大概是這樣的:
label_dict = {1: 'setosa', 2: 'versicolor', 3: 'virginica'}
下面我們分別求三種鳶尾花數(shù)據(jù)在不同特征維度上的均值向量 Mi。
求均值的代碼如下:
np.set_printoptions(precision=4)
mean_vectors = []
for c1 in range(1, 4):
mean_vectors.append(np.mean(X[y == c1], axis=0))
print('Mean Vector class %s : %s\n' % (c1, mean_vectors[c1 - 1]))
三個類別,求出的均值如下:
下面計算兩個 4*4 維矩陣:類內(nèi)散布矩陣和類間散布矩陣
類內(nèi)散度矩陣公式如下:
?代碼如下:
S_W = np.zeros((4, 4))
for c1, mv in zip(range(1, 4), mean_vectors):
# scatter matrix for every class
class_sc_mat = np.zeros((4, 4))
for row in X[y == c1]:
# make column vectors
row, mv = row.reshape(4, 1), mv.reshape(4, 1)
class_sc_mat += (row - mv).dot((row - mv).T)
# sum class scatter metrices
S_W += class_sc_mat
print('within-class Scatter Matrix:\n', S_W)
結(jié)果如下:
1 2 3 4 5 |
|
類間散布矩陣如下:
代碼如下:
overall_mean = np.mean(X, axis=0)
S_B = np.zeros((4, 4))
for i, mean_vec in enumerate(mean_vectors):
n = X[y == i + 1, :].shape[0]
# make column vector
mean_vec = mean_vec.reshape(4, 1)
# make column vector
overall_mean = overall_mean.reshape(4, 1)
S_B += n * (mean_vec - overall_mean).dot((mean_vec - overall_mean).T)
print('between-class Scatter matrix:\n', S_B)
結(jié)果展示:
1 2 3 4 5 |
|
然后我們求解矩陣的特征值:
代碼如下:
eig_vals, eig_vecs = np.linalg.eig(np.linalg.inv(S_W).dot(S_B))
for i in range(len(eig_vals)):
eigvec_sc = eig_vecs[:, i].reshape(4, 1)
print('\n Eigenvector {}: \n {}'.format(i+1, eigvec_sc.real))
print('Eigenvalue {: }: {:.2e}'.format(i+1, eig_vals[i].real))
結(jié)果如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
|
最后求特征值與特征向量,其中:
- 特征向量:表示映射方向
- 特征值:特征向量的重要程度
代碼如下:
# make a list of (eigenvalue, eigenvector) tuples
eig_pairs = [(np.abs(eig_vals[i]), eig_vecs[:, i]) for i in range(len(eig_vals))]
# sort the (eigenvalue, eigenvector) tuples from high to low
eig_pairs = sorted(eig_pairs, key=lambda k: k[0], reverse=True)
# Visually cinfirm that the list is correctly sorted by decreasing eigenvalues
print('Eigenvalues in decreasing order: \n')
for i in eig_pairs:
print(i[0])
特征向量如下:
?特征值代碼如下:
print('Variance explained:\n')
eigv_sum = sum(eig_vals)
for i, j in enumerate(eig_pairs):
print('eigenvalue {0:}: {1:.2%}'.format(i + 1, (j[0] / eigv_sum).real))
?結(jié)果如下:
我們從上可以知道,選擇前兩維特征:
W = np.hstack((eig_pairs[0][1].reshape(4, 1), eig_pairs[1][1].reshape(4, 1)))
print('Matrix W: \n', W.real)
特征矩陣W如下:
lda如下:?
X_lda = X.dot(W)
assert X_lda.shape == (150, 2), 'The matrix is not 150*2 dimensional.'
下面畫圖:
def plt_step_lda():
ax = plt.subplot(111)
for label, marker, color in zip(range(1, 4), ('^', 's', 'o'), ('blue', 'red', 'green')):
plt.scatter(x=X_lda[:, 0].real[y == label],
y=X_lda[:, 1].real[y == label],
marker=marker,
color=color,
alpha=0.5,
label=label_dict[label])
plt.xlabel('LD1')
plt.ylabel('LD2')
leg = plt.legend(loc='upper right', fancybox=True)
leg.get_frame().set_alpha(0.5)
plt.title('LDA: Iris projection onto the first 2 linear discriminants')
# hide axis ticks
plt.tick_params(axis='both', which='both', bottom='off',
top='off', labelbottom='on', left='off',
labelleft='on')
# remove axis spines
ax.spines['top'].set_visible(False)
ax.spines['right'].set_visible(False)
ax.spines['bottom'].set_visible(False)
ax.spines['left'].set_visible(False)
plt.grid()
plt.tight_layout()
plt.show()
如圖所示:
使用sklearn實現(xiàn)lda:
# LDA
sklearn_lda = LDA(n_components=2)
X_lda_sklearn = sklearn_lda.fit_transform(X, y)
def plot_scikit_lda(X, title):
ax = plt.subplot(111)
for label, marker, color in zip(range(1, 4), ('^', 's', 'o'), ('blue', 'red', 'green')):
plt.scatter(x=X_lda[:, 0].real[y == label],
# flip the figure
y=X_lda[:, 1].real[y == label] * -1,
marker=marker,
color=color,
alpha=0.5,
label=label_dict[label])
plt.xlabel('LD1')
plt.ylabel('LD2')
leg = plt.legend(loc='upper right', fancybox=True)
leg.get_frame().set_alpha(0.5)
plt.title(title)
# hide axis ticks
plt.tick_params(axis='both', which='both', bottom='off',
top='off', labelbottom='on', left='off',
labelleft='on')
# remove axis spines
ax.spines['top'].set_visible(False)
ax.spines['right'].set_visible(False)
ax.spines['bottom'].set_visible(False)
ax.spines['left'].set_visible(False)
plt.grid()
plt.tight_layout()
plt.show()
plot_scikit_lda(X, title='Default LDA via scikit-learn')
結(jié)果如下:
(四)手機價格分類實例
本例數(shù)據(jù)來源于機器學習競賽平臺Kaggle,一個關(guān)于手機價格分類的數(shù)據(jù)。數(shù)據(jù)地址:https://www.kaggle.com/iabhishekofficial/mobile-price-classification?
數(shù)據(jù)一共2000個樣例,20個字段。分類字段為price_range,一共分為了4類。數(shù)據(jù)集無缺失值,無錯誤值。字段及解釋如下:
由于從一般常識得知,機身厚度和機身重量對價格往往是沒有直接影響的,故在建模時將這兩個字段剔除。
import pandas as pd
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis
from sklearn import model_selection
# 讀取數(shù)據(jù)
data = pd.read_csv(r'C:\Users\Administrator\Desktop\train.csv')
# 剔除兩個無關(guān)字段
data.drop(['m_dep', 'mobile_wt'], axis=1, inplace=True)
X = data[data.columns[:-1]]
Y = data[data.columns[-1]]
# 拆分為訓練集和測試集
x_train, x_test, y_train, y_test = model_selection.train_test_split(X, Y, test_size=0.25, random_state=1234)
# LDA
lda = LinearDiscriminantAnalysis()
# 訓練模型
lda.fit(x_train, y_train)
# 模型評估
print('模型準確率:\n', lda.score(x_test, y_test))
?最終得到模型的準確率為94.8%,說明模型效果還是不錯的。
?
?參考文獻:
1、線性判別分析LDA原理總結(jié)
2、用scikit-learn進行LDA降維?
3、線性分類(二)-- 線性判別分析 LDA
4、Python機器學習筆記:線性判別分析(LDA)算法文章來源:http://www.zghlxwxcb.cn/news/detail-400440.html
5、機器學習算法理論與實踐——線性判別分析(LDA)文章來源地址http://www.zghlxwxcb.cn/news/detail-400440.html
到了這里,關(guān)于線性判別分析法(LDA)的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!