‘%d’ espera un argumento del tipo ‘int’, pero el argumento 2 tiene el tipo ‘long unsigned int’ [-Wformat=] [duplicate]

4 minutos de lectura

avatar de usuario
luizgsa13

Sigo recibiendo advertencias de compilación, pero no sé cómo solucionarlo:

'%d' espera un argumento del tipo 'int', pero el argumento 2 tiene el tipo 'long unsigned int' [

The program runs fine but I still get the compile warnings:

/* Sizeof.c--Program to tell byte size of the C variable */
#include <stdio.h>

int main(void) {
    printf("\nA Char is %d bytes", sizeof( char ));
    printf("\nAn int is %d bytes", sizeof( int ));
    printf("\nA short is %d bytes", sizeof( short ));
    printf("\nA long is %d bytes", sizeof( long ));
    printf("\nA long long is %d bytes\n", sizeof( long long ));
    printf("\nAn unsigned Char is %d bytes", sizeof( unsigned char ));
    printf("\nAn unsigned int is %d bytes", sizeof( unsigned int));
    printf("\nAn unsigned short is %d bytes", sizeof( unsigned short ));
    printf("\nAn unsigned long is %d bytes", sizeof( unsigned long ));
    printf("\nAn unsigned long long is %d bytes\n",
            sizeof( unsigned long long ));
    printf("\nfloat is %d bytes", sizeof( float ));
    printf("\nA double is %d bytes\n", sizeof( double ));
    printf("\nA long double is %d bytes\n", sizeof( long double ));

    return 0;

}

  • replace %d with %ld

    – storenth

    Aug 19, 2020 at 12:45

user avatar
Shafik Yaghmour

sizeof returns size_t you need to use %zu for the format string instead of %d. The type of unsigned integer of size_t can vary (depending on platform) and may not be long unsigned int everywhere, which is covered in the draft C99 standard section 6.5.3.4 The sizeof operator paragraph 4:

The value of the result is implementation-defined, and its type (an unsigned integer type)
is size_t, defined in (and other headers).

Also note that using the wrong format specifier for printf is undefined behavior, which is covered in section 7.19.6.1 The fprintf function, which also covers printf with respect to format specifiers says:

If a conversion specification is invalid, the behavior is undefined.248) If any argument is not the correct type for the corresponding conversion specification, the behavior is undefined.

Update

Visual Studio does not support the z format specifier:

The hh, j, z, and t length prefixes are not supported.

the correct format specifier in this case would be %Iu.

  • In GCC 4.8.1 on Windows I get error: “unknown conversion type character ‘z’ in format” when printf’ing %zu.

    – Czarek Tomczak

    Feb 18, 2014 at 13:57

  • @CzarekTomczak updated answer, probably related.

    – Shafik Yaghmour

    Feb 18, 2014 at 14:25


  • Thanks Shafik. Unfortunately none of this is cross platform. I have to cast size_t to (unsigned long) for the code to work on both Linux and Windows. On Linux when using %Iu (I as Integer) getting error “format ‘%u’ expects argument of type ‘unsigned int’”.

    – Czarek Tomczak

    Feb 18, 2014 at 14:35


  • @CzarekTomczak you are probably better off using an ifdef based on the OS to set a format specifier variable and use that instead.

    – Shafik Yaghmour

    Feb 18, 2014 at 14:40


  • For now I will just stick with the cast, as this is only some debugging info, it’s not that important. But I will keep it in my mind on how to do it the right way in the future. Thanks again.

    – Czarek Tomczak

    Feb 18, 2014 at 14:42

user avatar
Fiddling Bits

The compiler is warning you that you may suffer a loss of precision. That is, the format specifier that you’re using to print a sizeof, %d, is not capable of printing the full range of size_t. Change %d to %zu and your warning will go away.

  • It’s actually not just a loss of precision, it’s a possible segfault or stack overwrite. Passing a size_t on most 64-bit systems will push 8 bytes onto the stack whereas %d will read only 4 bytes. It’s simply an accident that his program doesn’t crash; the bottom 4 bytes of the 8 bytes pushed happened to contain the right value (may not be the case on a big-endian system) and printf didn’t read any more bytes afterwards.

    – Anonymous1847

    Sep 24, 2020 at 22:18

  • Unknown conversion z.

    – john

    Feb 23, 2021 at 13:36

i had the same problem in Linux. the same program runs without error in windows (means ‘%d’ worked without error), but for linux i had to replace all the ‘%d’ with’%lu’ to run the program.

¿Ha sido útil esta solución?

Esta web utiliza cookies propias y de terceros para su correcto funcionamiento y para fines analíticos y para mostrarte publicidad relacionada con sus preferencias en base a un perfil elaborado a partir de tus hábitos de navegación. Al hacer clic en el botón Aceptar, acepta el uso de estas tecnologías y el procesamiento de tus datos para estos propósitos. Configurar y más información
Privacidad