2016-03-31 10 views
2

Ich erstelle eine grundlegende Dateikopie Operation in Windows-Anwendung. Ich bemerkte System.IO File.Copy Dateien nach dem Zufallsprinzip kopieren. Gibt es eine Möglichkeit zu steuern, welche Dateien zuerst kopiert werden sollen. Zum Beispiel, wenn wir Dateien von der kleinsten zur größten Dateigröße kopieren wollen. Oder nach alphabetischer Reihenfolge, beginnen wir mit dem Kopieren von Dateien mit Dateiname [beginnend von] A bis Z oder nach numerischer Reihenfolge mit Dateiname [von] 1 bis 100.Kopieren Sie Datei (en) im Auftrag mit .NET System.IO File.Copy

Ich verwende diesen einfachen Code, um Dateien aus einem Ordner zu kopieren , aber das kopiert Dateien "zufällig". Siehe unten:

Private Sub btnCopy_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnCopy.Click 
    Dim source as string = "c:\copyfiles" 
    Dim destination as string = "d:\backup" 
    Dim filepath as string = destination & "\" 

     For Each filename As String In Directory.GetFiles(source) 
      If File.Exists(filename) Then 
       Dim dFile As String = String.Empty 
       Dim dFilePath As String = String.Empty 

       dFile = Path.GetFileName(filename) 'get filenames from source 
       dFilePath = filepath & dFile 'concatenate filepath and filename 

       File.Copy(filename, dFilePath, True) 'copy files from "c:\copyfiles" folder to destination 
      End If 

     Next 
     MsgBox("Copy Successful", vbOKOnly, "Message") 
End Sub 
+1

Verwenden LINQ die Ergebnisse von 'Verzeichnis zu bestellen. GetFiles ", wie Sie das Kopieren bestellen möchten. – crashmstr

+0

Und da 'System.IO File.Copy' für jeden Aufruf nur eine Datei kopiert, kann dies nicht zufällig geschehen. – crashmstr

+0

@crashmstr Wenn das Kopieren mit der kleinsten bis größten Dateigröße möglich ist. –

Antwort

3

Wenn Sie sie verarbeiten, die von anderen etwas tun wollen, als Name (smallest to largest file size oder vielleicht neueste oder älteste), dann sollten Sie DirectoryInfo verwenden, so können Sie an diesen FileInfo Eigenschaften erhalten.

' simple ordering by size 
Dim dix As New DirectoryInfo(_your_file_path) 
For Each f As FileInfo In dix.EnumerateFiles. 
       OrderByDescending(Function(o) o.Length) 
    ' do stuff 
Next 

Wenn Sie denken, Sie auch Filter benötigen könnten (dh kopieren Sie einfach die Dateien seit dem letzten Mal lief es) dann, EnumerateFiles anstatt GetFiles() mit einigen Linq wird effizienter. In diesem Fall wird .NET Ihre Filter bewerten und geben nur die, die für Ihre (n) Filter und nicht alle von ihnen für Sie manuell in Code auszuschließen:

' process only TXT files in order of size 
For Each f As FileInfo In dix.EnumerateFiles. 
       Where(Function(w) w.Name.EndsWith(".txt")). 
       OrderByDescending(Function(o) o.Length) 
    ' do stuff 
Next 
1

Statt foreach in Directory.GetFiles der Verwendung von() das Ergebnis in eine Liste bekommen und diese Liste sortieren. Wenn Sie basierend auf anderen Werten sortieren möchten, verwenden Sie den FileInfo-Datenblock, um die Dateiinformationen abzurufen und basierend auf diesen Werten zu sortieren.

Mit Ihrer sortierten Liste, dann iterieren Sie es mit Foreach. Die Liste <> stellt garantiert einen Iterator bereit, der Elemente in der Liste in der Reihenfolge zurückgibt, in der sie eingefügt wurden.

public void GetOrderedFiles() 
{ 
    // Get unsorted list of file names 
    List<string> fileNames = System.IO.Directory.GetFiles(strPath); 

    List<System.IO.FileInfo> fileInformationList = new List<System.IO.FileInfo>(); 
    // For each file name, get a full file information block 
    fileNames.ForEach(fileName => fileInformationList.Add(new System.IO.FileInfo(fileName))); 
    // Order by CreationTime. Could be any FileInfo data item. 
    IOrderedEnumerable<System.IO.FileInfo> sortedFileInformation = fileInformationList.OrderBy(item => item.CreationTime); 

    // Iterate round the sorted collection 
    foreach(System.IO.FileInfo fileInformation in sortedFileInformation) 
    { 
     System.IO.File.Copy(fileInformation.FullName, /* Destination file name */) 
    } 
} 
+0

das ist eine gute Idee. Aber es scheint mir schwer zu sein. Wenn Sie ein einfaches Arbeitsbeispiel angeben können. Ich werde deine Antwort definitiv akzeptieren. –

1

Sie müssen sie zuerst

For Each filename As String In Directory.GetFiles(source) 

Änderung über die Linie sortieren:

Dim filenames() as String 
filenames = filenames.OrderBy(Function(f) f.CreationTime) //by time 
filenames = filenames.OrderBy(Function(f) f) //alphabetical, not sure of that one 
filenames = filenames.OrderBy(Function(f) New FileInfo(f).Length) // by size 
    For Each filename As String In filenames 
+0

das ist eine einfache Lösung. Ich hoffe das funktioniert. Danke Freund –

+0

Probieren Sie es aus und lassen Sie mich wissen – Claudius

+0

Ihr Code oben löst einen Fehler aus: "Wert des Typs 'System.Linq.IOrderedEnumerable (Of String)' kann nicht in '1-dimensionales Array von String' umgewandelt werden." –

1

Sortieren nach Namen:

For Each filename As String In Directory.GetFiles(source).OrderBy(Function(f) f) 

Sortieren nach Größe:

For Each filename As String In Directory.GetFiles(source).OrderBy(Function(f) New FileInfo(f).Length) 
Verwandte Themen