O padrão C99 possui tipos inteiros com tamanho de bytes como int64_t. Estou usando o seguinte código:
#include <stdio.h>
#include <stdint.h>
int64_t my_int = 999999999999999999;
printf("This is my_int: %I64d\n", my_int);
e recebo este aviso do compilador:
warning: format ‘%I64d’ expects type ‘int’, but argument 2 has type ‘int64_t’
Eu tentei com:
printf("This is my_int: %lld\n", my_int); // long long decimal
Mas eu recebo o mesmo aviso. Estou usando este compilador:
~/dev/c$ cc -v
Using built-in specs.
Target: i686-apple-darwin10
Configured with: /var/tmp/gcc/gcc-5664~89/src/configure --disable-checking --enable-werror --prefix=/usr --mandir=/share/man --enable-languages=c,objc,c++,obj-c++ --program-transform-name=/^[cg][^.-]*$/s/$/-4.2/ --with-slibdir=/usr/lib --build=i686-apple-darwin10 --program-prefix=i686-apple-darwin10- --host=x86_64-apple-darwin10 --target=i686-apple-darwin10 --with-gxx-include-dir=/include/c++/4.2.1
Thread model: posix
gcc version 4.2.1 (Apple Inc. build 5664)
Qual formato devo usar para imprimir a variável my_int sem ter um aviso?
Respostas:
Para o
int64_t
tipo:para o
uint64_t
tipo:você também pode usar
PRIx64
para imprimir em hexadecimal.cppreference.com tem uma lista completa de macros disponíveis para todos os tipos, incluindo
intptr_t
(PRIxPTR
). Existem macros separadas para scanf, comoSCNd64
.Uma definição típica de PRIu16 seria
"hu"
, portanto, a concatenação implícita de constante de sequência acontece em tempo de compilação.Para que seu código seja totalmente portátil, você deve usar
PRId32
e assim por diante para impressãoint32_t
e"%d"
similares ou para impressãoint
.fonte
#define __STDC_FORMAT_MACROS
incluir antesinttypes.h
.PRId64
é uma macro que se traduz internamente"lld"
. Assim, é tão bom quanto escrevendoprintf("%lld\n", t);
Veja a descrição: qnx.com/developers/docs/6.5.0/...ld
. Portabilidade é o motivo da macro.O caminho C99 é
Ou você poderia lançar!
Se você está preso à implementação do C89 (principalmente o Visual Studio), pode usar um código aberto
<inttypes.h>
(e<stdint.h>
): http://code.google.com/p/msinttypes/fonte
#if !defined(__cplusplus) || defined(__STDC_FORMAT_MACROS)
Com C99, o
%j
modificador de comprimento também pode ser usado com a família de funções printf para imprimir valores do tipoint64_t
euint64_t
:Compilar esse código com
gcc -Wall -pedantic -std=c99
não produz avisos, e o programa imprime a saída esperada:Isto é de acordo com
printf(3)
meu sistema Linux (a página de manual diz especificamente quej
é usada para indicar uma conversão para umintmax_t
ouuintmax_t
; no meu stdint.h, ambosint64_t
eintmax_t
são digitados exatamente da mesma maneira e da mesma forma parauint64_t
). Não tenho certeza se isso é perfeitamente portátil para outros sistemas.fonte
%jd
prnts anintmax_t
, a chamada correta seriaprintf("a=%jd (0x%jx)", (intmax_t) a, (intmax_t) a)
. Não há garantia de queint64_t
eintmax_t
sejam do mesmo tipo e, se não forem, o comportamento será indefinido.%jd
para imprimirint64_t
valores se você convertê-los explicitamenteintmax_t
antes de passá-los paraprintf
:printf("a=%jd\n", (intmax_t)a)
. Isso evita a feiura (IMHO) das<inttypes.h>
macros. Claro que isso pressupõe que os seus suportes de implementação%jd
,int64_t
eintmax_t
, todos os quais foram adicionados pelo C99.Vindo do mundo incorporado, onde nem o uclibc está sempre disponível, e codifica como
uint64_t myval = 0xdeadfacedeadbeef; printf("%llx", myval);
está imprimindo sua porcaria ou não está funcionando - eu sempre uso um pequeno auxiliar, que me permite despejar corretamente uint64_t hex:
fonte
No ambiente Windows, use
no Linux, use
fonte
%lld
é o formato paralong long int
, que não é necessariamente o mesmo queint64_t
.<stdint.h>
possui uma macro para o formato correto paraint64_t
; veja a resposta de ouah .long long
é pelo menos 64 bits,printf("%lld", (long long)x);
deve funcionar, exceto talvez -0x8000000000000000, que não pode ser representável comolong long
se esse tipo não estivesse usando o complemento de dois.long long
).//VC6.0 (386 e melhor)
Saudações.
fonte