A impressão unsigned long long int Valor Devolve o Tipo de Resultados Estranhos
-
11-12-2019 - |
Pergunta
Eu tenho um problema ao utilizar o printf
função para imprimir os valores do tipo unsigned long long int
Eu não tenho nenhuma idéia o que está errado.Eu estou usando o Dev-Cpp 4.9.9.2 e Visual Studio 2010 Professional (eu sei que não é o compilador C, mas, de qualquer forma, queria tentar) no Windows 7 Professional de 64 bits.Para a exibição, que eu usei %llu
modificador (de acordo com Como você printf um unsigned long long int(o especificador de formato para unsigned long long int)? mas eu também tentei I64d com efeito...
Em primeiro lugar, eu só queria imprimir mínimo e um valor máximo de unsigned long long int
(usando ULONG_MAX
a partir de limits.h
)
printf("unsigned long long int: \n%llu to %llu \n\n", 0, ULONG_MAX);
Retorna:
unsigned long long int:18446744069414584320 para 1580552164021 (Dev-Cpp)
unsigned long long int:18446744069414584320 para 0 (Visual Studio)
Então eu tentei usar printf
para imprimir dois zeros
printf("unsigned long long int: \n%llu to %llu \n\n", 0, 0);
Retorna:
unsigned long long int:0 a 1580552164021 (Dev-Cpp)
unsigned long long int:0 a 0 (Visual Studio)
Também tentei dois ULONG_MAX
valores
printf("unsigned long long int: \n%llu to %llu \n\n", ULONG_MAX, ULONG_MAX);
Retorna:
unsigned long long int:18446744073709551615 para 1580552164021 (Dev-Cpp)
unsigned long long int:18446744073709551615 para 0 (Visual Studio)
Por isso não se comportam assim?Você poderia explicar-me?
Solução
Isso é errado:
printf("unsigned long long int: \n%llu to %llu \n\n", 0, ULONG_MAX);
Você usa um unsigned long long
especificador de formato, mas você passar um int
e um unsigned long
o valor.Regras da promoção significa que você pode ser superficial por tudo int
de tamanho ou menor, o que faz não aplicar a long long
.
Use lança:
printf("unsigned long long int: \n%llu to %llu \n\n",
0ULL, (unsigned long long) ULONG_MAX);
Explicação: Quando passar argumentos para printf
, de qualquer tipo que possa caber em um int
é promovido para int
, e , em seguida, de qualquer tipo que possa caber em um unsigned int
é promovido para unsigned int
.Também é certo para passar um unsigned tipo de assinado um especificador de formato ou vice-versa, desde que o valor passados pode ser representada usando o tipo especificado pelo especificador de formato.
Então você deve ser cuidadoso com long
e long long
, mas pode ser desleixado com int
, short
, e char
.
A maioria dos compiladores têm configurações para torná-los avisá-lo sobre esse tipo de erro, pois podem ser detectados em tempo de compilação com bastante facilidade;O GCC e o Clang ter -Wformat
o que resulta nos seguintes avisos:
test.c:5: warning: format ‘%llu’ expects type ‘long long unsigned int’, but argument 2 has type ‘int’ test.c:5: warning: format ‘%llu’ expects type ‘long long unsigned int’, but argument 3 has type ‘long unsigned int’
Outras dicas
Você não está passando unsigned long longs
.Você está passando um int
(0) e unsigned long
(ULONG_MAX).Você deve passar para printf()
exatamente o que você promessa de passar a seqüência de caracteres de formato.
Tente isso:
printf("unsigned long long int: \n%llu to %llu \n\n", 0ULL, (unsigned long long)ULONG_MAX);
ULONG_MAX
refere-se a unsigned long
e não para unsigned long long
.Para estes últimos, a utilização ULLONG_MAX
(nota extra L
).
Você precisa alterar o printf()
chamadas assim:
printf("unsigned long long int: \n%llu to %llu \n\n", 0ULL, ULLONG_MAX);
printf("unsigned long long int: \n%llu to %llu \n\n", ULLONG_MAX, ULLONG_MAX);
Isso garante que os argumentos para printf()
corresponder os especificadores de formato.
long long int é um tipo de padrão C99, MSVC não oferece suporte a esta.Tomar um compilador com C99 apoio (como MinGW para Windows) e ele irá funcionar.