Я все делаю правильно?
Вы все делаете правильно.Проблема в реализации Visual Studio std::valarray
.
Почему std::valarray
не работает должным образом в Visual Studio 2015?
Просто откройте реализацию любогоvalarray
оператор, например operator+
.Вы увидите что-то вроде (после расширения макроса):
template<class _Ty> inline
valarray<_Ty> operator+(const valarray<_Ty>& _Left,
const valarray<_Ty>& _Right)
{
valarray<TYPE> _Ans(_Left.size());
for (size_t _Idx = 0; _Idx < _Ans.size(); ++_Idx)
_Ans[_Idx] = _Left[_Idx] + _Right[_Idx];
return (_Ans)
}
Как видите, создается новый объект, в который копируется результат операции.Там действительно нет оптимизации.Я не знаю почему, но это факт.Похоже, что в Visual Studio std::valarray
был добавлен только для совместимости.
Для сравнения рассмотрим реализацию GNU .Как видите, каждый оператор возвращает класс шаблона _Expr , который содержит только операцию , но не содержит данных.Реальные вычисления выполняются в операторе присваивания и, более конкретно, в функции __ valarray_copy .Таким образом, пока вы не выполните назначение, все действия выполняются с прокси-объектом _Expr
.Только когда вызывается operator=
, операция, сохраненная в _Expr
, выполняется в одном цикле.Вот почему вы получаете такие хорошие результаты с g ++.
Как мне решить проблему?
Вам нужно найти подходящую реализацию std::valarray
наИнтернет или вы можете написать свой собственный.Вы можете использовать реализацию GNU в качестве примера.