Partilhar via


snprintf, _snprintf, _snprintf_l, _snwprintf, _snwprintf_l

Grava dados formatados em uma cadeia de caracteres. Estão disponíveis versões mais seguras destas funções; ver _snprintf_s, _snprintf_s_l, , _snwprintf_s_snwprintf_s_l.

Sintaxe

int snprintf(
   char *buffer,
   size_t count,
   const char *format [,
   argument] ...
);

int _snprintf(
   char *buffer,
   size_t count,
   const char *format [,
   argument] ...
);

int _snprintf_l(
   char *buffer,
   size_t count,
   const char *format,
   _locale_t locale [,
   argument] ...
);

int _snwprintf(
   wchar_t *buffer,
   size_t count,
   const wchar_t *format [,
   argument] ...
);

int _snwprintf_l(
   wchar_t *buffer,
   size_t count,
   const wchar_t *format,
   _locale_t locale [,
   argument] ...
);

template <size_t size>
int _snprintf(
   char (&buffer)[size],
   size_t count,
   const char *format [,
   argument] ...
); // C++ only

template <size_t size>
int _snprintf_l(
   char (&buffer)[size],
   size_t count,
   const char *format,
   _locale_t locale [,
   argument] ...
); // C++ only

template <size_t size>
int _snwprintf(
   wchar_t (&buffer)[size],
   size_t count,
   const wchar_t *format [,
   argument] ...
); // C++ only

template <size_t size>
int _snwprintf_l(
   wchar_t (&buffer)[size],
   size_t count,
   const wchar_t *format,
   _locale_t locale [,
   argument] ...
); // C++ only

Parâmetros

buffer
Local de armazenamento para a saída.

count
Número máximo de caracteres para gravar. Para as funções que levam wchar_t, é o número máximo de caracteres largos para escrever.

format
Cadeia de caracteres de controle de formato.

argument
Argumentos opcionais.

locale
A localidade a ser usada para formatar a saída.

Para obter mais informações, consulte Sintaxe de especificação de formato: printf e wprintf funções.

Valor de retorno

O número de caracteres que teria sido gravado no buffer se count fosse ignorado. A contagem não inclui o caractere de terminação NULL .

Seja len o comprimento da cadeia de dados formatada, não incluindo a terminação NULL.
Para todas as funções, se len < count, então len os caracteres são armazenados em buffer, um terminador nulo é acrescentado, e o número de caracteres escritos, não incluindo a terminação NULL, é retornado.

As versões de caracteres largos dessas funções retornam o número de caracteres largos gravados, não incluindo a terminação NULL.

Consulte Resumo do comportamento para obter detalhes.

Observações

A partir do UCRT no Visual Studio 2015 e no Windows 10, snprintf não é mais idêntico ao _snprintf. O snprintf comportamento agora é compatível com o padrão C99. A diferença é que, se você ficar sem buffer, null-termina o final do buffer e retorna o número de caracteres que teriam sido necessários, snprintf enquanto _snprintf não null-termina o buffer e retorna -1. Além disso, _snprintf() inclui mais um caractere na saída porque ele não termina nulo o buffer.

  • snprintf e a _snprintf família de funções formatar e armazenar count ou menos caracteres no buffer.
  • snprintf sempre armazena um caractere de terminação NULL , truncando a saída, se necessário.
  • Se snprintf retornar um valor >count - 1, a saída foi truncada.
  • A _snprintf família de funções só acrescenta um caractere de terminação NULL se o comprimento da cadeia formatada for estritamente menor que count caracteres.
  • Cada argument um (se houver) é convertido e é produzido de acordo com a especificação de formato correspondente em format. O formato consiste em caracteres comuns e tem a mesma forma e função que o argumento format para printf. Se a cópia ocorrer entre cadeias de caracteres que se sobrepõem, o comportamento será indefinido.

Resumo do comportamento

Para a tabela a seguir:

  • Seja sizeOfBuffer do tamanho de buffer. Se a função usa um char buffer, o tamanho é em bytes. Se a função usa um wchar_t buffer, o tamanho especifica o número de palavras de 16 bits.
  • Seja len o tamanho dos dados formatados. Se a função usa um char buffer, o tamanho é em bytes. Se a função usa um wchar_t buffer, o tamanho especifica o número de palavras de 16 bits.
  • Caracteres referem-se a char caracteres para funções que usam um char buffer e a wchar_t caracteres para funções que usam um wchar_t buffer.
  • Para obter mais informações sobre o manipulador de parâmetros inválido, consulte Validação de parâmetros.
