我试图以更快的方式读取文件。我目前的做法如下,但对于大文件来说速度非常慢。我想知道是否有更快的方法来做到这一点?我需要存储结构的值,我在下面定义了它。
std::vector<matEntry> matEntries;
inputfileA.open(matrixAfilename.c_str());
// Read from file to continue setting up sparse matrix A
while (!inputfileA.eof()) {
// Read row, column, and value into vector
inputfileA >> (int) row; // row
inputfileA >> (int) col; // col
inputfileA >> val; // value
// Add row, column, and value entry to the matrix
matEntries.push_back(matEntry());
matEntries[index].row = row-1;
matEntries[index].col = col-1;
matEntries[index].val = val;
// Increment index
index++;
}
我的结构:
struct matEntry {
int row;
int col;
float val;
};
文件的格式如下(int,int,float):
1 2 7.9
4 5 9.008
6 3 7.89
10 4 10.21
更多信息:
答案 0 :(得分:3)
为了简化操作,我为您的结构定义了一个输入流操作符。
std::istream& operator>>(std::istream& is, matEntry& e)
{
is >> e.row >> e.col >> e.val;
e.row -= 1;
e.col -= 1;
return is;
}
关于速度,如果没有very basic级别的文件IO,则没有太多改进。我认为你唯一能做的就是初始化你的向量,这样它就不会在循环中一直调整大小。使用定义的输入流操作符,它看起来也更清晰:
std::vector<matEntry> matEntries;
matEntries.resize(numberOfLines);
inputfileA.open(matrixAfilename.c_str());
// Read from file to continue setting up sparse matrix A
while(index < numberOfLines && (is >> matEntries[index++]))
{ }
答案 1 :(得分:2)
根据评论中的建议,您应该在尝试优化之前对代码进行概要分析。如果你想尝试随机的东西,直到表现足够好,你可以先尝试将其读入内存。这是一个简单的例子,其中包含一些基本的分析:
#include <vector>
#include <ctime>
#include <fstream>
#include <sstream>
#include <iostream>
// Assuming something like this...
struct matEntry
{
int row, col;
double val;
};
std::istream& operator << ( std::istream& is, matEntry& e )
{
is >> matEntry.row >> matEntry.col >> matEntry.val;
matEntry.row -= 1;
matEntry.col -= 1;
return is;
}
std::vector<matEntry> ReadMatrices( std::istream& stream )
{
auto matEntries = std::vector<matEntry>();
auto e = matEntry();
// For why this is better than your EOF test, see https://isocpp.org/wiki/faq/input-output#istream-and-while
while( stream >> e ) {
matEntries.push_back( e );
}
return matEntries;
}
int main()
{
const auto time0 = std::clock();
// Read file a piece at a time
std::ifstream inputFileA( "matFileA.txt" );
const auto matA = ReadMatrices( inputFileA );
const auto time1 = std::clock();
// Read file into memory (from http://stackoverflow.com/a/2602258/201787)
std::ifstream inputFileB( "matFileB.txt" );
std::stringstream buffer;
buffer << inputFileB.rdbuf();
const auto matB = ReadMatrices( buffer );
const auto time2 = std::clock();
std::cout << "A: " << ((time1 - time0) * CLOCKS_PER_SEC) << " B: " << ((time2 - time1) * CLOCKS_PER_SEC) << "\n";
std::cout << matA.size() << " " << matB.size();
}
请注意连续两次读取磁盘上的相同文件,因为磁盘缓存可能会隐藏性能差异。
其他选项包括:
std::async()
]; medium :管道,以便完成读取和转换在不同的线程上; 硬:在不同的线程中处理相同的文件)其他更高级别的考虑可能包括:
答案 2 :(得分:2)
根据我的经验,这种代码中最慢的部分是解析数值(特别是浮点值)。因此,您的代码很可能受CPU限制,并且可以通过并行化加速,如下所示:
假设您的数据位于 N 行,并且您将使用 k 线程处理它,则每个线程都必须处理[ N <强> / k ]行。
mmap()
文件。std::istream
that wraps an in-memory buffer)并行处理其范围。请注意,这需要确保填充数据结构的代码是线程安全的。