所有之前的答案都涉及到文件锁问题的方面,但没有一个完全解决根本原因和解决办法。本答案提供了导致问题的技术背景,总结了解决方案,并提供了避免将来出现问题的技巧。
首先,文件锁不仅仅是一个h5py的问题。它是在底层HDF5 API中实现的,适用于以写访问方式打开的任何文件。(这就是为什么基于Java的HDFView可能会引起文件访问冲突的原因。)如1个答案中所述,默认情况下,HDF5具有SWMR访问(单写;多读)。关于此的更多信息请参见末尾。每当一个文件以写访问方式打开时,API会“锁定”该文件,以防止其他进程的写访问。这样做是为了防止文件损坏。
因此,每当一个进程以写模式打开一个文件时,另一个进程就无法以写模式访问该文件。当发生这种情况时,您将在原始帖子中收到“无法锁定文件”的错误消息。(注意:这不会阻止另一个进程以只读模式打开文件。)
有几种情况可能会触发文件锁:
尝试同时运行两个具有写访问权限的进程访问同一个文件。有两个答案提到了这个问题:
同时运行另一个应用程序,例如
myapp.py
以默认写访问模式运行HDFView。(与上述情况相同,其中HDFView是第一个应用程序。)
在上一个进程退出时,尝试以写模式打开文件,而没有正确关闭文件。
这通常发生在崩溃后。根据我的经验,这是最常见的原因。
如果程序在退出时没有正确关闭文件,也可能发生这种情况。(参见关于“以一种隐晦的方法未能关闭”的答案。)
如何避免文件锁定:
使用HDFView时,可以将默认访问模式设置为“只读”以避免问题。或者,可以使用文件菜单中的“打开为...只读”选项。
为了避免意外的文件锁定(崩溃或未关闭退出),需要对应用程序代码进行更改。在Python中,最好的方法是使用“with/as:”上下文管理器。通过上下文管理器,当程序正常退出或发生异常时,文件会自动关闭。
“with/as:”的示例:
with h5py.File('my_h5_file.hdf5','w') as h5f:
some code that writes to your file
end of that code block
如何重置文件锁定状态:
现在,如果所有尝试都失败了,你仍然无法以写模式访问文件,那么有一个HDF5实用程序可以解锁文件。(我认为你需要本地安装HDF5才能使用此实用程序。)命令行输入如下:
h5clear –-status filename.h5 (or just -s)
多进程写入访问:
如上所述,默认的HDF5行为是SWMR。然而,可以通过一些额外的工作实现并行写入访问。 h5py
使用 mpi4py
包来完成这个任务。然而,这需要一个HDF5并行构建,并且 h5py
必须以“MPI模式”编译。详细信息请参考h5py Parallel HDF5 docs。