线性代数 - 使用犰狳C++的余弦相似性给了我负面的结果



我输入了一个使用犰狳c ++线性库的余弦相似性函数。我的代码是下一个:

double cosine_similarity(rowvec A, rowvec B)
{
   double dot = as_scalar(A*B.t());
   double denomA = as_scalar(A*A.t());
   double denomB = as_scalar(B*B.t());
   return dot / (sqrt(denomA) * sqrt(denomB)) ;
}

我以这个矩阵为例:

-

0.0261 -0.6780 -0.7338 0.0345

-

0.0230 0.0082 -0.0400 -0.7056

-0.2590 -

0.7052 0.6590 -0.0371

-

0.9650 0.2072 -0.1551 0.0426

-

0.0230 0.0082 -0.0400 -0.7056

当我计算第二行与所有行之间的余弦相似性时,我得到以下结果:

相似性 [1,0]: -1.07944e-16

相似性 [1,1]: 1

相似性 [1,2]: -1.96262e-17

相似性 [1,3]: -1.71729e-16

相似性 [1,4]: 1

这是对的吗?我担心负面结果,即使它们的意思是零。我想知道我是否做错了什么。cosine_similarity以这种方式使用:

for (unsigned int row = 0; row < redV.n_rows ; row++)
{
    double ans = cosine_similarity(redV.row(indicate), redV.row(row));
    cout << "Similarity [" << indicate << "," << row << "]: " << ans << endl;
    cout << "Similarity [" << indicate << "," << row << "]: " << norm_dot(redV.row(indicate), redV.row(row)) << endl;
}

您的代码似乎是正确的,您只是遇到了机器精度问题。 A第三行的A*B.t()和第二行的B(反之亦然)应为零,但不是,但在机器精度范围内。Scipy的cosine也有同样的问题:

In [10]: from scipy.spatial.distance import cosine
In [11]: 1 - cosine([-0.2590, -0.7052, 0.6590, -0.0371], [-0.0230, 0.0082, -0.0400, -0.7056])
Out[11]: -1.114299639159988e-05  # <=============== should not be negative!

(我减去 1 只是因为 Scipy 如何定义cosine.这个答案与你的答案不符,因为你只发布了四个小数点——但关键是,它是负面的。

如果要检查浮点数x是否在另一个y的机器精度范围内,请将它们的差异与std::numeric_limits::epsilon进行比较。请参阅此处almost_equal的定义。您可能希望cosine_similarity检查结果是almost_equal为 0 还是 1,在这种情况下返回 0 或 1。

相关内容

  • 没有找到相关文章

最新更新