我解决了需要非常快速输入/输出的问题。更确切地说,输入数据文件将高达15MB。有没有一种快速的方法来读取/打印整数值。
注意:我不知道它是否有帮助,但输入文件的格式如下:
注2:输入文件为stdin
。
编辑:以下内容不够快:
void fast_scan(int &n) {
char buffer[10];
gets(buffer);
n=atoi(buffer);
}
void fast_scan_three(int &a,int &b,int &c) {
char buffval[3][20],buffer[60];
gets(buffer);
int n=strlen(buffer);
int buffindex=0, curindex=0;
for(int i=0; i<n; ++i) {
if(!isdigit(buffer[i]) && !isspace(buffer[i]))break;
if(isspace(buffer[i])) {
buffindex++;
curindex=0;
} else {
buffval[buffindex][curindex++]=buffer[i];
}
}
a=atoi(buffval[0]);
b=atoi(buffval[1]);
c=atoi(buffval[2]);
}
答案 0 :(得分:3)
通用输入/输出优化原则执行尽可能少的I / O操作读取/写入尽可能多的数据。
因此,性能感知解决方案通常如下所示:
E.g。您可以使用std::basic_istream::read
按大块输入数据,而不是逐行进行。与输出类似的想法 - 生成单个字符串作为结果手动添加换行符号并立即输出。
答案 1 :(得分:1)
如果要最小化物理I / O操作开销,请通过名为memory mapped files的技术将整个文件加载到内存中。我怀疑你会获得明显的性能提升。解析很可能会花费更多。
答案 2 :(得分:0)
将几个输入行放在缓冲区中,拆分它们,然后在不同的线程中同时解析它们。
答案 3 :(得分:0)
考虑使用线程。线程对很多事情很有用,但这正是推动线程发明的问题。
基本思想是分离输入,处理和输出,以便这些不同的操作可以并行运行。做得对,你会看到显着的加速。
让一个线程接近纯输入。它将行读入行缓冲区。让第二个线程快速进行预解析并将原始输入组织成块。您有两件事需要解析,包含包含三元组的行数的行以及包含包含四元组的行数的行。此线程将原始输入形成块,这些块仍然主要是文本。第三个线程解析三元组和四元组,将输入重新形成为完全解析的结构。由于数据现在被组织成独立的块,因此您可以拥有此第三个操作的多个实例,以便更好地利用计算机上的多个处理器。最后,其他线程将在这些完全解析的结构上运行。注意:组合其中一些操作可能更好,例如将输入和预解析操作组合到一个线程中。
答案 4 :(得分:0)
它只有15MB。我只是将整个事物啜饮到内存缓冲区,然后解析它。 解析看起来像这样,大约:
#define DIGIT(c)((c) >= '0' && (c) <= '9')
while(*p == ' ') p++;
if (DIGIT(*p)){
a = 0;
while(DIGIT(*p){
a *= 10; a += (*p++ - '0');
}
}
// and so on...
你应该能够在睡梦中写下这种代码。
我不知道这是否比atoi
更快,但它并不是在弄清楚数字的开始和结束位置。我会远离scanf
,因为它经过九码计算出它的格式字符串。
如果你在一个循环中运行这整件1000次并获取一些堆栈样本,你应该看到它花费了近100%的时间读取文件并生成输出(你没有提到)。 你无法击败那个。 如果您确实看到在实际解析中花费了大量时间,则可能会执行重叠I / O,但是机器必须非常慢,或者I / O非常快(例如来自固态驱动器)在此之前是有意义的。