FileChannel#强制和缓冲

我想说清楚,并立即在FileOutputStream和FileChannel之间绘制一些相似之处。

首先, 使用标准Java io编写文件的最有效方法似乎是使用包含BufferedOutputStream的FileOutputStream 。 因为它会自动刷新,当内部缓冲区溢出时。 能够进行单次写入(单字节,浮点数等)以及数组写入并且不担心速度是很方便的。 你唯一不应该忘记的是关闭它(进行最后的冲洗)。 使用BufferedOutputStream包装器的好处很明显,每个人都必须拥有 (我希望)。

现在关于FileChannel。 FileChannel有force方法,它相当于FileOutputStream中的flush,不是吗? javadocs清楚地说,您应该使用它来确保您对目标文件进行了更改。 但是,如果没有“BufferedFileChannel”包装器,我不明白何时以及为什么要使用它。 换句话说,FileChannel的缓冲在哪里? 它是自动的并且隐藏在FileChannel本身,就像在BufferedOutputStream中一样吗? 如果没有,那么为什么我需要强制方法,因为没有什么可以强迫的(所有更改都已经在使用write方法后应用于文件)并且我必须自己实现缓冲吗?

BufferedOutputStream 在java中有一个缓存, FileChannel没有。

但是, FileChannel确实具有操作系统级缓存。 其中.force()fsync / fdatasync相同。

在OpenJDK 6 src/solaris/native/sun/nio/ch/FileChannelImpl.c

  157 JNIEXPORT jint JNICALL 158 Java_sun_nio_ch_FileChannelImpl_force0(JNIEnv *env, jobject this, 159 jobject fdo, jboolean md) 160 { 161 jint fd = fdval(env, fdo); 162 int result = 0; 163 164 if (md == JNI_FALSE) { 165 result = fdatasync(fd); 166 } else { 167 result = fsync(fd); 168 } 169 return handle(env, result, "Force failed"); 170 } 

如果您想了解更多操作系统在此级别的工作原理,请阅读此博客 。