0

我正在尝试将文件投影到内存中以对其进行操作。该文件包含结构,因此我尝试使用指向一个结构开头的指针,然后读取它并修改一些变量。问题是执行时间很长,我想使用 mmap 时间会更短。这是代码,有什么建议吗?

#include <unistd.h>
#include <sys/stat.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/mman.h>

int revisanotas(int fd)
{
int nbytes=1;
int nbytese=0;
int i=0;
int n=0;
struct stat datos;
fstat(fd, &datos);
evaluacion buf;
evaluacion* buffer=mmap(0,datos.st_size, PROT_READ | PROT_WRITE, MAP_PRIVATE, fd, 0);
int actual = read(fd,buffer,datos.st_size);
{
i++;
if (buffer[i].notamedia >= 4.5 && buffer[i].notamedia < 5)
{
n=n+1;
printf("Notamedia = %f\n",buffer[i].notamedia);

buffer[i].notamedia=5;
}

}while (i<(datos.st_size/(sizeof(evaluacion))));
return
4

5 回答 5

2

好吧,首先,请告诉我们evaluacion定义是什么,并将与 ;do匹配的while; 我假设它就在“int实际”行之后。

其次,看起来您调用 mmap() 的次数可能超出了需要;多久被revisanotas()调用一次fdmmap调用本身很慢,例如malloc;速度是您使用映射文件时的速度,在这种情况下,是 . 指向的数据buffer

第三,datos.st_size/(sizeof(evaluacion))在循环外计算一次并更改while子句以与之比较。当前的代码看起来像是在循环中每次迭代执行一次除法,并且除法很慢。

看看是否有帮助。

于 2009-11-15T14:08:29.270 回答
2

调用 toread()是不必要的。 为您将文件内容Mmap() 映射read()到内存中 - 这就是为什么它通常比使用. 您应该能够read()完全删除对的调用。不过,您的代码还有一些其他问题。

如果您希望修改实际反映在磁盘文件中,那么您应该调用msync(buffer, dataos.st_size, MS_SYNC). 完成后,调用munmap(buffer, dataos.st_size)以释放共享内存段。可以将msync()其视为等同于fflush()munmap()类似的共享内存close()munmap()和之间的主要区别在于close()前者不会刷新缓冲区或同步到磁盘,因此您必须自己完成。

于 2009-11-15T14:11:21.087 回答
0

我认为我正在取得一些进展,但似乎我没有修改文件。如果我运行程序一次,它会检测到 32 个变量已修改,但如果我运行两次仍然相同,那么它应该被修改:(

我认为现在的执行时间还不错

int revisanotas(int fd)
{
int i=0;
int n=0;
struct stat datos;
fstat(fd, &datos);
int num=datos.st_size/(sizeof(evaluacion));
evaluacion buf;
evaluacion* buffer=mmap(0,datos.st_size, PROT_READ | PROT_WRITE, MAP_PRIVATE, fd, 0);
do
{
i++;
if (buffer[i].notamedia >= 4.5 && buffer[i].notamedia < 5)
{
n=n+1;

buffer[i].notamedia=5;
}
msync(&buffer[i],sizeof(buffer[i]),MS_SYNC);
}while (i<(num));
munmap(buffer,datos.st_size);
return(n);
}
于 2009-11-15T15:19:49.117 回答
0

我认为现在正在工作:),代码如下。如果您发现有问题,请发表评论:

int revisanotas(int fd)
{
int i=0;
int n=0;
struct stat datos;
fstat(fd, &datos);
int num=datos.st_size/(sizeof(evaluacion));

evaluacion* buffer=mmap(0,datos.st_size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
do
{
i++;
if (buffer[i].notamedia >= 4.5 && buffer[i].notamedia < 5)
{
n=n+1;
buffer[i].notamedia=5;
}

}while (i<(num));
int r=munmap(&buffer[0],datos.st_size);

return(n);
}

谢谢大家的帮助。

于 2009-11-15T17:12:39.173 回答
0
Thanks mike for the answer, the struct is something like this and it's defined in a header file: 

struct evaluacion 
{ char id[16]; 
 char apellido1[32]; 
char apellido2[32]; 
char name[32]; float nota1p; 
float nota2p; 
float notamedia; 
char photofilename[20]; 
int photosize; 
char photodata[16000]; 
}; 

只有一个fd,只有一个文件打开,但里面有很多结构

于 2009-11-15T14:35:00.363 回答