String literal coincide con bool overload en lugar de std:: string
Estoy tratando de escribir una clase de C++ que tiene algunos métodos sobrecargados:
class Output
{
public:
static void Print(bool value)
{
std::cout << value ? "True" : "False";
}
static void Print(std::string value)
{
std::cout << value;
}
};
Ahora digamos que llamo al método de la siguiente manera:
Output::Print("Hello World");
Este es el resultado
Verdadero
Entonces, ¿por qué, cuando he definido que el método puede aceptar booleano y string, utiliza la sobrecarga booleana cuando paso un valor no booleano?
EDIT: Vengo de un entorno C # / Java, ¡muy nuevo en C++!
2 answers
"Hello World"
es un literal de cadena de tipo " array of 12 const char
" que se puede convertir en un "puntero a const char
" que a su vez se puede convertir en un bool
. Eso es precisamente lo que está sucediendo. El compilador prefiere esto a usar el constructor de conversión de std::string
.
Una secuencia de conversión que involucra a un constructor de conversión se conoce como secuencia de conversión definida por el usuario. La conversión de "Hello World"
a bool
es una secuencia de conversión estándar . La norma establece que un la secuencia de conversión estándar siempre es mejor que una secuencia de conversión definida por el usuario(§13.3.3.2/2):
Una secuencia de conversión estándar (13.3.3.1.1) es una mejor secuencia de conversión que una secuencia de conversión definida por el usuario o una secuencia de conversión de puntos suspensivos
Este análisis de "mejor secuencia de conversión" se realiza para cada argumento de cada función viable (y solo tiene un argumento) y la mejor función se elige por resolución de sobrecarga.
Si si desea asegurarse de que se llama a la versión std::string
, debe darle un std::string
:
Output::Print(std::string("Hello World"));
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-02-08 10:23:23
FWIW, se puede direccionar de esta manera (si se pueden usar plantillas), si no desea agregar sobrecargas para const char*
.
#include <iostream>
#include <string>
#include <type_traits>
template <typename Bool,
typename T = std::enable_if_t<std::is_same<Bool, bool>{}>>
void foo(Bool)
{
std::cerr << "bool\n";
}
void foo(const std::string&)
{
std::cerr << "string\n";
}
int main()
{
foo("bar");
foo(false);
}
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-03-16 12:26:34