2010-09-04 56 views
7

Tôi cần thủ tục kiểm tra xem thư mục/tệp mới đã được thêm vào thư mục đã chọn chưa. Tôi cần quy trình này để chạy khi ứng dụng khởi động nên thời gian xử lý ở giai đoạn này là quan trọng.Làm cách nào để kiểm tra xem nội dung của thư mục có bị thay đổi hay không

Tôi đoán tôi có thể tạo nhật ký trạng thái hiện tại, nhật ký của trạng thái trước đó, sắp xếp và so sánh chúng.

  1. Trước tiên, tôi cần biết nếu có cách nào khác.

  2. Thứ hai nếu không có cách nào khác là cách tốt nhất để tìm sự khác biệt giữa hai danh sách đường dẫn tệp: cả cấu trúc và thuật toán.

Cũ trạng:

c:\firstfolder\a.doc 
c:\firstfolder\b.doc 
c:\firstfolder\secondFolder\a.doc 
c:\firstfolder\secondFolder\b.doc 

New trạng:

c:\firstfolder\a.doc 
c:\firstfolder\b.doc 
c:\firstfolder\secondFolder\a.doc 
c:\firstfolder\secondFolder\b.doc 
c:\firstfolder\secondFolder\c.doc 

Tôi đang tìm c:\firstfolder\secondFolder\c.doc.

+0

Bạn cần phải biết * nếu * đã có một sự thay đổi, tức là 'kết quả boolean', hoặc gì đã thay đổi, tức là' Danh sách '? =) – Rob

+0

cần danh sách ... Tôi quản lý để làm điều đó theo cách sau tạo một tệp xml cho trạng thái trước đó và chính xác và so sánh nó bằng cách sử dụng "Ngoại trừ" như Timwi sugested: http://stackoverflow.com/question/3647958/find-the-delta-between-two-xelements-using-except-c ...nó hoạt động nhưng nó là chậm – Asaf

Trả lời

1

Vì ứng dụng của bạn không chạy liên tục, sử dụng FileSystemWatcher dường như không phải là một lựa chọn tốt cho bạn, nhưng tôi muốn đề cập đến nó vì nó có thể gây ra một số ý tưởng về phía bạn.

Nếu bạn có một danh sách các trạng thái cũ và tạo ra một danh sách các trạng thái mới, bạn có thể sử dụng một thuật toán như một phác thảo here để so sánh hai danh sách để xác định bổ sung và xóa từ danh sách đầu tiên được tạo ra. Đó là câu trả lời được chấp nhận cho liên kết được cung cấp cũng có một giải pháp tốt đẹp hoạt động rất tốt nếu các danh sách không được sắp xếp.

+0

HashSets trông đầy hứa hẹn nhưng tôi không biết bất cứ điều gì về họ ... Cố gắng cố gắng tìm hiểu thêm về chúng. Cảm ơn – Asaf

3

Bạn có thể sử dụng lớp học FileSystemWatcher, tôi nghĩ rằng nó đang làm chính xác những gì bạn đang làm sau.

+3

Điều đó chỉ hoạt động khi ứng dụng đang chạy. Nó sẽ không phát hiện những thay đổi xảy ra giữa các lời gọi của chương trình. – ChrisF

+1

+1 @CyberDude: cảm ơn, rất tốt khi biết rằng người nghe này tồn tại, (nó làm tôi tự hỏi nếu tôi cần nó) nhưng ChrisF nói nó chỉ bắt những thay đổi trong thời gian chạy, và tôi cần phải biết những gì đã thay đổi kể từ khi chạy trước đó của ứng dụng – Asaf

0

Tôi nghĩ rằng đặt cược tốt nhất là đệ quy qua thư mục và lưu trạng thái. Một cái gì đó như thế này:

