java FileChannel.transferTo 用于 windows 中的大文件
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/7379469/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
FileChannel.transferTo for large file in windows
提问by Tapas Bose
Using Java NIO use can copy file faster. I found two kind of method mainly over internet to do this job.
使用Java NIO 使用可以更快地复制文件。我主要通过互联网找到了两种方法来完成这项工作。
public static void copyFile(File sourceFile, File destinationFile) throws IOException {
if (!destinationFile.exists()) {
destinationFile.createNewFile();
}
FileChannel source = null;
FileChannel destination = null;
try {
source = new FileInputStream(sourceFile).getChannel();
destination = new FileOutputStream(destinationFile).getChannel();
destination.transferFrom(source, 0, source.size());
} finally {
if (source != null) {
source.close();
}
if (destination != null) {
destination.close();
}
}
}
In 20 very useful Java code snippets for Java DevelopersI found a different comment and trick:
在20 个对 Java 开发人员非常有用的 Java 代码片段中,我发现了一个不同的评论和技巧:
public static void fileCopy(File in, File out) throws IOException {
FileChannel inChannel = new FileInputStream(in).getChannel();
FileChannel outChannel = new FileOutputStream(out).getChannel();
try {
// inChannel.transferTo(0, inChannel.size(), outChannel); // original -- apparently has trouble copying large files on Windows
// magic number for Windows, (64Mb - 32Kb)
int maxCount = (64 * 1024 * 1024) - (32 * 1024);
long size = inChannel.size();
long position = 0;
while (position < size) {
position += inChannel.transferTo(position, maxCount, outChannel);
}
} finally {
if (inChannel != null) {
inChannel.close();
}
if (outChannel != null) {
outChannel.close();
}
}
}
But I didn't find or understand what is meaning of
但我没有找到或理解什么是
"magic number for Windows, (64Mb - 32Kb)"
“Windows 的幻数,(64Mb - 32Kb)”
It says that inChannel.transferTo(0, inChannel.size(), outChannel)
has problem in windows, is 32768 (= (64 * 1024 * 1024) - (32 * 1024)) byte is optimum for this method.
它说inChannel.transferTo(0, inChannel.size(), outChannel)
在 Windows中有问题,是 32768 (= (64 * 1024 * 1024) - (32 * 1024)) 字节最适合这种方法。
采纳答案by user207421
Windows has a hard limit on the maximum transfer size, and if you exceed it you get a runtime exception. So you need to tune. The second version you give is superior because it doesn't assume the file was transferred completely with one transferTo()
call, which agrees with the Javadoc.
Windows 对最大传输大小有硬性限制,如果超过该限制,则会出现运行时异常。所以你需要调整。您提供的第二个版本更好,因为它不假设文件是通过一次transferTo()
调用完全传输的,这与 Javadoc 一致。
Setting the transfer size more than about 1MB is pretty pointless anyway.
无论如何,将传输大小设置为超过 1MB 是毫无意义的。
EDITYour second version has a flaw. You should decrement size
by the amount transferred each time. It should be more like:
编辑您的第二个版本有缺陷。您应该减少size
每次转移的金额。它应该更像是:
while (position < size) {
long count = inChannel.transferTo(position, size, outChannel);
if (count > 0)
{
position += count;
size-= count;
}
}
回答by Danny Rancher
I have read that it is for compatibility with the Windows 2000 operating system.
我读到它是为了与 Windows 2000 操作系统兼容。
Source: http://www.rgagnon.com/javadetails/java-0064.html
来源:http: //www.rgagnon.com/javadetails/java-0064.html
Quote: In win2000, the transferTo() does not transfer files > than 2^31-1 bytes. it throws an exception of "java.io.IOException: Insufficient system resources exist to complete the requested service is thrown." The workaround is to copy in a loop 64Mb each time until there is no more data.
引用:在 win2000 中,transferTo() 不会传输大于 2^31-1 字节的文件。它抛出“java.io.IOException:系统资源不足,无法完成所请求的服务被抛出”的异常。解决方法是每次循环复制 64Mb,直到没有更多数据。
回答by Femi
There appears to be anecdotal evidence that attempts to transfer more than 64MB at a time on certain Windows versions results in a slow copy. Hence the check: this appears to be the result of some detail of the underlying native code that implements the transferTo
operation on Windows.
似乎有传闻证据表明,尝试在某些 Windows 版本上一次传输超过 64MB 的数据会导致复制速度变慢。因此检查:这似乎是transferTo
在 Windows 上实现操作的底层本机代码的某些细节的结果。