Собственный пользовательский тип выражения (или функтор CWise Op?) - PullRequest
0 голосов
/ 17 апреля 2020

рассмотрим эту простую функцию (вид псевдокода):

template <typename Derived>
void f (const MatrixBase<Derived>& input1,
        const MatrixBase<Derived>& input2,
        const MatrixBase<Derived>& input3,
        Vec6& output)
{
    part1(output) = <an expr using the three inputs>;
    part2(output) = <another expr using the three inputs>;
}

Где part1 и part2 - блочные выражения, выбирающие верхние 3 строки и нижние 3 строки output соответственно , Я знаю, что output - это всегда вектор-столбец с 6 коэффициентами.

Я бы хотел избежать передачи аргумента output. Но я также хотел бы избежать возврата явного Vec6, чтобы избежать копий временных данных.

Таким образом, я хотел бы вернуть один из тех магических объектов собственного выражения, которые хранят только ссылку на входные данные и фактически выполнять вычисления только при необходимости.

Мои вопросы:

  1. Стоит ли это того? Учитывая, что это «маленький» 6-мерный вектор (например, в документах говорится, что с маленькими 3-векторами компиляторы обычно могут оптимизировать временные расчеты, поэтому нет смысла их избегать)

  2. Могу ли я реализовать свой тип выражения возврата с помощью специального функтора и CWiseNullaryOp или мне действительно нужен пользовательский тип выражения?

Спасибо


РЕДАКТИРОВАТЬ: таким образом, мы установили, что временные данные оптимизированы (см. Комментарии); который отвечает на вопрос 1 и делает 2 не релевантным.

Однако, ради любопытства и получения дополнительной информации об Эйгене, есть ли у кого-нибудь какие-либо намеки на жизнеспособный тип выражения для моей функции? (предполагая, что стоило придумать один)

1 Ответ

1 голос
/ 18 апреля 2020

Предполагая, что Vec6 был спроектирован "должным образом" (см. например, Rule Of Zero ), тогда, если ваша функция f() принимает форму

Vec6 f(const MatrixBase<Derived>& input1,
       const MatrixBase<Derived>& input2,
       const MatrixBase<Derived>& input3)
{
    Vec6 answer;

    //Manipulate answer
    //...

    return answer; 
}

, тогда с включенной оптимизацией на большинстве современных компиляторов копирование не произойдет. См. Раздел Википедии по оптимизации возвращаемого значения здесь .

(Чтобы проверить теорию с вашим объектом и компилятором, вы можете обернуть Vec6 в свой собственный класс, заставить все конструкторы печатать, когда они и убедитесь, что вы получаете ожидаемое количество вызовов конструктора.)

...