public List<FileData> RecurseDirectory(string directory, int level, out int files, out int folders) 
     { 
      IntPtr INVALID_HANDLE_VALUE = new IntPtr(-1); 
      //long size = 0; 
      files = 0; 
      folders = 0; 
      WIN32_FIND_DATA findData; 
      List<FileData> list = new List<FileData>(); 

      IntPtr findHandle; 

      // add global escape chars if not present. 
      if (directory.StartsWith(@"\\?\")) 
      { 
       findHandle = FindFirstFile(directory + @"\*", out findData); 
      } 
      else 
      { 
       findHandle = FindFirstFile(@"\\?\" + directory + @"\*", out findData); 
      } 


      if (findHandle != INVALID_HANDLE_VALUE) 
      { 
       //if file exists: 


       do 
       { 
        if ((findData.dwFileAttributes & FileAttributes.Directory) != 0) 
        { 
         //if it's a directory: 

         if (findData.cFileName != "." && findData.cFileName != "..") 
         { 
          //increment folder counter. 
          folders++; 

          int subfiles, subfolders; 
          string subdirectory = directory + (directory.EndsWith(@"\") ? "" : @"\") + 
           findData.cFileName; 
          //Console.WriteLine("Dir:" + subdirectory); 

          //add it to list 
          String path = subdirectory; 
          FileData tempFileData = new FileData(); 
          tempFileData.path = path; 
          tempFileData.fileProperties = findData; 
          list.Add(tempFileData); 

          //allows -1 to do complete search. 
          if (level != 0) 
          { 
           //recurse through to next subfolder 
           list.AddRange(RecurseDirectory(subdirectory, level - 1, out subfiles, out subfolders)); 

           folders += subfolders; 
           files += subfiles; 
          } 
         } 
        } 
        else 
        { 
         // File 
         files++; 
         string subfile = directory + (directory.EndsWith(@"\") ? "" : @"\") + 
           findData.cFileName; 
         //Console.WriteLine("File:" + subfile); 
         //list.Add("File:" + subfile); 
         String path = subfile; 
         FileData t = new FileData(); 
         t.path = path; 
         t.fileProperties = findData; 
         list.Add(t); 

         //size += (long)findData.nFileSizeLow + (long)findData.nFileSizeHigh * 4294967296L; 
        } 
       } 
       while (FindNextFile(findHandle, out findData)); 
       FindClose(findHandle); 

      } 

      return list; 
     } 

Sau này, bạn sẽ có danh sách trạng thái. Nếu bạn có trạng thái cũ trong danh sách. So sánh các danh sách ngay bây giờ.

+0

Không cần cho tất cả đệ quy, Directory.GetDirectories và trong Framework 4.0 Directory.EnumerateDirectories có thể đi qua toàn bộ cây trong một cuộc gọi duy nhất. Chưa kể rằng mã trên cũng sẽ yêu cầu khai báo P/Invoke bổ sung, không được hiển thị. –

0

Bạn có thể lưu thông tin thời gian của trạng thái cuối cùng. Sau đó, bạn chỉ có thể so sánh thời gian tạo của các tập tin và thư mục với điều đó. Mã sau đây có thể cung cấp cho bạn ý tưởng:

foreach(FileInfo f in dir.GetFiles() { 
    if(f.CreationTime > dtLastState) { 
     //do some interesting stuff 
    } 
} 

Chỉnh sửa: Đây không phải là câu trả lời hoàn chỉnh. Bạn không thể lấy các tệp đã xóa bằng mã này.

2

Tôi nghĩ rằng Khung đồng bộ hóa có thể là những gì bạn đang tìm kiếm.

http://msdn.microsoft.com/en-us/sync/default.aspx

+0

Tôi cần so sánh hai thư mục có cùng thư mục con nhưng các tệp chỉ bằng tên ... chúng được tạo riêng để nội dung, kích thước và các tham số khác không bằng thư mục nguồn. Đó là lý do tôi không nghĩ rằng giải pháp của bạn sẽ làm việc cho tôi lần này. Cảm ơn Asaf – Asaf

Các vấn đề liên quan