¿Por const para la conversión implícita?
-
29-09-2019 - |
Pregunta
Después de una extensa lectura de ISO / IEC 14882, lenguaje de programación - C ++ todavía estoy seguro de por qué se necesita const
para la conversión implícita de un tipo definido por el usuario con un único constructor sin argumentos como el siguiente
#include <iostream>
class X {
public:
X( int value ) {
printf("constructor initialized with %i",value);
}
}
void implicit_conversion_func( const X& value ) {
//produces "constructor initialized with 99"
}
int main (int argc, char * const argv[]) {
implicit_conversion_func(99);
}
Comenzando con la sección 4 línea 3
Una expresión e se puede convertir implícitamente a un tipo T si y sólo si la declaración T t = e; es bien formado, por alguna variable inventado t temporal (8,5). Ciertas construcciones de lenguaje requieren que una expresión puede convertir en un valor booleano. Una expresión e apareciendo en contexto tal se dice que ser convertidos contextualmente a bool y está bien formado si y sólo si la declaración bool t (e); es bien formado, por alguna variable inventado t temporal (8,5). El efecto de cualquiera de conversión implícita es la misma que la realización de la declaración y la inicialización y a continuación, utilizando la variable temporal como el resultado de la conversión. El resultado es un lvalue si T es un tipo de referencia lvalue (8.3.2), y un valor p de otra manera. La expresión E se utiliza como un valor-I si y sólo si la inicialización se utiliza como un valor-I.
Después de haber encontrado la sección sobre inicializadores relacionadas con los tipos definidos por el usuario en 8,5 línea 6
Si un programa llama para la inicialización por defecto de un objeto de un tipo T-const cualificado, T serán del tipo de clase con un constructor por defecto proporcionado por el usuario.
Finalmente acabé en 12,3 línea 2 acerca de las conversiones definidas por el usuario que los estados
conversiones definidas por el usuario se aplica sólo donde están los inequívoca (10.2, 12.3.2).
No hace falta decir, 10.2 y 12.3.2 no respondió a mi pregunta.
- ¿Alguien puede arrojar algo de luz sobre el efecto que tiene sobre
const
conversiones implícitas? - ¿El uso de
const
hacer la conversión "inequívoca" por 12,3 línea 2? - ¿El
const
alguna manera afecta lvalue vs rvalue hablamos en la sección 4?
Solución
En realidad no tiene mucho que ver con el bienestar de conversión implícita ??em>. Por otra parte, en realidad no tiene mucho que ver con conversiones . Realmente se trata de rvalues ?? vs lvalues ??.
Al convertir a 99
tipo X
, el resultado es un rvalue . En los resultados de C ++ de conversiones son siempre rvalues ??(a menos que convertir a tipo de referencia). Es ilegal en C ++ para adjuntar referencias no const a rvalues.
Por ejemplo, este código no compila
X& r = X(99); // ERROR
porque intenta adjuntar una referencia no const a un valor p. Por otra parte, este código está bien
const X& cr = X(99); // OK
debido a que es perfectamente bien para adjuntar una referencia constante a un valor de lado derecho.
Lo mismo sucede en su código. El hecho de que se trata de una conversión implícita es un poco fuera de lugar. Puede reemplazar la conversión implícita con una explícita uno
implicit_conversion_func(X(99));
y terminan con la misma situación: con const
compila, sin const
no lo hace.
Una vez más, la única función de la conversión (explícito o implícito) juega aquí es que nos ayuda a producir un valor de lado derecho. En general, se puede producir un valor de lado derecho de alguna otra manera y correr en la misma edición
int &ir = 3 + 2; // ERROR
const int &cir = 3 + 2; // OK
Otros consejos
Según la sección 5.2.2 párrafo 5, cuando un argumento de una función es del tipo de referencia const
, una variable temporal se introduce automáticamente si es necesario. En el ejemplo, el resultado de rvalue X(99)
tiene que ser puesto en una variable temporal para que esa variable puede ser pasado por referencia a const
implicit_conversion_func
.