Это моя наивная реализация точечного продукта:
float simple_dot(int N, float *A, float *B) {
float dot = 0;
for(int i = 0; i < N; ++i) {
dot += A[i] * B[i];
}
return dot;
}
И это с помощью библиотеки C ++:
float library_dot(int N, float *A, float *B) {
return std::inner_product(A, A+N, B, 0);
}
Я провел какой-то тест (код здесь https://github.com/ijklr/sse), и версия библиотеки намного медленнее.
Мой флаг компилятора -Ofast -march=native
Ваши две функции не делают одно и то же. Алгоритм использует аккумулятор, тип которого счислимый от начального значения, которое в вашем случае (0
) является int
, Накопление операций с плавающей точкой в int не только занимает больше времени, чем накапливание в операции с плавающей точкой, но также дает другой результат.
Эквивалентом вашего исходного кода цикла является использование начального значения 0.0f
или эквивалентно float{}
,
(Обратите внимание, что std::accumulate
очень похоже в этом отношении.)
Других решений пока нет …