在打印之前将内容存储在内存中的目的是什么?

时间:2015-01-22 21:30:17

标签: c++

我是C ++的新手,目前正在使用visual studio。

我在网上看到许多教程,当用 ifstream 读取文件时,在循环遍历每一行的 cout 内容之前,我们写了当前的内容一行 char data [] var然后 cout 数据。

如下所示

#include<iostream>
#include<fstream>
using namespace std;

int main()
{
        ifstream f("D:\\file1.txt");
        char a[80];

        while(!f.eof())
        {
                f >> a;
                cout << a << endl;
        }

        return(0);
}

有什么意义
char a[80];
...
f >> a;
cout << a << endl;

当我们可以做的时候

cout << f << endl;

并保存声明一个字符并浪费更多行代码?

2 个答案:

答案 0 :(得分:0)

C ++中的首选方法是:

#include<iostream>
#include<fstream>

int main()
{
        std::ifstream f("D:\\file1.txt");

        if( f )
        {
            std::string line;
            while(getline(f, line) )
            {
                std::cout << line << endl;
            }
         }

        return 0 ;
}

如果要复制或列出文件,请使用操作系统命令。操作系统命令更适合处理文件。此外,它们已经存在并经过测试,因此您不会浪费您的时间。

答案 1 :(得分:0)

  

在打印内容之前将内容存储在内存中的目的是什么?

在你的例子中,没有太多意义。从std::cin读取的数据将直接发送到std::cout以显示在控制台上。通常,您希望在打印之前将数据存储在程序存储器中的唯一原因是您要修改数据或检查数据的属性并根据这些属性采取某些操作。

应该注意的是,虽然这是一个常见的例子,但while (!eof())的使用是在读取数据之前检查流的有效性的错误方法。此方法在读取输入之前检查流,如果读取并随后使用无效数据,则可能导致未定义的行为。读取数据的常规方法是在执行读取后检查流的有效性。例如,在您的程序中,这将更改为:

while (f >> a)
{
    std::cout << a << std::endl;
}

执行读取后,流将转换为布尔值。它将返回truefalse,具体取决于流的有效性。如果流读取文件结束(EOF)字符,则读取失败,流将返回false

  

有什么意义
char a[80];
...
f >> a;
cout << a << endl;
     

当我们可以做的时候

cout << f << endl;

首先,cout << f将无法满足您的期望。对于某些类型,流插入运算符(operator<<())已重载。 f的类型为std::ifstream - 此运算符未过载的类型。 Pre-C ++ 11 C ++ IOStreams包含到void*的转换,因此可以在布尔上下文中使用它们。流插入运算符被重载以指向void,因此您获得的输出不是您期望的。从C ++ 11开始,你会遇到编译器错误,无法找到该类型的运算符重载。

然而,std::streambuf*有一个重载,指针是IOStreams缓冲区。每个流都有一个缓冲区,用于存储和维护源或接收器中的字符。此运算符的重载从缓冲区读取数据并将其发送到自己的缓冲区,因此您可以执行以下操作:

std::cout << f.rdbuf();

rdbuf()返回指向流缓冲区的指针。

虽然这是对流功能的有效使用,但数据仍然存储在std::cout的缓冲区中。流被缓冲,并且发送到源或接收器的数据被委托到缓冲区,在缓冲区中等待直到刷新缓冲区。您可以使用std::nounitbuf取消缓冲std::cout,以便直接写入外部设备:

std::cout << std::nounitbuf
          << f.rdbuf();

对于一个包含小文件的简单示例,实际上不需要缓冲。如果你有一个非常大的文件,那么缓冲是非常有用的,因为程序不必为每个插入的字符进行系统调用。