Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/57.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/file/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何以优化的方式将较大的文本文件加载到缓冲区--c程序_C_File_Optimization_File Io - Fatal编程技术网

如何以优化的方式将较大的文本文件加载到缓冲区--c程序

如何以优化的方式将较大的文本文件加载到缓冲区--c程序,c,file,optimization,file-io,C,File,Optimization,File Io,我有一个文本文件(无符号短值),如下所示 while(!feof(ref)) { fscanf(ref,"%d\n",&ref[count]); count++; } abc.txt 2311 1231 1232 54523 32423 我在函数中使用while循环读取此文件,并将其存储在缓冲区中,如下所示 while(!feof(ref)) { fscanf(ref,"%d\n",&ref[count]); count++; } 读取大文件

我有一个文本文件(无符号短值),如下所示

while(!feof(ref))
{
    fscanf(ref,"%d\n",&ref[count]);
    count++;
}
abc.txt

2311
1231
1232
54523
32423
我在函数中使用while循环读取此文件,并将其存储在缓冲区中,如下所示

while(!feof(ref))
{
    fscanf(ref,"%d\n",&ref[count]);
    count++;
}

读取大文件花费的时间太长。是否有任何方法优化fscanf操作。

使用本地缓冲区,并在二进制模式下使用fread()读取数据块。解析文本数据并继续下一个块

正确调整缓冲区大小,可能是64K或1Mb大小,这取决于您的应用程序

#include <stdio.h>

int BUFFER_SIZE = 1024;
FILE *source;
FILE *destination;
int n;
int count = 0;
int written = 0;

int main()
{
    unsigned char buffer[BUFFER_SIZE];

    source = fopen("myfile", "rb");

    if (source)
    {
        while (!feof(source))
        {
            n = fread(buffer, 1, BUFFER_SIZE, source);
            count += n;
            // here parse data
        }
    }

    fclose(source);
    return 0;
}
#包括
int BUFFER_SIZE=1024;
文件*来源;
文件*目的地;
int n;
整数计数=0;
int-writed=0;
int main()
{
无符号字符缓冲区[缓冲区大小];
source=fopen(“myfile”、“rb”);
如果(来源)
{
而(!feof(源))
{
n=fread(缓冲区,1,缓冲区大小,源);
计数+=n;
//这里是解析数据
}
}
fclose(来源);
返回0;
}

这是因为辅助内存访问比主内存访问慢。首先在二进制模式下使用
fread()
将文件转储到主内存中。然后从主内存逐整数读取。

一种常见的方法是将较大的块读入较大的内存缓冲区,然后从该缓冲区解析出数据


另一种方法是,操作系统将把文件放入进程虚拟内存映射中,这样你就可以像从内存中读取一样读取文件。

如果每行只有一个数字,这可能会更快,atoi()比使用fscanf()快得多

…匆忙输入代码,而不是编译或运行;)

您可以通过设置流缓冲区(例如

#define STRMBUF_SIZE (64*1024)
char strmbuf[STRMBUF_SIZE];
setvbuf( fp, strmbuf,_IOFBF,STRMBUF_SIZE);

不要在(!feof(ref))时执行
,它将不会像您期望的那样工作。原因是在尝试从文件末尾以外的位置读取之前,不会设置
EOF
标志。这意味着您将从一次循环到多次循环,并使用一个
fscanf
,它将在您没有注意到的情况下失败。相反,在您的情况下,执行
while(fscanf(ref,“%d”,&ref[count])==1)
。只要文件处于打开状态,或者直到文件中出现错误,就会循环。请定义“时间过长”。例如,如果仅仅读取文件(而不进行任何解码)的时间仍然太长,游戏就结束了。你真的不希望尾随的换行符以某种格式出现,特别是如果有人提供输入的话。它的意思是“跳过任何类型的空白,包括换行符,直到你读到一个非空白的东西”。因此,如果您是提供输入的人,您需要键入数字,然后键入换行符,然后程序将等待键入其他字符-可能是“咒骂”中的
e
,或者可能是一个中断或退出信号。@ScottHunter实际上我正在将这个值与另一个文本文件进行比较,以找出匹配的模式。i、 e.TextFile1包含100000个数据,textfile2包含10个数据。我想找到textfile1与textfile2匹配的确切位置。
ref
,重复的名称。哎哟!请参见下面的答案,为什么
而(!feof(ref))
是个坏主意。我不知道这有什么用。据我所知,C库函数应该是缓冲的。因此,你的缓冲区将是第三个多余的缓冲区,使事情变慢;OP是关于读取无符号短值的,一个缓冲区一个缓冲区的读取会使“此处解析数据”变得棘手,因为缓冲区的每一端都可能对分一行文本。在任何情况下,setvbuf()都要简单得多。在高效解析文本文件时,无论文本格式如何,都要将其视为二进制文件。然后,解析缓冲区内的原始数据。问题是如何使读取速度更快?用于文件处理的C库函数不是已经缓冲了吗?@Ali确实如此,而且缓冲区通常与磁盘块大小上的文件系统同步。但是,将较大的块读入内存,然后在内存中循环,可能比执行许多较小的读取并使用
fscanf
(这是一种非常通用的解析器,可能不如专门针对所讨论的文件格式而设计的解析器有效)要快。