Aracılığıyla paylaş


vsnprintf, _vsnprintf, _vsnprintf_l, _vsnwprintf, , _vsnwprintf_l

Bir bağımsız değişken listesinin işaretçisini kullanarak biçimlendirilmiş çıktı yazın. Bu işlevlerin daha güvenli sürümleri mevcuttur; bkz. vsnprintf_s, _vsnprintf_s, _vsnprintf_s_l_vsnwprintf_s, , _vsnwprintf_s_l.

Sözdizimi

int vsnprintf(
   char *buffer,
   size_t count,
   const char *format,
   va_list argptr
);

int _vsnprintf(
   char *buffer,
   size_t count,
   const char *format,
   va_list argptr
);

int _vsnprintf_l(
   char *buffer,
   size_t count,
   const char *format,
   _locale_t locale,
   va_list argptr
);

int _vsnwprintf(
   wchar_t *buffer,
   size_t count,
   const wchar_t *format,
   va_list argptr
);

int _vsnwprintf_l(
   wchar_t *buffer,
   size_t count,
   const wchar_t *format,
   _locale_t locale,
   va_list argptr
);

template <size_t size>
int vsnprintf(
   char (&buffer)[size],
   size_t count,
   const char *format,
   va_list argptr
); // C++ only

template <size_t size>
int _vsnprintf(
   char (&buffer)[size],
   size_t count,
   const char *format,
   va_list argptr
); // C++ only

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

template <size_t size>
int _vsnwprintf(
   wchar_t (&buffer)[size],
   size_t count,
   const wchar_t *format,
   va_list argptr
); // C++ only

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

Parametreler

buffer
Çıkış için Depolama konum.

count
Yazacak karakter sayısı üst sınırı. öğesini alan wchar_tişlevler için, yazacak geniş karakter sayısıdır.

format
Biçim belirtimi.

argptr
Bağımsız değişken listesinin işaretçisi.

locale
Kullanılacak yerel ayar.

Daha fazla bilgi için bkz . Biçim belirtimi söz dizimi.

Dönüş değeri

Sonlandırıcı NULLdahil değil, yazılan karakter sayısı veya bir çıkış hatası oluşursa negatif bir değer.

Ayrıntılar için bkz . Davranış özeti .

Açıklamalar

Bu işlevlerin her biri bir bağımsız değişken listesinin işaretçisini alır, ardından verileri biçimlendirip tarafından bufferişaret edilen belleğe karakter yazarcount. İşlev vsnprintf , çıkışı kesse bile her zaman null bir sonlandırıcı yazar. ve _vsnwprintfkullandığınızda _vsnprintf arabellek null olarak sonlandırılır, ancak sonunda yer varsa (yani, yazacak karakter sayısı küçüksecount).

Visual Studio 2015 ve Windows 10'daki UCRT ile başlayarak, vsnprintf artık ile _vsnprintfaynı değildir. vsnprintf işlevi C99 standardına uygundur; _vsnprintf eski kodla geriye dönük uyumluluk için tutulur. Aradaki fark, arabelleğiniz biterse arabelleğin vsnprintf sonunu null-sonlandırır ve gerekli olabilecek karakter sayısını döndürürken _vsnprintf arabelleği null olarak sonlandırmaz ve -1 döndürür. Ayrıca, _vsnprintf() arabelleği null olarak sonlandırmadığından çıkışa bir karakter daha ekler.

Önemli

Belirli tür güvenlik risklerini önlemek için kullanıcı tanımlı bir dize olmadığından emin olun format . Daha fazla bilgi için bkz . Arabellek taşmalarından kaçınma. Windows 10 sürüm 2004 'den (derleme 19041) printf başlayarak, işlev ailesi yuvarlama için IEEE 754 kurallarına göre tam olarak temsil edilebilir kayan nokta numaraları yazdırır. Windows'un önceki sürümlerinde, '5' ile biten tam olarak temsil edilebilir kayan nokta sayıları her zaman yukarı yuvarlanırdı. IEEE 754, en yakın çift rakama ("Bankacı Yuvarlama" olarak da bilinir) yuvarlamaları gerektiğini belirtir. Örneğin, hem hem de printf("%1.0f", 1.5)printf("%1.0f", 2.5) 2'ye yuvarlanmalıdır. Daha önce 1,5 2'ye, 2,5 ise 3'e yuvarlardı. Bu değişiklik yalnızca tam olarak temsil edilebilir sayıları etkiler. Örneğin, 2,35 (bellekte temsil edildiğinde 2,3500000000000000000008'e daha yakındır) 2,4'e kadar yuvarlanmaya devam eder. Bu işlevler tarafından yapılan yuvarlama artık tarafından fesetroundayarlanan kayan nokta yuvarlama moduna da dikkat eder. Daha önce yuvarlama her zaman davranışı seçmişti FE_TONEAREST . Bu değişiklik yalnızca Visual Studio 2019 sürüm 16.2 ve üzeri kullanılarak oluşturulan programları etkiler. Eski kayan nokta yuvarlama davranışını kullanmak için 'legacy_stdio_float_rounding.obj' ile bağlantı sağlayın.

