【问题标题】:Do you need to normalize your data before using scipy.spatial.distance.cosine() in python?在 python 中使用 scipy.spatial.distance.cosine() 之前是否需要对数据进行规范化?
【发布时间】:2020-07-06 15:51:59
【问题描述】:

我有两个数据集 D1 和 D2。每个数据集有 n 个特征(列),特征值有不同的尺度。我需要找到 D1 和 D2 中每对相关样本之间的余弦距离,以量化 D1 和 D2 的相似程度。在使用余弦距离之前是否需要对 D1 和 D2 进行归一化?我正在使用 scipy.spatial.distance.cosine(u, v) 来查找样本 u 和样本 v 之间的距离。

谢谢!

【问题讨论】:

    标签: python scipy cosine-similarity scipy-spatial


    【解决方案1】:

    在 python 中使用 scipy.spatial.distance.cosine() 之前是否需要对数据进行规范化?

    如果“规范化”数据仅涉及将输入乘以标量,那么不,您不需要规范化。查看docstring 中的距离公式。现在假设 ab 是正标量。那么

    cosine(a*u, b*v) = 1 - dot(a*u, b*v)/(norm(a*u)*norm(b*v))
                     = 1 - a*b*dot(u, v)/(a*b*norm(u)*norm(v))
                     = 1 - dot(u, v)/(norm(u)*norm(v))
                     = cosine(u, v)
    

    因此,用于规范化输入的比例因子将取消并且不会影响结果。

    您可以在一个简单的示例中看到这一点:

    In [17]: from scipy.spatial.distance import cosine
    
    In [18]: u = np.array([1.0, 3.0, 5.0, 10.0])
    
    In [19]: v = np.array([-3.0, 1.0, 0.0, 2.0])
    
    In [20]: cosine(u, v)
    Out[20]: 0.5399562937717639
    
    In [21]: cosine(u/10, v)
    Out[21]: 0.5399562937717639
    
    In [22]: cosine(3*u, 4*v)
    Out[22]: 0.5399562937717639
    

    【讨论】:

    • 但是为什么当我使用 StandardScaler().fit_transform() 并在使用 scipy.spatial.distance.cosine() 之前对数据进行标准化时,我得到的结果与输入原始数据时不同?另外,通过阅读以下链接,似乎规范化确实会影响结果:stats.stackexchange.com/questions/292596/…
    • 你问的问题是关于scipy.spatial.distance.cosine。问题中没有关于 scikit-learn 或 StandardScaler().fit_transform() 的内容。也许您应该就此提出一个新问题。请务必附上minimal, reproducible example,以便读者可以轻松清晰地了解您遇到的问题。
    • StandardScalar 按平均值移动数据。在cosine 的输入上使用它会影响距离。
    • 感谢您的回复!那么问题来了,当不同的特征有不同的尺度时,我们不应该在应用余弦之前将数据按均值移动吗?
    猜你喜欢
    • 2016-10-15
    • 2021-05-14
    • 1970-01-01
    • 1970-01-01
    • 2018-12-12
    • 2017-04-05
    • 2018-10-06
    • 2020-07-31
    • 2013-06-30
    相关资源
    最近更新 更多