Copia efectiva de múltiples archivos
Pregunta
Tengo que copiar muchos archivos de una carpeta a otra. Actualmente lo estoy haciendo de esta manera:
string[] files = Directory.GetFiles(rootFolder, "*.xml");
foreach (string file in files)
{
string otherFile = Path.Combine(otherFolder, Path.GetFileName(file));
File.Copy(file, otherFile);
}
¿Es esa la forma más eficiente? Parece tomar años.
EDITAR: Realmente estoy preguntando si hay una forma más rápida de hacer una copia por lotes, en lugar de copiar archivos individuales, pero supongo que la respuesta es no.
Solución
No puedo pensar en una forma más eficiente que File.Copy, va directamente al sistema operativo.
Por otro lado, si toma tanto tiempo, sugeriría encarecidamente mostrar un diálogo de progreso, como SHFileOperation lo hace por usted. Al menos sus usuarios sabrán lo que está sucediendo.
Otros consejos
Puede usar el sistema operativo para mover los archivos. Esto es lo que hacen herramientas como WinMerge. Hace clic en " copiar " abotone en su aplicación y aparece el cuadro de progreso de Windows como si hubiera utilizado el Explorador para organizar la copia. Este hilo lo describe.
Recientemente implementé mis copias de archivos usando filestreams en VB .NET:
fsSource = New FileStream(backupPath, FileMode.OpenOrCreate, FileAccess.Read, FileShare.None, 1024, FileOptions.WriteThrough)
fsDest = New FileStream(restorationPath, FileMode.OpenOrCreate, FileAccess.Write, FileShare.None, 1024, FileOptions.WriteThrough)
TransferData(fsSource, fsDest, 1048576)
Private Sub TransferData(ByVal FromStream As IO.Stream, ByVal ToStream As IO.Stream, ByVal BufferSize As Integer)
Dim buffer(BufferSize - 1) As Byte
Do While IsCancelled = False 'Do While True
Dim bytesRead As Integer = FromStream.Read(buffer, 0, buffer.Length)
If bytesRead = 0 Then Exit Do
ToStream.Write(buffer, 0, bytesRead)
sizeCopied += bytesRead
Loop
End Sub
Parece rápido y una forma muy fácil de actualizar la barra de progreso (con sizeCopied) y cancelar la transferencia de archivos si es necesario (con IsCancelled).