Not

, ve çağrıları _vsnprintfsırasında sonlandırıcı null değere yer olduğundan emin olmak için, _vsnprintf_l_vsnwprintf arabellek uzunluğundan count kesinlikle daha az olduğundan emin olun ve işlevi çağırmadan önce arabelleği null olarak _vsnwprintf_lbaşlatın.

Her vsnprintf zaman sonlandırıcı bir null yazdığından count , parametre arabelleğin boyutuna eşit olabilir.

Bu işlevlerin sonekli _l sürümleri aynıdır, ancak geçerli iş parçacığı yerel ayarı yerine geçirilen yerel ayar parametresini kullanırlar.

C++ dilinde, bu işlevlerin daha yeni ve güvenli karşılıklarını çağıran şablon aşırı yüklemeleri vardır. Daha fazla bilgi için bkz . Güvenli şablon aşırı yüklemeleri.

Davranış özeti

Aşağıdaki tablo için:

  • boyutunun bufferolması gerekirsizeOfBuffer. İşlev bir char arabellek alırsa boyut bayt cinsindendir. İşlev bir wchar_t arabellek alırsa, boyut 16 bit sözcük sayısını belirtir.
  • len Biçimlendirilmiş verilerin boyutu olsun. İşlev bir char arabellek alırsa boyut bayt cinsindendir. İşlev bir wchar_t arabellek alırsa, boyut 16 bit sözcük sayısını belirtir.
  • Karakterler, arabelleğe alınan char işlevlerin karakterlerine wchar_t ve arabelleğe alınan wchar_t işlevlere yönelik karakterlere başvururchar.
  • Geçersiz parametre işleyicisi hakkında daha fazla bilgi için bkz . Parametre Doğrulama.
Koşul Davranış Dönüş değeri errno Geçersiz parametre işleyicisini çağırır
Başarılı Belirtilen biçim dizesini kullanarak karakterleri arabelleğe yazar. Sonlandırıcı null karakteri saymayan, yazılan karakter sayısı. Yok Hayır
Biçimlendirme sırasında kodlama hatası Dize tanımlayıcısı s, , Sveya Z, biçimlendirme belirtimi işleme durdurulursa. -1 EILSEQ (42) Hayır
Biçimlendirme sırasında kodlama hatası Karakter tanımlayıcısı c veya Cişleniyorsa geçersiz karakter atlanır. Yazılan karakter sayısı, atlanan karakter için artırılmıyor ve bu karakter için yazılan veri yok. Biçim belirtimi işleme, tanımlayıcıyı kodlama hatasıyla atladıktan sonra devam eder. Sonlandırıcı NULLdahil değil, yazılan karakter sayısı. EILSEQ (42) Hayır
buffer == NULL ve count != 0 Geçersiz parametre işleyicisi yürütülürken yürütme devam ederse, negatif bir değer ayarlar errno ve döndürür. -1 EINVAL (22) Yes
count == 0 Hiçbir veri yazıldı Sonlandırıcı NULLdahil olmak üzere yazılabilecek karakter sayısı. Dize ve sonlandırıcı NULLiçin yeterli arabellek alanı ayırmak ve ardından arabelleği doldurmak için işlevi yeniden çağırmak için bu sonucu kullanabilirsiniz. Yok Hayır
count < 0 Güvenli değil: değer işaretsiz olarak kabul edilir ve büyük olasılıkla arabelleğinden sonra gelen belleğin üzerine yazılmasıyla sonuçlanan büyük bir değer oluşturur. Yazılan karakter sayısı. Yok Hayır
count < sizeOfBuffer ve len <= count Tüm veriler yazılır ve sonlandırıcı NULL eklenir. Sonlandırıcı NULLdahil değil, yazılan karakter sayısı. Yok Hayır
count < sizeOfBuffer ve len > count İlk count-1 karakterlerin ardından null-terminator yazılır. Yazılmış olabilecek karakter sayısı, null sonlandırıcı dahil olmak üzere çıkış için karakter sayısıyla eşleşmişti count . Yok Hayır
count >= sizeOfBuffer ve len < sizeOfBuffer Tüm veriler sonlandırıcı NULLile yazılır. Sonlandırıcı NULLdahil değil, yazılan karakter sayısı. Yok Hayır
count >= sizeOfBuffer ve len >= sizeOfBuffer Güvenli değil: Arabelleği izleyen belleğin üzerine yazar. Sonlandırıcı NULLdahil değil, yazılan karakter sayısı. Yok Hayır
format == NULL Hiçbir veri yazılmıştır. Geçersiz parametre işleyicisi yürütülürken yürütme devam ederse, negatif bir değer ayarlar errno ve döndürür. -1 EINVAL (22) Yes

