1

我试图将马氏距离计算为使用 PCA 转换后的欧几里得距离,但是,我没有得到相同的结果。以下代码:

import numpy as np
from scipy.spatial.distance import mahalanobis
from sklearn.decomposition import PCA

X = [[1,2], [2,2], [3,3]]

mean = np.mean(X, axis=0)
cov = np.cov(X, rowvar=False)
covI = np.linalg.inv(cov)

maha = mahalanobis(X[0], mean, covI)
print(maha)

pca = PCA()

X_transformed = pca.fit_transform(X)

stdev = np.std(X_transformed, axis=0)
X_transformed /= stdev

print(np.linalg.norm(X_transformed[0]))

印刷

1.1547005383792515
1.4142135623730945

据我了解,PCA 与维度无关,除以标准差对每个维度的权重均等,因此欧几里德距离应等于马氏距离。我哪里错了?

4

1 回答 1

2

根据这个讨论,PCA 和马氏距离之间的关系仅适用于具有单位方差的 PCA 分量。这可以通过对白化数据应用 PCA 来获得(更多信息在这里)。

一旦你这样做了,原始空间中的马氏距离等于 PCA 空间中的欧几里德距离。您可以在下面的代码中看到它的演示:

import numpy as np
from scipy.spatial.distance import mahalanobis,euclidean
from sklearn.decomposition import PCA
from sklearn.preprocessing import StandardScaler

X = np.array([[1,2], [2,2], [3,3]])

cov = np.cov(X, rowvar=False)
covI = np.linalg.inv(cov)
mean=np.mean(X)
maha = mahalanobis(X[0], X[1], covI)

pca = PCA(whiten=True)
X_transformed= pca.fit_transform(X)

print('Mahalanobis distance: '+str(maha))
print('Euclidean distance: '+str(euclidean(X_transformed[0],X_transformed[1])))

输出给出:

Mahalanobis distance: 2.0
Euclidean distance: 2.0000000000000004
于 2021-11-02T15:58:27.123 回答