What is wscanf_s in C?

wscanf_s is defined in the wchar.h header file, reads data from stdin, formats it according to the format wide string, and stores the result into the destinations specified by the additional arguments. What makes wscanf_s different from the normal wscanf is that it performs extra run-time checks on the arguments before they are executed.

Syntax

The syntax for the wscanf_s function is declared as follows:

Parameters

The wscanf_s function takes in 1 mandatory argument and then a list of additional arguments:

  • format: The pointer to the format string that may include format specifiers like %ls.

  • ...: These are the optional arguments that correspond to the specifiers used in the format wide string. These arguments are pointers to storage spaces (variables) and must have the same type as their corresponding specifier. This means e.g. if there’s a %ls specifier in the format wide string there should be a wide character pointer in the additional arguments.

Return value

wscanf_s can possibly return one of the two things:

  • Upon successful execution, it returns the number of items filled in the list of additional arguments given in the parameters.

  • If there is a failure during the assignment of arguments or while interpreting an input or if any of the run-time constraints are violated EOF (End Of File) is returned.

Example

The following is an example of how the wscanf_s function takes input from stdin and stores the data in it to several other variables:

wscanf_s reads from the input string sequentially, and we must give the list of arguments in the order specified in the format string.

#define __STDC_WANT_LIB_EXT1__ 1
#include <stdio.h>
#include <wchar.h>
int main ()
{
// variables in which to store data
wchar_t name [15];
wchar_t unit [15];
int amount;
// taking input and storing in variables
// a sample input string would be:
// "Faraz owns 500 acres of land"
// only use wscanf_s if __STDC_LIB_EXT1__ is already defined
#ifdef __STDC_LIB_EXT1__
wscanf_s (L"%ls %*s %d %ls",name,&amount,unit);
#endif
// use normal wscanf
wscanf (L"%ls %*s %d %ls",name,&amount,unit);
// print out new wide string using the extracted values
wprintf (L"% d %ls of land is owned by %ls\n",amount, unit, name);
return 0;
}

All bounds-checked functions (with “_s” suffix in their names) including the wscanf_s function are only guaranteed to work if __STDC_LIB_EXT1__ is pre-defined by the implementation and if the user defines __STDC_WANT_LIB_EXT1__ to int 1 before including stdio.h header file. The GCC compiler does not support this function. Hence, you will get an implicit declaration of function… error. We use the following variant to get the job done: int wscanf_s ( const char_t * format, ... );“.

In this example, we require an input with the specific format matching our format wide string, i.e., with the first word being a wide string, the second can be anything since it is ignored, the third an int, and another wide string after that. An example input would be “Faraz owns 500 acres of land”. We then use the wscanf_s function to read from this input and store parts of the wide string corresponding to the amount of land, units of measurement, and the owner’s name, which we then used to print a new wide string. Note how we did not need the word “owns” in the input wide string. So even though we denoted it by %*s in the format wide string, it was ignored since we did not give any string pointer argument.

Copyright ©2024 Educative, Inc. All rights reserved