Condição Comportamento Valor de retorno errno Invoca manipulador de parâmetros inválido
Sucesso Grava os caracteres no buffer usando a cadeia de caracteres de formato especificado. O número de caracteres escritos. N/A Não
Erro de codificação durante a formatação Se o processamento do especificador sde cadeia de caracteres , Sou Z, o processamento da especificação de formato parar, um NULL será colocado no início do buffer. -1 EILSEQ (42) Não
Erro de codificação durante a formatação Se processar o especificador c de caracteres ou C, o caractere inválido será ignorado. O número de caracteres escritos não é incrementado para o caractere ignorado, nem são gravados dados para ele. O processamento da especificação de formato continua depois de ignorar o especificador com o erro de codificação. O número de caracteres gravados, não incluindo a terminação NULL. EILSEQ (42) Não
buffer == NULL e count != 0 Se a execução continuar depois que o manipulador de parâmetros inválido for executado, definirá errno e retornará um valor negativo. -1 EINVAL (22) Sim
count == 0 O número de caracteres que teriam sido escritos, não incluindo o encerramento NULL. Você pode usar esse resultado para alocar espaço de buffer suficiente para a cadeia de caracteres e uma terminação NULLe, em seguida, chamar a função novamente para preencher o buffer. N/A Não
count < 0 Não seguro: o valor é tratado como não assinado, provavelmente criando um valor grande que resulta na substituição da memória que segue o buffer. O número de caracteres escritos N/A Não
count < sizeOfBuffer e len <= count Todos os dados são gravados e uma terminação NULL é anexada. O número de caracteres gravados, não incluindo a terminação NULL. N/A Não
count < sizeOfBuffer e len > count Os primeiros count-1 caracteres são escritos seguidos por um terminador nulo. O número de caracteres que teriam sido gravados correspondeu count ao número de caracteres para a saída, não incluindo o terminador nulo. N/A Não
count >= sizeOfBuffer e len < sizeOfBuffer Todos os dados são gravados com uma terminação NULL. O número de caracteres gravados, não incluindo a terminação NULL. N/A Não
count >= sizeOfBuffer e len >= sizeOfBuffer Não seguro: Substitui a memória que segue o buffer. O número de caracteres gravados, não incluindo a terminação NULL. N/A Não
format == NULL Nenhum dado é gravado. Se a execução continuar depois que o manipulador de parâmetros inválido for executado, definirá errno e retornará um valor negativo. -1 EINVAL (22) Sim

Para obter informações sobre esses e outros códigos de erro, consulte _doserrno, errno, _sys_errliste _sys_nerr.

Importante

Certifique-se de que format não é uma cadeia de caracteres definida pelo usuário. Como as funções não garantem terminação _snprintf nula — em particular, quando o valor de retorno é count—, certifique-se de que elas sejam seguidas pelo código que adiciona o terminador nulo. Para obter mais informações, consulte Evitando saturações de buffer.

A partir do Windows 10 versão 2004 (build 19041), a família de funções imprime printf números de ponto flutuante exatamente representáveis de acordo com as regras IEEE 754 para arredondamento. Em versões anteriores do Windows, números de ponto flutuante exatamente representáveis terminando em '5' sempre arredondavam para cima. IEEE 754 afirma que eles devem arredondar para o dígito par mais próximo (também conhecido como "Arredondamento do Banqueiro"). Por exemplo, ambos printf("%1.0f", 1.5) e printf("%1.0f", 2.5) deve arredondar para 2. Anteriormente, 1,5 arredondava para 2 e 2,5 arredondava para 3. Esta alteração afeta apenas números exatamente representáveis. Por exemplo, 2.35 (que, quando representado na memória, está mais próximo de 2.35000000000000008) continua a arredondar para 2.4. O arredondamento feito por essas funções agora também respeita o modo de arredondamento de ponto flutuante definido pela fesetround. Anteriormente, o arredondamento sempre escolhia o FE_TONEAREST comportamento. Essa alteração afeta apenas os programas criados usando o Visual Studio 2019 versão 16.2 e posterior. Para usar o comportamento de arredondamento de ponto flutuante herdado, vincule-se a legacy_stdio_float_rounding.obj.

_snwprintfé uma versão de caracteres largos de ; os argumentos de ponteiro para _snprintf são cadeias de _snwprintfcaracteres largos. A deteção de erros de codificação em _snwprintf pode diferir da deteção em _snprintf. _snwprintf, assim como swprintf, grava a saída em uma cadeia de caracteres em vez de um destino do tipo FILE.

As versões dessas funções que têm o sufixo _l são idênticas, exceto que elas usam o parâmetro locale passado em vez da localidade thread atual.

