Advertencia del compilador (nivel 3) C4839
uso no estándar de la clase "type" como argumento de una función variádica
Las clases o estructuras que se pasan a una función variádica como printf
se deben poder copiar trivialmente. Al pasar objetos de este tipo, el compilador simplemente realiza una copia bit a bit y no llama al constructor ni al destructor.
Esta advertencia está disponible a partir de Visual Studio 2017.
Ejemplo
El ejemplo siguiente genera la advertencia C4839:
// C4839.cpp
// compile by using: cl /EHsc /W3 C4839.cpp
#include <atomic>
#include <memory>
#include <stdio.h>
int main()
{
std::atomic<int> i(0);
printf("%i\n", i); // error C4839: non-standard use of class 'std::atomic<int>'
// as an argument to a variadic function
// note: the constructor and destructor will not be called;
// a bitwise copy of the class will be passed as the argument
// error C2280: 'std::atomic<int>::atomic(const std::atomic<int> &)':
// attempting to reference a deleted function
}
Para corregir el error, puede llamar a una función miembro que devuelva un tipo que se pueda copiar trivialmente
std::atomic<int> i(0);
printf("%i\n", i.load());
En el caso de las cadenas compiladas y administradas por medio de CStringW
, se debe usar el operator LPCWSTR()
proporcionado para convertir un objeto CStringW
en el puntero C esperado por la cadena de formato.
CStringW str1;
CStringW str2;
// ...
str1.Format("%s", static_cast<LPCWSTR>(str2));