我有一个带有读取功能的简单 C 程序,但我不明白输出结果。
//code1.c
#include <unistd.h>
#include <stdio.h>
#include <fcntl.h>
int main()
{
int r;
char c; // In C, char values are stored in 1 byte
r = read ( 0, &c, 1);
// DOC:
//ssize_t read (int filedes, void *buffer, size_t size)
//The read function reads up to size bytes from the file with descriptor filedes, storing the results in the buffer.
//The return value is the number of bytes actually read.
// Here:
// filedes is 0, which is stdin from <stdio.h>
// *buffer is &c : address in memory of char c
// size is 1 meaning it will read only 1 byte
printf ("r = %d\n", r);
return 0;
}
结果截图如下:
如上所示,我运行了该程序 2 次,第一次尝试输入“a”,第二次尝试输入“aecho hi”。
我如何尝试解释结果:
- 当
read
被调用时,它发现 stdin 已关闭并打开它(从我的角度来看,为什么?它应该只是读取它。我不知道它为什么打开它)。 - 我在 bash 中输入“aecho hi”,然后按回车键。
read
优先处理 stdin 并读取“aecho hi”的第一个字节:“a”。- 我得到确认,
read
已使用 printf 处理了 1 个字节。 - a.out 已完成并终止。
- stdin 中的剩余数据以某种方式在 bash(我的程序之父)中处理并转到执行它的 stdout 并且由于某种原因第一个字节已被
read
删除。
这都是假设性的,而且非常模糊。非常欢迎任何帮助理解正在发生的事情。
最佳答案
当您在终端模拟器上键入时,它会将您的击键写入一个"file",在本例中是一个内存缓冲区,由于文件系统,它看起来就像磁盘上的任何其他文件一样。
每个进程从其父进程继承 3 个打开的文件句柄。我们在这里对其中之一感兴趣,标准输入。由终端仿真器执行的程序(此处为 bash
)作为其标准输入给出了第一段中描述的内存缓冲区。
a.out
, 当由 bash
运行时,也接收这个相同的文件作为它的标准输入。请记住这一点:bash
和 a.out
正在从同一个已打开的文件中读取。
在你运行 a.out
之后, 它的 read
block ,因为它的标准输入是空的。当您键入 aecho hi<enter>
,终端将这些字符写入缓冲区( <enter>
成为单个换行符)。 a.out
只请求一个字符,所以它得到a
并将其余字符留在文件中。 (或者更准确地说,在读取 e
之后,文件指针仍然指向 a
。)
在 a.out
之后完成,bash
尝试从同一个文件中读取。通常,文件为空(即文件指针位于文件末尾),因此 bash
block 等待另一个命令。但是,在这种情况下,已经有可用的输入:echo hi\n
. bash
现在阅读它就像您在 之后输入它一样 a.out
完成。
关于C 在 bash 中读取 : stdin and stdout,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41209541/