Cprogramming 简明教程

Input and Output Functions in C

从用户处读取输入并在控制台上显示输入(输出)是每个 C 程序都需要执行的常见任务。C 语言提供了包含各种 functions for input and output 的库(头文件)。在本教程中,我们将学习不同类型的格式化和非格式化 input and output functions

Reading input from the user and showing it on the console (output) are the common tasks every C program needs. C language provides libraries (header files) that contain various functions for input and output. In this tutorial, we will learn different types of formatted and unformatted input and output functions.

The Standard Files in C

The C language treats all the devices as files 。因此,诸如“显示屏”之类的设备和“文件”的寻址方式相同。

The C language treats all the devices as files. So, devices such as the "display" are addressed in the same way as "files".

当一个程序执行时,以下三个文件会自动打开,以提供对键盘和屏幕的访问权限。

The following three files are automatically opened when a program executes to provide access to the keyboard and screen.

Standard File

File

Device

Standard input

stdin

Keyboard

Standard output

stdout

Screen

Standard error

stderr

Your screen

为了访问文件,C 使用一个预定义的 FILE 结构类型来引用需要读写的文件。阅读本章以了解如何从屏幕中读取值以及如何在屏幕上打印结果。

To access a file, C uses a predefined FILE struct type to refer to the file for reading and writing purpose. Read this chapter to understand how to read values from the screen and how to print the result on the screen.

Types of Input and Output Functions

在 C 中,我们有以下几类 IO 函数 −

We have the following categories of IO function in C −

  1. Unformatted character IO functions: getchar() and putchar()

  2. Unformatted string IO functions: gets() and puts()

  3. Formatted IO functions: scanf() and printf()

未格式化 I/O 函数将数据作为字节流进行读写,没有任何格式,而格式化 I/O 函数使用诸如“%d”、“%c”或“%s”之类的预定义格式从流中读写数据。

The unformatted I/O functions read and write data as a stream of bytes without any format, whereas formatted I/O functions use predefined formats like "%d", "%c" or "%s" to read and write data from a stream.

Unformatted Character Input & Output Functions: getchar() and putchar()

这两个函数分别从键盘接收单个字符作为输入,并在输出终端上显示单个字符。

These two functions accept a single character as input from the keyboard, and display a single character on the output terminal, respectively.

getchar() function 在不使用 Enter 键的情况下读取单个按键。

The getchar() function it reads a single key stroke without the Enter key.

int getchar(void)

不需要任何参数。该函数返回一个整型数,与用户输入的字符键的 ASCII 编码值相对应。

There are no parameters required. The function returns an integer corresponding to the ASCII value of the character key input by the user.

Example 1

以下程序将单个键读入 char 变量中:

The following program reads a single key into a char variable −

#include <stdio.h>

int main() {

   char ch;

   printf("Enter a character: ");
   ch = getchar();

   puts("You entered: ");
   putchar(ch);

   return 0;
}

运行代码并检查其输出:

Run the code and check its output −

Enter a character: W
You entered:
W

Example 2

以下程序显示了如何读取一系列字符,直到用户按下 Enter 键:

The following program shows how you can read a series of characters till the user presses the Enter key −

#include <stdio.h>

int main() {

   char ch;
   char word[10];
   int i = 0;

   printf("Enter characters. End with pressing enter: ");

   while(1) {
      ch = getchar();
      word[i] = ch;
      if (ch == '\n')
         break;
      i++;
   }

   printf("\nYou entered the word: %s", word);

   return 0;
}

运行代码并检查其输出:

Run the code and check its output −

Enter characters. End with pressing enter: Hello
You entered the word: Hello

你还可以使用 unformatted putchar() function 打印单个字符。C 库函数“ int putchar(int char) ”将参数 char 指定的字符(一个无符号 char )写入 stdout 中。

You can also use the unformatted putchar() function to print a single character. The C library function "int putchar(int char)" writes a character (an unsigned char) specified by the argument char to stdout.

int putchar(int c)

此函数的单个参数是要写入的字符。你还可以传递其对应的 ASCII 整数。此函数返回以 int 形式强制转换的无符号 char 形式的字符,或在出错时返回 EOF。

A single parameter to this function is the character to be written. You can also pass its ASCII equivalent integer. This function returns the character written as an unsigned char cast to an int or EOF on error.

Example 3

以下示例展示了如何使用 putchar() 函数:

The following example shows how you can use the putchar() function −

#include <stdio.h>

int main() {

   char ch;

   for(ch = 'A' ; ch <= 'Z' ; ch++) {
      putchar(ch);
   }

   return(0);
}

当你运行这段代码时,它将产生以下输出:

When you run this code, it will produce the following output −

ABCDEFGHIJKLMNOPQRSTUVWXYZ

Formatted String Input & Output Functions: gets(), fgets(), puts(), and fputs()

char *gets(char *str) functionstdin 中读取一行,并将数据写入 str 指向的缓冲区中,直到遇到终止换行符或 EOF(文件结尾)。

The char *gets(char *str) function reads a line from stdin into the buffer pointed to by str until either a terminating newline or EOF (End of File) is encountered.

char *gets (char *str)

此函数有一个参数。它是一个指向 char 数组的指针, C string 存储在该数组中。成功时,函数将返回“str”;出错时或在 EOF 发生且未读取任何字符时,将返回 NULL。

This function has a single argument. It is the pointer to an array of chars where the C string is stored. The function returns "str" on success and NULL on error or when EOF occurs while no characters have been read.

Example

请看以下示例:

Take a look at the following example −

#include <stdio.h>

int main() {

   char name[20];

   printf("Enter your name: ");
   gets(name);
   printf("You entered the name: %s", name);

   return 0;
}
Enter your name: Ravikant Soni
You entered the name: Ravikant Soni

scanf("%s") 读取字符,直到遇到空白(空格、制表符、换行符等)或 EOF。因此,如果你尝试输入一个包含多个单词(以空白分隔)的字符串,那么它会将第一个空白之前的字符作为字符串的输入来接收。

scanf("%s") reads characters until it encounters a whitespace (space, tab, newline, etc.) or EOF. So, if you try to input a string with multiple words (separated by a whitespace), then it accepts characters before the first whitespace as the input to string.

fgets() Function

在较新版本的 C 中, gets() 已被弃用,因为它可能是一个危险的函数,因为它不执行边界检查,并且可能会导致缓冲区溢出。

In newer versions of C, gets() has been deprecated as it is potentially a dangerous function because it doesn’t perform bound checks and may result in buffer overflow.

相反,建议使用 fgets() function

Instead, it is advised to use fgets() function

fgets(char arr[], size, stream);

fgets() 可以用于从任何输入流(如 stdin(键盘)或 FILE(文件流))接收输入。

fgets() can be used to accept input from any input stream such as stdin (keyboard) or FILE (file stream).

Example 1

以下程序展示了如何使用 fgets() 从用户接收多单词输入:

The following program shows how you can use fgets() to accept multi-word input from the user −

#include <stdio.h>

int main () {

   char name[20];

   printf("Enter a name: \n");
   fgets(name, sizeof(name), stdin);

   printf("You entered: \n");
   printf("%s", name);

   return 0;
}

运行代码并检查其输出:

Run the code and check its output −

Enter a name:
Rakesh Sharma

You entered:
Rakesh Sharma

函数“ int puts (const char *str) ”将字符串“s”和一个尾随换行符写入 stdout

The function "int puts (const char *str)" writes the string 's' and a trailing newline to stdout.

int puts(const char *str)

str 参数是要写入的 C 字符串。如果成功,则返回一个非负值。如果出错,则函数返回 EOF。

The str parameter is the C string to be written. If successful, it returns a non-negative value. On error, the function returns EOF.

我们可以使用带有 %s 说明符的 printf() 函数来打印字符串。我们还可以使用 puts() 函数(在 C11 和 C17 版本中已弃用)或 fputs() function 作为替代。

We can use the printf() function with %s specifier to print a string. We can also use the puts() function (deprecated in C11 and C17 versions) or the fputs() function as an alternative.

Example 2

以下示例显示了 puts()fputs() 之间的差异 −

The following example shows the difference between puts() and fputs()

#include <stdio.h>

int main () {

   char name[20] = "Rakesh Sharma";

   printf("With puts(): \n");
   puts(name);

   printf("\nWith fputs(): \n");
   fputs(name, stdout);

   return 0;
}

运行代码并检查其输出:

Run the code and check its output −

With puts():
Rakesh Sharma

With fputs():
Rakesh Sharma

Formatted Input & Output Functions: scanf() and printf()

scanf() function 从标准输入流 stdin 读取输入,并根据提供的格式扫描该输入 −

