Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/64.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_Multithreading - Fatal编程技术网

C 在同一文件上写入的多个线程

C 在同一文件上写入的多个线程,c,multithreading,C,Multithreading,我想知道我们是否可以使用多个线程在同一个文件上写入二进制数据 FILE *fd = openfile("test"); int SIZE = 1000000000; int * table = malloc(sizeof(int) * SIZE); // .. filling the table fwrite(table, sizeof(*table), SIZE, fd); 所以我想知道我是否可以使用线程,每个线程调用fssek来寻找不同的位置来写入同一个文件 FILE *fd = open

我想知道我们是否可以使用多个线程在同一个文件上写入二进制数据

FILE *fd = openfile("test");
int SIZE = 1000000000;
int * table = malloc(sizeof(int) * SIZE);
// .. filling the table
fwrite(table, sizeof(*table), SIZE, fd);
所以我想知道我是否可以使用线程,每个线程调用fssek来寻找不同的位置来写入同一个文件

FILE *fd = openfile("test");
int SIZE = 1000000000;
int * table = malloc(sizeof(int) * SIZE);
// .. filling the table
fwrite(table, sizeof(*table), SIZE, fd);

有什么想法吗?

fseek和fwrite是线程安全的,因此您可以使用它们,而无需额外的同步。

fwrite应该是线程安全的,但您仍然需要一个互斥锁,因为您需要将寻道和写入设置为原子。根据您的平台,您可能有一个带偏移量的写函数,或者您可以在每个线程中打开文件。如果正如代码所建议的那样,所有内容都在内存中,那么更好的选择是将每个线程填充到单个大数组中,然后在完成所有内容后将其写出

让每个线程打开文件,并确保它们写入不同的位置,最后让每个线程关闭文件并完成您的操作

更新:

这至少适用于IX'ish系统。

虽然
fread()
fwrite()
是线程安全的,但
文件*
表示的流缓冲区不是线程安全的。因此,您可以让多个线程访问同一个文件,但不能通过同一个
文件*
——每个线程都必须有自己的文件,并且它们引用的文件必须是可共享的——这取决于操作系统


另一种可能更简单的方法是使用,这样每个线程都将文件视为共享内存,让操作系统处理文件I/O。这比普通文件I/O有很大的优势,因为它是真正的随机访问,所以您不需要担心
fseek()
和顺序读/写等。

阅读
fwrite()
的文档,了解它是否是线程安全的。如果没有,您将需要实现自己的互斥来保护它。
int*table=sizeof(sizeof(int)*SIZE)此处似乎缺少某些内容。但调用fseek然后调用fwrite需要synchronization@WilliamPursell这取决于实施情况。如果每个线程都有自己的文件描述符,那么在不进行同步的情况下一个接一个地调用它们是安全的。一个实现示例?@zeomega你是说一个在不进行额外同步的情况下工作正常的实现吗?您可以通过在每个线程中调用
fopen
在所有线程中打开同一个文件。您有一个小示例吗?实际上我已经有一个大数组(表),但我想同时使用线程将“int*table”写入我的文件,这是因为您希望它更快吗?我认为这不太可能,因为写操作必须在某个阶段序列化。事实上,额外的搜索可能会大大降低速度。你是说在多个线程中使用全局文件指针访问
fprintf()
fwrite()
是不安全的吗?@JohnStrood;我没有确切地说,但是答案适用于使用
文件*
的任何函数,因为
文件
不是原子对象。此外,该问题需要独立的
fseek()
操作,并且由于当前文件位置保留在
文件
对象中,在这种特殊情况下,如果不将两个线程的整个寻道/写序列包装在互斥锁中以确保操作的序列化,则是不可行的“所有读取、写入、定位或查询流位置的函数都会在访问流之前锁定流。当访问完成时,它们释放与流关联的锁“()。请注意,这指的是锁定流,而不是底层文件。@JohnBollinger:我不清楚您指的是答案的哪一部分或随后的评论。这是很久以前的事了-我不确定现在是否要更改它,但澄清您的评论可能会有用-也就是说,确切的答案可能是什么关于C99?@Clifford,我首先注意到我的注意力是由以下人员引导的,因此这可能会有助于理解上下文。但我指的是你的整个第一段。虽然标准没有明确规定
文件
对象可共享,但其有关strea的规定没有可行的解释ms和流锁定不会导致该结果。