背景
- 余弦相似度是通过计算两个向量的夹角余弦值来评估他们的相似度,原理非常简单,应用空间却非常广阔,如人脸特征求相似度,还有NLP领域求文本相似度等等.
- 余弦相似计算在一般cpu上计算量其实并不大,但是如若人脸特征底库达到一定规模时,在求取最高相似度时速度问题就凸显出来了,特别是在ARM这样计算量十分有限的平台.所以很有必要对余弦相似计算进行优化加速.
参考资料
公式

代码实现(未用NEON)
- 下面这段代码应该很好理解, a_data、b_data是输入两个N维的特征向量, score是a_data、b_data两个特征向量的相似度输出.注意 a_data、b_data维度要相等
- 代码中 ab_mult_add:是上面公式的分母
- 代码中 sqrt(a_len * b_len):是上面公式的分子
#include <stdio.h>
#include <iostream>
#include <vector>
#include <math.h>
bool cos_similarity(const std::vector<float>& a_data,
const std::vector<float>& b_data,
float & score)
{
const int data_length = a_data.size();
double ab_mult_add = 0.0f;
double a_len = 0.0f;
double b_len = 0.0f;
if((0 != data_length) and (b_data.size() != data_length))
{
return false;
}
//ab_mult_add:分母
//sqrt(a_len * b_len) :分子
for (std::size_t i = 0; i