Em C++, essas funções têm sobrecargas de modelo que invocam as contrapartes mais novas e mais seguras. Para obter mais informações, consulte Sobrecargas de modelo seguro.

Mapeamentos de rotina de texto genérico

Tchar.h rotina _UNICODE e _MBCS não definido _MBCS definido _UNICODE definido
_sntprintf _snprintf _snprintf _snwprintf
_sntprintf_l _snprintf_l _snprintf_l _snwprintf_l

Requerimentos

Rotina Cabeçalho obrigatório
snprintf, _snprintf, _snprintf_l <stdio.h>
_snwprintf, _snwprintf_l <stdio.h> ou <wchar.h>

Para obter mais informações sobre compatibilidade, consulte Compatibilidade.

Exemplo

// crt_snprintf.c
// compile with: /W3
#include <stdio.h>
#include <stdlib.h>

#if !defined(__cplusplus)
typedef int bool;
const bool true = 1;
const bool false = 0;
#endif

#define FAIL 0 // change to 1 and see what happens

int main(void)
{
   char buffer[200];
   const static char s[] = "computer"
#if FAIL
"computercomputercomputercomputercomputercomputercomputercomputer"
"computercomputercomputercomputercomputercomputercomputercomputer"
"computercomputercomputercomputercomputercomputercomputercomputer"
"computercomputercomputercomputercomputercomputercomputercomputer"
#endif
   ;
   const char c = 'l';
   const int i = 35;
#if FAIL
   const double fp = 1e300; // doesn't fit in the buffer
#else
   const double fp = 1.7320534;
#endif
   /* !subtract one to prevent "squeezing out" the terminal null! */
   const int bufferSize = sizeof(buffer)/sizeof(buffer[0]) - 1;
   int bufferUsed = 0;
   int bufferLeft = bufferSize - bufferUsed;
   bool bSuccess = true;
   buffer[0] = 0;

   /* Format and print various data: */

   if (bufferLeft > 0)
   {
      int perElementBufferUsed = _snprintf(&buffer[bufferUsed],
      bufferLeft, "   String: %s\n", s ); // C4996
      // Note: _snprintf is deprecated; consider _snprintf_s instead
      if (bSuccess = (perElementBufferUsed >= 0))
      {
         bufferUsed += perElementBufferUsed;
         bufferLeft -= perElementBufferUsed;
         if (bufferLeft > 0)
         {
            int perElementBufferUsed = _snprintf(&buffer[bufferUsed],
            bufferLeft, "   Character: %c\n", c ); // C4996
            if (bSuccess = (perElementBufferUsed >= 0))
            {
               bufferUsed += perElementBufferUsed;
               bufferLeft -= perElementBufferUsed;
               if (bufferLeft > 0)
               {
                  int perElementBufferUsed = _snprintf(&buffer
                  [bufferUsed], bufferLeft, "   Integer: %d\n", i ); // C4996
                  if (bSuccess = (perElementBufferUsed >= 0))
                  {
                     bufferUsed += perElementBufferUsed;
                     bufferLeft -= perElementBufferUsed;
                     if (bufferLeft > 0)
                     {
                        int perElementBufferUsed = _snprintf(&buffer
                        [bufferUsed], bufferLeft, "   Real: %f\n", fp ); // C4996
                        if (bSuccess = (perElementBufferUsed >= 0))
                        {
                           bufferUsed += perElementBufferUsed;
                        }
                     }
                  }
               }
            }
         }
      }
   }

   if (!bSuccess)
   {
      printf("%s\n", "failure");
   }
   else
   {
      /* !store null because _snprintf doesn't necessarily (if the string
       * fits without the terminal null, but not with it)!
       * bufferUsed might be as large as bufferSize, which normally is
       * like going one element beyond a buffer, but in this case
       * subtracted one from bufferSize, so we're ok.
       */
      buffer[bufferUsed] = 0;
      printf( "Output:\n%s\ncharacter count = %d\n", buffer, bufferUsed );
   }
   return EXIT_SUCCESS;
}
Output:
   String: computer
   Character: l
   Integer: 35
   Real: 1.732053

character count = 69

Ver também

E/S de fluxo
sprintf, _sprintf_l, swprintf, _swprintf_l, __swprintf_l
fprintf, _fprintf_l, fwprintf, _fwprintf_l
printf, _printf_l, wprintf, _wprintf_l
scanf, _scanf_l, wscanf, _wscanf_l
sscanf, _sscanf_l, swscanf, _swscanf_l
vprintf funções