Java StandardOpenOption.SYNC与StandardOpenOption.DSYNC 和之间有什么区别 使用DSYNC会发生什么样的数据丢失 DSYNC适合哪些用例?如果已经决定同步文件内容,为什么要放弃同步文件元数据?开销的相对差异难道不可以忽略吗

Java StandardOpenOption.SYNC与StandardOpenOption.DSYNC 和之间有什么区别 使用DSYNC会发生什么样的数据丢失 DSYNC适合哪些用例?如果已经决定同步文件内容,为什么要放弃同步文件元数据?开销的相对差异难道不可以忽略吗,java,nio,Java,Nio,吉利 DSYNC是SYNC的一个子集 同步要求同步写入所有数据(文件系统管理的文件数据和文件元数据),而DSYNC要求仅同步写入文件数据。至于开销,我认为这是一个巨大的“它取决于文件系统”。使用诸如写时复制、卷影复制、版本控制、校验等概念查看现代文件系统。。。我想,在所有工作完成之前,尝试阻止整个写操作可能会很昂贵 数据丢失的可能性是一个更令人困惑的答案;异步文件I/O的优点是,底层文件系统或磁盘实际上可以批处理或排序写入,以避免随机I/O,并以更连续的方式构造写入 这很好,但要回答您关于数据丢

吉利

DSYNC是SYNC的一个子集

同步要求同步写入所有数据(文件系统管理的文件数据和文件元数据),而DSYNC要求仅同步写入文件数据。至于开销,我认为这是一个巨大的“它取决于文件系统”。使用诸如写时复制、卷影复制、版本控制、校验等概念查看现代文件系统。。。我想,在所有工作完成之前,尝试阻止整个写操作可能会很昂贵

数据丢失的可能性是一个更令人困惑的答案;异步文件I/O的优点是,底层文件系统或磁盘实际上可以批处理或排序写入,以避免随机I/O,并以更连续的方式构造写入

这很好,但要回答您关于数据丢失的问题,可能是在可能丢失刷新之前,缓存中存在的任何挂起的写操作。简而言之,这很难说

简而言之,顺序如下所示:

  • (无选项)-速度最快,有可能从1个或多个尚未刷新的挂起写入中丢失文件数据和文件元数据
  • DSYNC-较慢,等待文件数据写入并返回(让我们稍后保存文件元)
  • SYNC-最慢,等待文件数据和文件元都写出来,并在返回前竖起大拇指
  • 我应该说,我假设所有这些问题都与Java7中的新版本有关;如果不是这样,我深表歉意。

    这里有一个特定于Linux文件系统的答案。 根据
    sun.nio.fs.UnixChannelFactory
    的来源,这些选项分别映射到的
    O_SYNC
    O_DSYNC
    选项表示:

    • O_SYNC
      ——like之后是对
    • O_DSYNC
      ——就像是在一个呼叫
    然后,
    fdatasync(2)
    的文档明确指出,对于文件数据的检索来说,任何非实质性的东西,例如上次访问时间和上次修改时间,都不会被
    O\u DSYNC
    刷新,但任何东西都是:

    fsync()。, 文件引用的文件的已修改缓冲区缓存页 磁盘设备(或其他永久存储设备)的描述符fd 这样,即使在 系统崩溃或已重新启动。。。呼叫将一直阻塞,直到设备停止 报告传输已完成。它还刷新元数据 与文件相关联的信息(见stat(2))

    fdatasync()类似于fsync(),但不刷新修改的数据 元数据,除非需要该元数据以允许 要正确处理后续的数据检索。例如 对st_atime或st_mtime的更改(分别为上次访问的时间) 最后一次修改的时间;见统计(2))无需冲洗 因为它们对于后续读取的数据不是必需的 处理正确。另一方面,对文件大小的更改 (如say ftruncate(2)所述,st_大小需要元数据 齐平

    因此,有根据的猜测是,除非程序使用这些属性对数据属性不重要(它们的值的同步很重要)
    StandardOpenOption.DSYNC
    是可以接受的。(虽然我不确定在实践中选择
    DSYNC
    而不是
    SYNC
    有多大的性能优势)

    仔细查看,像
    creationTime()
    lastModifiedTime()
    lastAccessTime()
    这样的字段可能属于这个“数据访问不重要”类别,而像
    isDirectory()
    isRegularFile()
    is*()
    size()
    这样的字段可能不会,因为我无法想象,如果数据是错误的,数据是可以访问的