The scanf() function reads the input from the standard input stream stdin and scans that input according to the format provided −

int scanf(const char *format, ...)

printf() function 将输出写入标准输出流 stdout ,并根据提供的格式生成输出。

The printf() function writes the output to the standard output stream stdout and produces the output according to the format provided.

int printf(const char *format, ...)

格式可以是一个简单的常量字符串,但是你可以指定 %s、%d、%c、%f 等,以打印或分别读取字符串、整数、字符或浮点数。还有许多其他可用的格式化选项,可以根据具体要求使用。

The format can be a simple constant string, but you can specify %s, %d, %c, %f, etc., to print or read strings, integers, characters or floats respectively. There are many other formatting options available which can be used based on the specific requirements.

Format Specifiers in C

CPU 以流方式执行输入和输出设备的 IO 操作。通过标准输入流从标准输入设备(键盘)读取的数据称为 stdin。类似地,通过标准输出设备发送到标准输出(计算机显示屏)的数据称为 stdout。

The CPU performs IO operations with input and output devices in a streaming manner. The data read from a standard input device (keyboard) through the standard input stream is called stdin. Similarly, the data sent to the standard output (computer display screen) through the standard output device is called stdout.

计算机以文本形式从流中接收数据,但是你可能希望将其解析为不同数据类型的变量,例如 int、float 或字符串。类似地,存储在 int、float 或 char 变量中的数据必须以文本格式发送到输出流。格式说明符符号恰好用于此目的。

The computer receives data from the stream in a text form, however you may want to parse it in variables of different data types such as int, float or a string. Similarly, the data stored in int, float or char variables has to be sent to the output stream in a text format. The format specifier symbols are used exactly for this purpose.

ANSI C 定义了许多格式说明符。下表列出了不同的说明符及其用途。

ANSI C defines a number of format specifiers. The following table lists the different specifiers and their purpose.

Format Specifier

Type

%c

Character

%d

Signed integer

%e or %E

Scientific notation of floats

%f

Float values

%g or %G

Similar as %e or %E

%hi

Signed integer (short)

%hu

Unsigned Integer (short)

%i

Unsigned integer

%l or %ld or %li

Long

%lf

Double

%Lf

Long double

%lu

Unsigned int or unsigned long

%lli or %lld

Long long

%llu

Unsigned long long

%o

Octal representation

%p

Pointer

%s

String

%u

Unsigned int

%x or %X

Hexadecimal representation

minus sign (−) 表示左对齐。% 后面的数字指定最小字段宽度。如果字符串小于宽度,则它将填充空格。 period (.) 用于分隔字段宽度和精度。

A minus sign (−) signifies left alignment. A number after "%" specifies the minimum field width. If a string is less than the width, it will be filled with spaces. A period (.) is used to separate field width and precision.

Example

以下示例演示了格式说明符的重要性 −

The following example demonstrates the importance of format specifiers −

#include <stdio.h>

int main(){

   char str[100];

   printf("Enter a value: ");
   gets(str);

   printf("\nYou entered: ");
   puts(str);

   return 0;
}

编译并执行上述代码后,它会等待你输入一些文本。当你输入文本并按 Enter 键时,程序会继续读取输入并以如下方式显示它 −

When the above code is compiled and executed, it waits for you to input some text. When you enter a text and press the Enter button, the program proceeds and reads the input and displays it as follows −

Enter a value: seven 7
You entered: seven 7

这里需要注意的是,scanf() 函数希望输入的格式与其提供的 “%s” 和 “%d” 相同,这意味着你必须提供诸如 “字符串后跟整数” 的有效输入。如果你提供了两个连续的字符串 “字符串字符串” 或两个连续的整数 “整数整数”,那么它将被认为是一组不正确的输入。

Here, it should be noted that the scanf() function expects the input in the same format as you provided "%s" and "%d", which means you have to provide valid inputs like "a string followed by an integer". If you provide two consecutive strings "string string" or two consecutive integers "integer integer", then it will be assumed as an incorrect set of input.

其次,在读取字符串时,scanf() 函数一旦遇到 “空格” 就停止读取,因此字符串 “This is Test” 实际上是 scanf() 函数的三组字符串。

Secondly, while reading a string, the scanf() function stops reading as soon as it encounters a "space", so the string "This is Test" is actually a set of three strings for the scanf() function.