¿Es más eficiente devolver por referencia de valor?

Resuelto Neil G asked hace 15 años • 2 respuestas

Por ejemplo:

Beta_ab&& Beta::toAB() const {
    return move(Beta_ab(1, 1));
}
Neil G avatar Jul 13 '09 01:07 Neil G
Aceptado
Beta_ab&&
Beta::toAB() const {
    return move(Beta_ab(1, 1));
}

Esto devuelve una referencia pendiente, al igual que con el caso de referencia lvalue. Después de que la función regrese, el objeto temporal se destruirá. Deberías devolver Beta_abpor valor, como el siguiente

Beta_ab
Beta::toAB() const {
    return Beta_ab(1, 1);
}

Ahora, está moviendo correctamente un Beta_abobjeto temporal al valor de retorno de la función. Si el compilador puede, evitará el movimiento por completo mediante el uso de RVO (optimización del valor de retorno). Ahora puedes hacer lo siguiente

Beta_ab ab = others.toAB();

Y moverá la construcción temporal a ab, o realizará RVO para omitir mover o copiar por completo. Le recomiendo que lea BoostCon09 Rvalue References 101 que explica el asunto y cómo (N)RVO interactúa con esto.


Su caso de devolver una referencia de valor sería una buena idea en otras ocasiones. Imagine que tiene una getAB()función que invoca con frecuencia de forma temporal. No es óptimo hacer que devuelva una referencia de valor constante para los temporales de valor r. Puedes implementarlo así.

struct Beta {
  Beta_ab ab;
  Beta_ab const& getAB() const& { return ab; }
  Beta_ab && getAB() && { return move(ab); }
};

Tenga en cuenta que moveen este caso no es opcional, porque abno es un valor local automático ni temporal. Ahora, el calificador ref && dice que la segunda función se invoca en los temporales rvalue, haciendo el siguiente movimiento, en lugar de copiar

Beta_ab ab = Beta().getAB();
Johannes Schaub - litb avatar Jul 12 '2009 19:07 Johannes Schaub - litb