Почему inline функция класса C++ медленнее обычной inline функции?

Программа должна суммировать два вектора. Даны две реализации.
Первая: на основе мета-программирования и классов:
struct Sum {
  template <class T>
  inline T operator()(const T &a, const T &b) const noexcept {
    return a + b;
  }
};

template <class FuncType>
struct Calc : public FuncType {
  template <class T>
  inline void operator()(std::vector<T> &result, 
                         const std::vector<T> &a,
                         const std::vector<T> &b) const {
    if (a.size() != b.size()) throw std::invalid_argument("vectors must have same size");
    if (result.size() < a.size()) result.resize(a.size());
#pragma omp parallel for
    for (size_t i = 0; i < a.size(); ++i) result[i] = FuncType::operator()(a[i], b[i]);
  }
};
const static Calc<Sum> sum;


Вторая: прямая реализация

template <class T>
inline void direct_sum(std::vector<T> &result, 
                       const std::vector<T> &a,
                       const std::vector<T> &b) {
  if (a.size() != b.size())  throw std::invalid_argument("vectors must have same size");
  if (result.size() < a.size()) result.resize(a.size());
#pragma omp parallel for
  for (size_t i = 0; i < a.size(); ++i) result[i] = a[i] + b[i];
}


Вопрос, почему первый вариант (sum(v1,v2,v3)) медленнее чем второй (direct_sum(v1,v2,v3)) примерно на 10%? Предполагалось, что компилятор раскроет все inline выражения, и проседания по производительности быть должно.
  • Вопрос задан
  • 1054 просмотра
Решения вопроса 1
jcmvbkbc
@jcmvbkbc
"I'm here to consult you" © Dogbert
Вопрос, почему первый вариант (sum(v1,v2,v3)) медленнее чем второй (direct_sum(v1,v2,v3)) примерно на 10%?

Потому что вы не показали ни опций компилятора, полной програмы, ни способа измерения времени.
Откомпилировав оба примера с вашими опциями я получил идентичный ассемблерный код для цикла вычислений.
Ответ написан
Пригласить эксперта
Ответы на вопрос 2
gbg
@gbg Куратор тега C++
Любые ответы на любые вопросы
Попробуйте начать с теста без omp parallel - ведь вы его даже не настраиваете перед пуском. Если результаты совпадут - настройте. В первом случае, у компилятора явно нет гарантий локальности оператора суммирования.

Можете кстати std::plus проверить, вдруг с ним сработает.

И да, под это дело есть std::transform. Реализации STL в C++11 по стандарту требуют от операндов transform гарантий, разрешающих параллельное исполнение. Остается открытым вопрос с тем, реализуют ли они параллелизм.

И да, не вижу версии с итераторами. Вот она будет быстрее всех ваших.
Ответ написан
heksen
@heksen
А вы дебагер откройте и посмотрите. Мой совет пишите максимально проще. Я вот смотрю и думаю вообще какой смысл в структуру sum запихивать оператор, когда изначально структура должна хранить в себе набор данных.
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы