Standard prägnante Möglichkeit, eine Datei in Java zu kopieren?

421

Es hat mich immer gestört, dass die einzige Möglichkeit, eine Datei in Java zu kopieren, darin besteht, Streams zu öffnen, einen Puffer zu deklarieren, eine Datei einzulesen, sie zu durchlaufen und in den anderen Steam zu schreiben. Das Web ist übersät mit ähnlichen, aber immer noch leicht unterschiedlichen Implementierungen dieser Art von Lösung.

Gibt es einen besseren Weg, der innerhalb der Grenzen der Java-Sprache bleibt (was bedeutet, dass keine betriebssystemspezifischen Befehle ausgeführt werden müssen)? Vielleicht würde dies in einem zuverlässigen Open-Source-Dienstprogramm diese zugrunde liegende Implementierung zumindest verdecken und eine einzeilige Lösung bieten?

Peter
quelle
5
In Apache Commons FileUtils könnte etwas enthalten sein , insbesondere die copyFile- Methoden.
Toolkit
22
Wenn Sie Java 7 verwenden, verwenden Sie stattdessen Files.copy, wie von @GlenBest empfohlen: stackoverflow.com/a/16600787/44737
rob

Antworten:

274

Wie oben erwähnt, ist Apache Commons IO der richtige Weg, insbesondere FileUtils . copyFile () ; Es erledigt das ganze schwere Heben für Sie.

Beachten Sie als Postskriptum, dass neuere Versionen von FileUtils (wie die Version 2.0.1) die Verwendung von NIO zum Kopieren von Dateien hinzugefügt haben. NIO kann die Leistung beim Kopieren von Dateien erheblich steigern , zum großen Teil, weil die NIO-Routinen das Kopieren direkt in das Betriebssystem / Dateisystem verzögern, anstatt es durch Lesen und Schreiben von Bytes über die Java-Schicht zu handhaben. Wenn Sie also nach Leistung suchen, sollten Sie überprüfen, ob Sie eine aktuelle Version von FileUtils verwenden.

Delfuego
quelle
1
Sehr hilfreich - haben Sie einen Einblick, wann eine offizielle Veröffentlichung diese nio-Änderungen enthalten wird?
Peter
2
Öffentliche Veröffentlichung von Apache Commons IO noch um 1.4, grrrrrrr
Peter
14
Ab Dezember 2010 befindet sich Apache Commons IO auf 2.0.1, das über die NIO-Funktionalität verfügt. Antwort aktualisiert.
Simon Nickerson
4
Eine Warnung an Android-
Benutzer
18
Wenn Sie Java 7 oder neuer verwenden, können Sie Files.copy verwenden, wie von @GlenBest vorgeschlagen: stackoverflow.com/a/16600787/44737
rob
278

Ich würde die Verwendung einer Mega-API wie Apache Commons vermeiden. Dies ist eine vereinfachte Operation, die im neuen NIO-Paket in das JDK integriert ist. Es war bereits in einer früheren Antwort verlinkt, aber die Schlüsselmethode in der NIO-API sind die neuen Funktionen "transferTo" und "transferFrom".

http://java.sun.com/javase/6/docs/api/java/nio/channels/FileChannel.html#transferTo(long,%20long,%20java.nio.channels.WritableByteChannel)

Einer der verlinkten Artikel zeigt eine großartige Möglichkeit, wie Sie diese Funktion mithilfe von transferFrom in Ihren Code integrieren können:

public static void copyFile(File sourceFile, File destFile) throws IOException {
    if(!destFile.exists()) {
        destFile.createNewFile();
    }

    FileChannel source = null;
    FileChannel destination = null;

    try {
        source = new FileInputStream(sourceFile).getChannel();
        destination = new FileOutputStream(destFile).getChannel();
        destination.transferFrom(source, 0, source.size());
    }
    finally {
        if(source != null) {
            source.close();
        }
        if(destination != null) {
            destination.close();
        }
    }
}

Das Erlernen von NIO kann etwas schwierig sein. Vielleicht möchten Sie einfach auf diesen Mechaniker vertrauen, bevor Sie loslegen und versuchen, NIO über Nacht zu lernen. Aus persönlicher Erfahrung kann es sehr schwierig sein zu lernen, wenn Sie nicht über die Erfahrung verfügen und über die java.io-Streams mit IO vertraut gemacht wurden.

Josh
quelle
2
Danke, nützliche Infos. Ich würde immer noch für so etwas wie Apache Commons argumentieren, besonders wenn es nio (richtig) darunter verwendet; Ich stimme jedoch zu, dass es wichtig ist, die zugrunde liegenden Grundlagen zu verstehen.
Peter
1
Leider gibt es Vorbehalte. Beim Kopieren einer 1,5-GB-Datei unter Windows 7 (32 Bit) konnte die Datei nicht zugeordnet werden. Ich musste nach einer anderen Lösung suchen.
Anton K.
15
Drei mögliche Probleme mit dem obigen Code: (a) Wenn getChannel eine Ausnahme auslöst, kann ein offener Stream verloren gehen. (b) Bei großen Dateien versuchen Sie möglicherweise, mehr auf einmal zu übertragen, als das Betriebssystem verarbeiten kann. (c) Sie ignorieren den Rückgabewert von transferFrom, sodass möglicherweise nur ein Teil der Datei kopiert wird. Aus diesem Grund ist org.apache.tools.ant.util.ResourceUtils.copyResource so kompliziert. Beachten Sie auch, dass transferTo unter JDK 1.4 unter Linux unterbrochen wird
Jesse Glick
7
Ich glaube, diese aktualisierte Version behebt
Mark Renouf
11
Dieser Code hat ein großes Problem. transferTo () muss in einer Schleife aufgerufen werden. Es wird nicht garantiert, den gesamten angeforderten Betrag zu überweisen.
Marquis von Lorne
180

Mit Java 7 können Sie jetzt die folgende Try-with-Resource-Syntax verwenden:

public static void copyFile( File from, File to ) throws IOException {

    if ( !to.exists() ) { to.createNewFile(); }

    try (
        FileChannel in = new FileInputStream( from ).getChannel();
        FileChannel out = new FileOutputStream( to ).getChannel() ) {

        out.transferFrom( in, 0, in.size() );
    }
}

Besser noch, dies kann auch mit der in Java 7 eingeführten neuen Files-Klasse erreicht werden:

public static void copyFile( File from, File to ) throws IOException {
    Files.copy( from.toPath(), to.toPath() );
}

Ziemlich schick, oder?

Scott
quelle
15
Es ist erstaunlich, dass Java solche Dinge bis heute noch nicht hinzugefügt hat. Bestimmte Vorgänge sind nur das Wesentliche beim Schreiben von Computersoftware. Die Oracle-Entwickler von Java könnten ein oder zwei Dinge von Betriebssystemen lernen und sich ansehen, welche Dienste sie bereitstellen, um es für Neulinge einfacher zu machen, zu migrieren.
Rick Hodgin
2
Ah danke! Die neue Klasse "Files" mit all ihren Hilfsfunktionen war mir nicht bekannt. Es hat genau das, was ich brauche. Danke für das Beispiel.
ChrisCantrell
1
In Bezug auf die Leistung ist Java NIO FileChannel besser. Lesen Sie diesen Artikel journaldev.com/861/4-ways-to-copy-file-in-java
Pankaj
5
Dieser Code hat ein großes Problem. transferTo () muss in einer Schleife aufgerufen werden. Es wird nicht garantiert, den gesamten angeforderten Betrag zu überweisen.
Marquis von Lorne
@Scott: Pete hat nach einer einzeiligen Lösung gefragt und Sie sind so nah dran ... es ist nicht notwendig, Files.copy in eine copyFile-Methode zu verpacken. Ich würde einfach die Datei "Files.copy" (Pfad von, Pfad zu) an den Anfang Ihrer Antwort setzen und erwähnen, dass Sie File.toPath () verwenden können, wenn Sie über Dateiobjekte verfügen: Files.copy (fromFile.toPath (), toFile.toPath ())
Rob
89
  • Diese Methoden sind leistungsorientiert (sie lassen sich in native E / A des Betriebssystems integrieren).
  • Diese Methoden arbeiten mit Dateien, Verzeichnissen und Links.
  • Jede der angebotenen Optionen kann weggelassen werden - sie sind optional.

Die Utility-Klasse

package com.yourcompany.nio;

class Files {

    static int copyRecursive(Path source, Path target, boolean prompt, CopyOptions options...) {
        CopyVisitor copyVisitor = new CopyVisitor(source, target, options).copy();
        EnumSet<FileVisitOption> fileVisitOpts;
        if (Arrays.toList(options).contains(java.nio.file.LinkOption.NOFOLLOW_LINKS) {
            fileVisitOpts = EnumSet.noneOf(FileVisitOption.class) 
        } else {
            fileVisitOpts = EnumSet.of(FileVisitOption.FOLLOW_LINKS);
        }
        Files.walkFileTree(source[i], fileVisitOpts, Integer.MAX_VALUE, copyVisitor);
    }

    private class CopyVisitor implements FileVisitor<Path>  {
        final Path source;
        final Path target;
        final CopyOptions[] options;

        CopyVisitor(Path source, Path target, CopyOptions options...) {
             this.source = source;  this.target = target;  this.options = options;
        };

        @Override
        FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) {
        // before visiting entries in a directory we copy the directory
        // (okay if directory already exists).
        Path newdir = target.resolve(source.relativize(dir));
        try {
            Files.copy(dir, newdir, options);
        } catch (FileAlreadyExistsException x) {
            // ignore
        } catch (IOException x) {
            System.err.format("Unable to create: %s: %s%n", newdir, x);
            return SKIP_SUBTREE;
        }
        return CONTINUE;
    }

    @Override
    public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) {
        Path newfile= target.resolve(source.relativize(file));
        try {
            Files.copy(file, newfile, options);
        } catch (IOException x) {
            System.err.format("Unable to copy: %s: %s%n", source, x);
        }
        return CONTINUE;
    }

    @Override
    public FileVisitResult postVisitDirectory(Path dir, IOException exc) {
        // fix up modification time of directory when done
        if (exc == null && Arrays.toList(options).contains(COPY_ATTRIBUTES)) {
            Path newdir = target.resolve(source.relativize(dir));
            try {
                FileTime time = Files.getLastModifiedTime(dir);
                Files.setLastModifiedTime(newdir, time);
            } catch (IOException x) {
                System.err.format("Unable to copy all attributes to: %s: %s%n", newdir, x);
            }
        }
        return CONTINUE;
    }

    @Override
    public FileVisitResult visitFileFailed(Path file, IOException exc) {
        if (exc instanceof FileSystemLoopException) {
            System.err.println("cycle detected: " + file);
        } else {
            System.err.format("Unable to copy: %s: %s%n", file, exc);
        }
        return CONTINUE;
    }
}

Kopieren eines Verzeichnisses oder einer Datei

long bytes = java.nio.file.Files.copy( 
                 new java.io.File("<filepath1>").toPath(), 
                 new java.io.File("<filepath2>").toPath(),
                 java.nio.file.StandardCopyOption.REPLACE_EXISTING,
                 java.nio.file.StandardCopyOption.COPY_ATTRIBUTES,
                 java.nio.file.LinkOption.NOFOLLOW_LINKS);

Verschieben eines Verzeichnisses oder einer Datei

long bytes = java.nio.file.Files.move( 
                 new java.io.File("<filepath1>").toPath(), 
                 new java.io.File("<filepath2>").toPath(),
                 java.nio.file.StandardCopyOption.ATOMIC_MOVE,
                 java.nio.file.StandardCopyOption.REPLACE_EXISTING);

Rekursives Kopieren eines Verzeichnisses oder einer Datei

long bytes = com.yourcompany.nio.Files.copyRecursive( 
                 new java.io.File("<filepath1>").toPath(), 
                 new java.io.File("<filepath2>").toPath(),
                 java.nio.file.StandardCopyOption.REPLACE_EXISTING,
                 java.nio.file.StandardCopyOption.COPY_ATTRIBUTES
                 java.nio.file.LinkOption.NOFOLLOW_LINKS );
Glen Best
quelle
Der Paketname für Dateien war falsch (sollte java.nio.file sein, nicht java.nio). Ich habe dafür eine Bearbeitung eingereicht. hoffe das ist OK!
Stuart Rossiter
43

In Java 7 ist es einfach ...

File src = new File("original.txt");
File target = new File("copy.txt");

Files.copy(src.toPath(), target.toPath(), StandardCopyOption.REPLACE_EXISTING);
Kevin Sadler
quelle
1
Was trägt Ihre Antwort zu Scott's oder Glen's bei?
Uri Agassi
11
Es ist prägnant, weniger ist mehr. Ihre Antworten sind gut und detailliert, aber ich habe sie beim Durchschauen vermisst. Leider gibt es viele Antworten darauf und viele davon sind lang, veraltet und kompliziert, und die guten Antworten von Scott und Glen gingen dabei verloren (ich werde Upvotes geben, um dabei zu helfen). Ich frage mich, ob meine Antwort verbessert werden könnte, indem sie auf drei Zeilen reduziert wird, indem die existierende () und die Fehlermeldung ausgeschaltet werden.
Kevin Sadler
Dies funktioniert nicht für Verzeichnisse. Verdammt, jeder versteht das falsch. Eher ein API-Kommunikationsproblem ist Ihre Schuld. Ich habe es auch falsch verstanden.
mmm
2
@momo die frage war wie man eine datei kopiert.
Kevin Sadler
28

Um eine Datei zu kopieren und in Ihrem Zielpfad zu speichern, können Sie die folgende Methode verwenden.

public void copy(File src, File dst) throws IOException {
    InputStream in = new FileInputStream(src);
    try {
        OutputStream out = new FileOutputStream(dst);
        try {
            // Transfer bytes from in to out
            byte[] buf = new byte[1024];
            int len;
            while ((len = in.read(buf)) > 0) {
                out.write(buf, 0, len);
            }
        } finally {
            out.close();
        }
    } finally {
        in.close();
    }
}
Rakshi
quelle
1
Das wird funktionieren, aber ich denke nicht, dass es besser ist als die anderen Antworten hier?
Rup
2
@ Rup Es ist erheblich besser als die anderen Antworten hier, (a) weil es funktioniert und (b) weil es nicht auf Software von Drittanbietern basiert.
Marquis von Lorne
1
@EJP OK, aber es ist nicht sehr klug. Das Kopieren von Dateien sollte ein Betriebssystem- oder Dateisystemvorgang sein, kein Anwendungsvorgang: Java kann hoffentlich eine Kopie erkennen und in einen Betriebssystemvorgang umwandeln, es sei denn, Sie lesen die Datei explizit, indem Sie sie dabei stoppen. Wenn Sie nicht glauben, dass Java dies kann, würden Sie darauf vertrauen, dass es 1K-Lese- und Schreibvorgänge in größere Blöcke optimiert? Und wenn sich Quelle und Ziel auf einer Remote-Freigabe über ein langsames Netzwerk befinden, ist dies eindeutig unnötige Arbeit. Ja, einige JARs von Drittanbietern sind dumm groß (Guave!), Aber sie fügen eine Menge solcher Dinge hinzu, die richtig gemacht wurden.
Rup
Lief wie am Schnürchen. Beste Lösung, die keine Bibliotheken von Drittanbietern benötigt und unter Java 1.6 funktioniert. Vielen Dank.
James Wierzba
@ Rup Ich stimme zu, dass es eine Betriebssystemfunktion sein sollte, aber ich kann Ihren Kommentar nicht anders verstehen. Dem Teil nach dem ersten Doppelpunkt fehlt irgendwo ein Verb; Ich würde weder "vertrauen" noch erwarten, dass Java 1k-Blöcke in etwas Größeres verwandelt, obwohl ich selbst sicherlich viel größere Blöcke verwenden würde; Ich würde niemals eine Anwendung schreiben, die überhaupt gemeinsam genutzte Dateien verwendet. und mir ist nicht bewusst, dass eine Bibliothek eines Drittanbieters etwas "Richtigeres" tut (was auch immer Sie damit meinen) als diesen Code, außer wahrscheinlich einen größeren Puffer zu verwenden.
Marquis von Lorne
24

Beachten Sie, dass alle diese Mechanismen nur den Inhalt der Datei kopieren, nicht die Metadaten wie Berechtigungen. Wenn Sie also eine ausführbare .sh-Datei unter Linux kopieren oder verschieben, ist die neue Datei nicht ausführbar.

Um eine Datei wirklich zu kopieren oder zu verschieben, dh um das gleiche Ergebnis wie beim Kopieren über eine Befehlszeile zu erzielen, müssen Sie tatsächlich ein natives Tool verwenden. Entweder ein Shell-Skript oder JNI.

Anscheinend könnte dies in Java 7 behoben werden - http://today.java.net/pub/a/today/2008/07/03/jsr-203-new-file-apis.html . Daumen drücken!

Brad bei Kademi
quelle
23

Die Guava-Bibliothek von Google verfügt außerdem über eine Kopiermethode :

public static void copy ( Datei  von,
                         Datei  zu)
                 wirft IOException
Kopiert alle Bytes von einer Datei in eine andere.

Warnung: Wenn es sich toum eine vorhandene Datei handelt, wird diese Datei mit dem Inhalt von überschrieben from. Wenn tound fromauf dieselbe Datei verweisen , wird der Inhalt dieser Datei gelöscht.

Parameter:from - die Quelldatei to- die Zieldatei

Auslöser: IOException - wenn ein E / A-Fehler auftritt IllegalArgumentException- wennfrom.equals(to)

Andrew McKinlay
quelle
7

Drei mögliche Probleme mit dem obigen Code:

  1. Wenn getChannel eine Ausnahme auslöst, kann ein offener Stream verloren gehen.
  2. Bei großen Dateien versuchen Sie möglicherweise, mehr auf einmal zu übertragen, als das Betriebssystem verarbeiten kann.
  3. Sie ignorieren den Rückgabewert von transferFrom, sodass möglicherweise nur ein Teil der Datei kopiert wird.

Deshalb org.apache.tools.ant.util.ResourceUtils.copyResourceist es so kompliziert. Beachten Sie auch, dass transferTo unter JDK 1.4 unter Linux unterbrochen wird (siehe Fehler-ID: 5056395 ) - Jesse Glick Jan.

Saji
quelle
7

Wenn Sie sich in einer Webanwendung befinden, die Spring bereits verwendet, und wenn Sie Apache Commons IO nicht zum einfachen Kopieren von Dateien einschließen möchten, können Sie FileCopyUtils des Spring-Frameworks verwenden.

Balaji Paulrajan
quelle
7

Hier sind drei Möglichkeiten, wie Sie Dateien einfach mit einer einzigen Codezeile kopieren können!

Java7 :

java.nio.file.Files # copy

private static void copyFileUsingJava7Files(File source, File dest) throws IOException {
    Files.copy(source.toPath(), dest.toPath());
}

Appache Commons IO :

FileUtils # copyFile

private static void copyFileUsingApacheCommonsIO(File source, File dest) throws IOException {
    FileUtils.copyFile(source, dest);
}

Guave :

Dateien # kopieren

private static void copyFileUsingGuava(File source,File dest) throws IOException{
    Files.copy(source,dest);          
}
Jaskey
quelle
Erstens funktioniert man nicht für Verzeichnisse. Verdammt, jeder versteht das falsch. Eher ein API-Kommunikationsproblem ist Ihre Schuld. Ich habe es auch falsch verstanden.
mmm
Zunächst benötigt man 3 Parameter. Files.copymit nur 2 Parametern ist für Pathzu Stream. Fügen Sie einfach den Parameter StandardCopyOption.COPY_ATTRIBUTESoder StandardCopyOption.REPLACE_EXISTINGfür PathzuPath
Pimp Trizkit
6
public static void copyFile(File src, File dst) throws IOException
{
    long p = 0, dp, size;
    FileChannel in = null, out = null;

    try
    {
        if (!dst.exists()) dst.createNewFile();

        in = new FileInputStream(src).getChannel();
        out = new FileOutputStream(dst).getChannel();
        size = in.size();

        while ((dp = out.transferFrom(in, p, size)) > 0)
        {
            p += dp;
        }
    }
    finally {
        try
        {
            if (out != null) out.close();
        }
        finally {
            if (in != null) in.close();
        }
    }
}
user3200607
quelle
Der Unterschied zur am häufigsten akzeptierten Antwort besteht also darin, dass Sie transferFrom in einer while-Schleife haben.
Rup
1
Kompiliert nicht einmal und der Aufruf von createNewFile () ist redundant und verschwenderisch.
Marquis von Lorne
3

NIO-Kopie mit Puffer ist nach meinem Test die schnellste. Den folgenden Arbeitscode aus einem meiner Testprojekte finden Sie unter https://github.com/mhisoft/fastcopy

import java.io.Closeable;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.text.DecimalFormat;


public class test {

private static final int BUFFER = 4096*16;
static final DecimalFormat df = new DecimalFormat("#,###.##");
public static void nioBufferCopy(final File source, final File target )  {
    FileChannel in = null;
    FileChannel out = null;
    double  size=0;
    long overallT1 =  System.currentTimeMillis();

    try {
        in = new FileInputStream(source).getChannel();
        out = new FileOutputStream(target).getChannel();
        size = in.size();
        double size2InKB = size / 1024 ;
        ByteBuffer buffer = ByteBuffer.allocateDirect(BUFFER);

        while (in.read(buffer) != -1) {
            buffer.flip();

            while(buffer.hasRemaining()){
                out.write(buffer);
            }

            buffer.clear();
        }
        long overallT2 =  System.currentTimeMillis();
        System.out.println(String.format("Copied %s KB in %s millisecs", df.format(size2InKB),  (overallT2 - overallT1)));
    }
    catch (IOException e) {
        e.printStackTrace();
    }

    finally {
        close(in);
        close(out);
    }
}

private static void close(Closeable closable)  {
    if (closable != null) {
        try {
            closable.close();
        } catch (IOException e) {
            if (FastCopy.debug)
                e.printStackTrace();
        }    
    }
}

}}

Tony
quelle
nett! Dieser ist eher schnell als Standard Java.io Stream .. Kopieren 10 GB nur in 160 Sekunden
aswzen
2

Schnell und arbeiten mit allen Versionen von Java auch Android:

private void copy(final File f1, final File f2) throws IOException {
    f2.createNewFile();

    final RandomAccessFile file1 = new RandomAccessFile(f1, "r");
    final RandomAccessFile file2 = new RandomAccessFile(f2, "rw");

    file2.getChannel().write(file1.getChannel().map(FileChannel.MapMode.READ_ONLY, 0, f1.length()));

    file1.close();
    file2.close();
}
user1079877
quelle
1
Allerdings unterstützen nicht alle Dateisysteme speicherabgebildete Dateien, und ich denke, dass dies für kleine Dateien relativ teuer ist.
Rup
Funktioniert mit keiner Java-Version vor 1.4 und es gibt nichts, was garantiert, dass ein einziger Schreibvorgang ausreicht.
Marquis von Lorne
1

Ein wenig zu spät zur Party, aber hier ist ein Vergleich der Zeit, die zum Kopieren einer Datei mit verschiedenen Dateikopiermethoden benötigt wird. Ich habe die Methoden 10 Mal durchlaufen und einen Durchschnitt ermittelt. Die Dateiübertragung mit E / A-Streams scheint der schlechteste Kandidat zu sein:

Vergleich der Dateiübertragung mit verschiedenen Methoden

Hier sind die Methoden:

private static long fileCopyUsingFileStreams(File fileToCopy, File newFile) throws IOException {
    FileInputStream input = new FileInputStream(fileToCopy);
    FileOutputStream output = new FileOutputStream(newFile);
    byte[] buf = new byte[1024];
    int bytesRead;
    long start = System.currentTimeMillis();
    while ((bytesRead = input.read(buf)) > 0)
    {
        output.write(buf, 0, bytesRead);
    }
    long end = System.currentTimeMillis();

    input.close();
    output.close();

    return (end-start);
}

private static long fileCopyUsingNIOChannelClass(File fileToCopy, File newFile) throws IOException
{
    FileInputStream inputStream = new FileInputStream(fileToCopy);
    FileChannel inChannel = inputStream.getChannel();

    FileOutputStream outputStream = new FileOutputStream(newFile);
    FileChannel outChannel = outputStream.getChannel();

    long start = System.currentTimeMillis();
    inChannel.transferTo(0, fileToCopy.length(), outChannel);
    long end = System.currentTimeMillis();

    inputStream.close();
    outputStream.close();

    return (end-start);
}

private static long fileCopyUsingApacheCommons(File fileToCopy, File newFile) throws IOException
{
    long start = System.currentTimeMillis();
    FileUtils.copyFile(fileToCopy, newFile);
    long end = System.currentTimeMillis();
    return (end-start);
}

private static long fileCopyUsingNIOFilesClass(File fileToCopy, File newFile) throws IOException
{
    Path source = Paths.get(fileToCopy.getPath());
    Path destination = Paths.get(newFile.getPath());
    long start = System.currentTimeMillis();
    Files.copy(source, destination, StandardCopyOption.REPLACE_EXISTING);
    long end = System.currentTimeMillis();

    return (end-start);
}

Der einzige Nachteil, den ich bei der Verwendung der NIO-Kanalklasse feststellen kann, ist, dass ich immer noch keine Möglichkeit finde, den Fortschritt beim Kopieren von Zwischendateien anzuzeigen.

Vinit Shandilya
quelle