nullptr o NULL
nullptr
y NULL
son utilizados en C++ para representar un puntero nulo, pero hay algunas diferencias importantes:
Tipo:
nullptr
es de tipostd::nullptr_t
.NULL
es a menudo definido como0
o((void*)0)
. En C++,NULL
no es un tipo específico, simplemente es un alias para el literal entero cero.
Contexto de Sobrecarga:
nullptr
es un valor literal y puede ser usado en contextos donde se necesita un puntero nulo. También es más fuertemente tipado y no se convierte automáticamente a otros tipos.NULL
es a menudo definido como0
, y puede causar problemas de ambigüedad cuando se usa en contextos donde la sobrecarga de funciones o plantillas está involucrada.
C++11:
nullptr
fue introducido en C++11 como una mejora para abordar problemas relacionados conNULL
.
Seguridad:
nullptr
es más seguro ya que tiene un tipo propio y no se convierte automáticamente a otros tipos. Esto puede prevenir errores sutiles que podrían ocurrir con la ambigüedad de tipos.NULL
puede ser menos seguro porque es simplemente un alias para0
, y puede llevar a ambigüedades en contextos complejos.
Dado que nullptr
es más moderno y ofrece mayor seguridad de tipo, se recomienda su uso en código nuevo de C++.
Ambigüedad de carga
Ya que nullptr
esta diseñado para evitar la conversión automática a otros tipos de punteros.
void func(int *ptr) {
std::cout << "Función para puntero int" << std::endl;
}
void func(double *ptr) {
std::cout << "Función para puntero double" << std::endl;
}
int main() {
func(nullptr); // Error, ambigüedad con NULL que podría convertirse a int o double
return 0;
}
En este caso, si intentas pasar nullptr a una función sobrecargada, el compilador te dará un error porque nullptr no se convierte automáticamente y no está claro cuál de las funciones sobrecargadas debería llamarse. Esto ayuda a evitar problemas de ambigüedad y mejora la seguridad del tipo en el código.
Para solucionar el problema de ambigüedad al llamar a la función func(nullptr)
, puedes proporcionar información adicional al compilador sobre qué versión de la función se desea llamar. Puedes hacerlo mediante una conversión explícita de nullptr a un tipo específico de puntero.
#include <iostream>
void func(int *ptr) {
std::cout << "Función para puntero int" << std::endl;
}
void func(double *ptr) {
std::cout << "Función para puntero double" << std::endl;
}
int main() {
// Llamada a func con nullptr convertido explícitamente a int*
func(static_cast<int*>(nullptr));
return 0;
}
Al proporcionar una conversión explícita mediante static_cast<int*>(nullptr)
, se esta indicando al compilador que deseas llamar a la versión de la función que acepta un puntero a int. Esta solución elimina la ambigüedad y le da al compilador la información necesaria para elegir la función correcta.