从std::cin中读取二进制数据

Read binary data from std::cin

本文关键字:二进制 数据 读取 cin std      更新时间:2023-10-16

std::cin读取二进制(非格式化)数据到stringstringstream的最简单方法是什么?

std::cin未使用ios_binary打开。如果您必须使用cin,那么您需要重新打开它,这不是标准的一部分。

这里有一些想法:https://comp.unix.programmer.narkive.com/jeVj1j3I/how-can-i-reopen-std-cin-and-std-cout-in-binary-mode

一旦它是二进制的,你可以使用cin.read()来读取字节。如果您知道在您的系统中,文本和二进制之间没有区别(并且您不需要可移植),那么您可以直接使用read,而不必担心。

对于windows,您可以将_setmode函数与cin.read()结合使用,如前所述。

_setmode(_fileno(stdin), _O_BINARY);
cin.read(...);

查看解决方案来源:http://talmai-oliveira.blogspot.com/2011/06/reading-binary-files-from-cin.html

cin.read将存储固定数量的字节,不需要对@Jason提到的那种类型的分隔符进行任何逻辑搜索。

但是,流上可能仍然有活动的翻译,例如CRLF -> NL,因此它仍然不是二进制数据的理想选择。

在Unix/POSIX系统上,您可以使用cin.get()方法逐字节读取数据并将数据保存到容器中,如std::vector<unsigned int>,或者您可以使用cin.read()以便将固定数量的字节读取到缓冲区中。您还可以使用cin.peek()来检查任何数据流结束指示器。

请记住,避免使用operator>>重载这种类型的操作…使用operator>>将导致每当观察到分隔符字符时出现分隔符,并且还将从流本身删除分隔符。这将包括任何等同于空格、制表符等的二进制值。因此,使用该方法最终从std::cin存储的二进制数据将不匹配输入二进制流。

所有预定义的iostream对象都必须绑定到相应的C流:

对象cin控制来自与对象stdin关联的流缓冲区的输入,该对象在<cstdio>中声明。

http://eel.is/c + +草案/narrow.stream.objects

,因此获取二进制数据的方法与C: 相同。

基本上,你能做的最好的就是:

freopen(NULL, "rb", stdin);

这将重新打开stdin,使其成为相同的输入流,但是是二进制的模式。在正常模式下,从Windows上的stdin读取将转换rn (Windows换行符)到单个字符ASCII 10。使用"rb"模式禁用这种转换,以便您可以正确地读入二进制数据。

https://stackoverflow.com/a/1599093/6049796

cplusplus.com:

  • 非格式化输入

    istream的大多数其他成员函数类用于执行未格式化的输入,即没有解释从输入中得到的字符。这些成员函数可以从输入字符中获取确定数目的字符序列(获取、getline peek,阅读,readsome )…

正如Lou Franco指出的,std::cin不是用std::ios_base::binary打开的,但是其中一个函数可能会让您接近您所寻找的行为。

在windows/mingw/msys/bash中,如果您需要在管道中使用二进制流来传输不同的命令,则需要将std::cin和std::cout作为二进制流来操作。

Mikhail的_setmode解决方案工作得很好。

使用MinGW,需要的头如下:

#include <io.h>
#include <fcntl.h>