Bunlar ve diğer hata kodları hakkında bilgi için bkz. _doserrno, errno, _sys_errlistve _sys_nerr.

Genel metin yordamı eşlemeleri

TCHAR.H Rutin _UNICODE ve _MBCS tanımlanmadı _MBCS Tanımlanan _UNICODE Tanımlanan
_vsntprintf _vsnprintf _vsnprintf _vsnwprintf
_vsntprintf_l _vsnprintf_l _vsnprintf_l _vsnwprintf_l

Gereksinimler

Yordam Gerekli üst bilgi (C) Gerekli üst bilgi (C++)
vsnprintf, _vsnprintf, _vsnprintf_l <stdio.h> <stdio.h> veya <cstdio>
_vsnwprintf, _vsnwprintf_l <stdio.h> veya <wchar.h> <stdio.h>, <wchar.h>, <cstdio>veya <cwchar>

, _vsnprintf_l_vsnwprintf ve _vsnwprintf_l işlevleri Microsoft'a _vsnprintfözeldir. Daha fazla uyumluluk bilgisi için bkz . Uyumluluk.

Örnek: ile geniş karakterler kullanma _vsnwprintf()

// crt_vsnwprintf.c
// compile by using: cl /W3 crt_vsnwprintf.c

// To turn off error C4996, define this symbol:
#define _CRT_SECURE_NO_WARNINGS

#include <stdio.h>
#include <wtypes.h>

#define BUFFCOUNT (10)

void FormatOutput(LPCWSTR formatstring, ...)
{
    int nSize = 0;
    wchar_t buff[BUFFCOUNT];
    memset(buff, 0, sizeof(buff));
    va_list args;
    va_start(args, formatstring);
    // Note: _vsnwprintf is deprecated; consider vsnwprintf_s instead
    nSize = _vsnwprintf(buff, BUFFCOUNT - 1, formatstring, args); // C4996
    wprintf(L"nSize: %d, buff: %ls\n", nSize, buff);
    va_end(args);
}

int main() {
    FormatOutput(L"%ls %ls", L"Hi", L"there");
    FormatOutput(L"%ls %ls", L"Hi", L"there!");
    FormatOutput(L"%ls %ls", L"Hi", L"there!!");
}
nSize: 8, buff: Hi there
nSize: 9, buff: Hi there!
nSize: -1, buff: Hi there!

Bunun yerine vsnprintf kullanırsanız, dar dize parametreleriyle birlikte davranış değişir. count parametresi arabellek boyutunun tamamı olabilir ve dönüş değeri, yeterince büyükse count yazılacak karakter sayısıdır:

Örnek: Dar dizelerle kullanma vsnprintf()

// crt_vsnprintf.c
// compile by using: cl /W4 crt_vsnprintf.c
#include <stdio.h>
#include <stdarg.h> // for va_list, va_start
#include <string.h> // for memset

#define BUFFCOUNT (10)

void FormatOutput(char* formatstring, ...)
{
    int nSize = 0;
    char buff[BUFFCOUNT];
    memset(buff, 0, sizeof(buff));
    va_list args;
    va_start(args, formatstring);
    nSize = vsnprintf(buff, sizeof(buff), formatstring, args);
    printf("nSize: %d, buff: %s\n", nSize, buff);
    va_end(args);
}

int main() {
    FormatOutput("%s %s", "Hi", "there");   //  8 chars + null
    FormatOutput("%s %s", "Hi", "there!");  //  9 chars + null
    FormatOutput("%s %s", "Hi", "there!!"); // 10 chars + null
}
nSize: 8, buff: Hi there
nSize: 9, buff: Hi there!
nSize: 10, buff: Hi there!

Ayrıca bkz.

Akış G/Ç
vprintf işlevleri
Biçim belirtimi söz dizimi: printf ve wprintf işlevleri
fprintf, _fprintf_l, fwprintf, _fwprintf_l
printf, _printf_l, wprintf, _wprintf_l
sprintf, _sprintf_l, swprintf, _swprintf_l, , __swprintf_l
va_arg, va_copy, va_end, va_start