You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在C程序中可移植地检测缓冲流的待处理输入输出

可移植实现方案说明

纯C标准没有提供查询stdio缓冲流(stdin/stdout/stderr)剩余待处理数据的标准化API,不存在100%兼容所有C语言运行环境的实现,但可以通过平台判断的方式,实现兼容绝大多数主流系统的方案:

输出流待输出数据检测

  • 仅需清除待输出数据的场景:直接调用标准库函数fflush(FILE *stream)即可,该函数是C89以来的标准函数,完全可移植。
  • 需要查询待输出数据量的场景:通过不同libc的非标准扩展实现,主流实现的查询逻辑如下:
    • glibc(Linux等环境):stream->_IO_write_ptr - stream->_IO_write_base
    • MSVCRT(Windows环境):stream->_cnt
    • BSD libc(macOS、FreeBSD等环境):stream->_p - stream->_bf._base

输入流待输入数据检测

用户态stdio缓冲待读数据

和输出流逻辑一致,通过对应libc的扩展字段查询:

  • glibc:stream->_IO_read_end - stream->_IO_read_ptr
  • MSVCRT:stream->_cnt
  • BSD libc:stream->_r

内核态未读数据查询

如果需要检测还未进入进程stdio缓冲、停留在内核缓冲区的待输入数据,可通过以下平台原生API实现:

  • POSIX兼容环境(Linux、macOS、BSD、Android等):使用poll设置零超时非阻塞查询:
#include <poll.h>
int has_pending_input(int fd) {
    struct pollfd pfd = {.fd = fd, .events = POLLIN};
    return poll(&pfd, 1, 0) > 0;
}
// 检测stdin调用方式:has_pending_input(fileno(stdin))
  • Windows环境:使用PeekNamedPipe查询标准输入句柄:
#include <windows.h>
int has_pending_stdin_input(void) {
    DWORD available_bytes = 0;
    PeekNamedPipe(GetStdHandle(STD_INPUT_HANDLE), NULL, 0, NULL, &available_bytes, NULL);
    return available_bytes > 0;
}

编译时通过_WIN32、__linux__、__APPLE__等预定义宏判断运行平台,调用对应实现即可覆盖绝大多数使用场景。


内容的提问来源于stack exchange,提问作者chqrlie

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.05 11:42:03