如何读取文件并将其写入字符串C++

Ele*_*ena 0 c++ string ifstream

我找到了解决方案,但我相信还有更好的方法。如何在不使用复杂工具的情况下改进我的代码?

string Read(string& file) {
    ifstream in;
    string text;
    string s;
    in.open(file, ios::in);
    try {
        while (!in.eof()) {
            text.append(s);
            in >> s;
        }
    }
    catch (exception& ex) {
        cout << ex.what();
    }
    in.close();
    return text; 
}
Run Code Online (Sandbox Code Playgroud)

Max*_*kin 5

您的代码读取以空格分隔的单词,丢弃空格,并将所有单词连接成一个没有空格的字符串。您可能想逐字阅读文件内容。


将整个文件读入std::string而不使用循环的一种方法是使用std::string带有两个迭代器的构造函数 - 构造函数为您执行循环。使用以下命令调用它std::istreambuf_iterator

#include <string>
#include <fstream>
#include <iterator>
#include <stdexcept>

std::string read(std::string filename) {
    std::ifstream file(filename, std::ios_base::binary | std::ios_base::in);
    if(!file.is_open())
        throw std::runtime_error("Failed to open " + filename);
    using Iterator = std::istreambuf_iterator<char>;
    std::string content(Iterator{file}, Iterator{});
    if(!file)
        throw std::runtime_error("Failed to read " + filename);
    return content;
}
Run Code Online (Sandbox Code Playgroud)

另一种替代方法是将文件映射到内存中(零复制方法),例如使用boost::iostreams::mapped_file,它尽可能干净和高效。对于大于 ~100kB 的文件,该方法速度更快,通过基准测试来获取硬数据。

一种优化是立即填充文件映射的所有页面,而不是在首次访问时进行请求分页

例子:

#include <iostream>
#include <boost/iostreams/device/mapped_file.hpp>

int main() {
    using boost::iostreams::mapped_file;
    mapped_file content("/etc/lsb-release", mapped_file::readonly);
    std::cout.write(content.const_data(), content.size());
}
Run Code Online (Sandbox Code Playgroud)