如何将流大小转换为其他或如何将流大小值传递给向量?

Posted

技术标签:

【中文标题】如何将流大小转换为其他或如何将流大小值传递给向量?【英文标题】:How to convert streamsize to other or how to pass streamsize value to vector? 【发布时间】:2018-11-24 14:52:52 【问题描述】:

我有一个问题,我需要将流大小值传递给向量。如果我没有将它传递给固定大小。它将使用带有千元素的 emplace_back 开销。错误编译器可能导致数据丢失。

ifstream input(i_inputFilePath, ios::binary);
if (input.is_open())

    ofstream output(o_outputFilePath, ios::binary);
    std::array<char, 1024> buffer;
    while (true) 
        input.read(buffer.data(), buffer.size());
        streamsize dataSize = input.gcount();
        if (dataSize) 
        
            std::vector<char> data(dataSize); // here the problem
            for (DWORD i = 0; i < dataSize; i++)
            
                data.emplace_back(buffer[i]);
            
            std::rotate(data.begin(), data.begin() + 1, data.end());
            output.write(data.data(), dataSize);    
        
        else 
         
            output.close();
            input.close();
            break;
           
    

else

    cout << "File is not exist";

【问题讨论】:

欢迎来到 Stack Overflow。请阅读the help pages、the SO tour、阅读how to ask good questions,以及this question checklist。还学习如何创建minimal reproducible example。如果询问构建错误,请包含复制粘贴的完整和完整输出,并在代码中添加注释以显示错误发生的位置。 @Someprogrammerdude 已经满了。我用评论编辑了我的问题以指出问题。 【参考方案1】:

如果您将单个整数参数传递给std::vector 的构造函数(如std::vector&lt;char&gt; data(dataSize);),将默认构造其中的许多元素,其大小将是传递的整数。

如果你然后emplace_back 进入它,它会增加它的大小,而不是覆盖已经构建的元素。

如果你想emplace_back你所有的元素,只需这样做,不需要将最终大小传递给构造函数:

std::vector<char> data;

std::vector 的大多数实现不会在每个 emplace_back 上重新分配,但会例如每次空间用完时将分配的空间加倍。因此,平均而言,这不会真的那么糟糕。

如果您担心重新分配,那么您可以强制向量预先分配空间

data.reserve(dataSize);

这实际上不会构造任何元素,但会确保提前分配必要的空间。

如果您收到关于从std::streamsize 转换为std::size_t 的错误消息,那么这是误报,因为在这种特殊情况下,您知道dataSize 只能具有范围为0 的值到1024。编译器正确地警告dataSize 的类型是有符号的,因此可能持有一个不能用无符号std::size_t 表示的负值。

你可以用类似的东西来测试这个假设是否正确

streamsize dataSize = input.gcount();
if(dataSize < 0 || dataSize > buffer.size()) 
    throw std::range_error("dataSize has unexpected value!");

data.reserve(static_cast<std::size_t>(dataSize));    

这确保dataSize 不会意外地为负数或大于预期值(如果是,它将抛出异常),否则它将提示编译器您确实想使用显式强制转换进行缩小转换,这应该抑制警告/错误消息。

【讨论】:

我知道,但它一直在调整大小。如果 100 万个元素保持调整大小为 1 以适应,它将产生开销。如果我知道缓冲区大小,为什么向量需要保持调整大小? streamsize dataSize 不想允许转换的问题。与 data.reserve(dataSize) 相同 我使用 Visual Studio 2017 社区和语言 c++17。统一码。和 MT 构建。我的配置有问题吗? 我在我的编译流中检查它的大小是 typedef long long。但是当我用streamsize创建long long variabel和initiliziation时。示例结果无法转换可能丢失的数据。 我目前的工作代码是我返工 itu 不使用向量,而是使用新的手动动态分配。但我需要自己实现旋转

以上是关于如何将流大小转换为其他或如何将流大小值传递给向量?的主要内容,如果未能解决你的问题,请参考以下文章

如何将流 responseType 传递给我的客户端?

Node.js - 如何将流转换为字符串

如何将流结果转换为字符串

如何从单个 JSON(IOT HUB)将流分析输出转换为多行

Objective-C - 将流数据传递到音频队列

将流列表转换为列表