2012-12-06 44 views
2

示例程序:侦听某个文件夹中的FileSystem事件,并在Timer事件触发时将FileSystem事件信息打印到控制台。C#事件和线程

class Program 
{ 
    public static string location = @"D:\TestEvents"; 
    public static double interval = 15000; 

    public static System.Timers.Timer timer; 
    public static List<string> listOfChanges = new List<string>(); 

    static void Main(string[] args) 
    { 
     StartWatch(); 
     StartTimer(); 

     Console.ReadLine(); 
    } 

    private static void StartWatch() 
    { 
     FileSystemWatcher Watcher = new FileSystemWatcher(); 
     Watcher.Path = location; 
     Watcher.Created += new FileSystemEventHandler(OnFileCreatedOrDeleted); 
     Watcher.Deleted += new FileSystemEventHandler(OnFileCreatedOrDeleted); 
     Watcher.EnableRaisingEvents = true; 
    } 

    static void OnFileCreatedOrDeleted(object sender, FileSystemEventArgs e) 
    { 
     listOfChanges.Add(String.Format("Change Type: {0}, Name: {1}, Time: {2}", e.ChangeType, e.Name, DateTime.Now)); 
    } 

    private static void StartTimer() 
    { 
     timer = new System.Timers.Timer(); 
     timer.AutoReset = false; 
     timer.Elapsed += new System.Timers.ElapsedEventHandler(OnTimerEpleased); 
     timer.Interval = interval; 
     timer.Start(); 
    } 

    private static void OnTimerEpleased(object sender, System.Timers.ElapsedEventArgs e) 
    { 
     Console.WriteLine("Timer event fired: " + DateTime.Now); 
     foreach (var item in listOfChanges) 
     { 
      Console.WriteLine(item); 
     } 
     Console.WriteLine(); 
     listOfChanges.Clear(); 

     timer.Interval = interval; 
     timer.Start(); 
    } 
} 

从两个事件处理程序访问相同的存储静态List<string> listOfChanges是否安全? 我不太了解事件如何在底下工作。是否创建了一些全局事件处理程序队列,并且尽管事件类型是一个接一个地运行所有事件处理程序?或者它为每个事件处理程序类型创建不同的线程?

编辑: 我想最好的解决办法是使用BlockingCollectionConcurrentQueue,所以它应该是这样的:

public static BlockingCollection<string> listOfChanges = new BlockingCollection<string>(); 

static void OnFileCreatedOrDeleted(object sender, FileSystemEventArgs e) 
{ 
    listOfChanges.Add(String.Format("Change Type: {0}, Name: {1}, Time: {2}", e.ChangeType, e.Name, DateTime.Now)); 
} 

private static void OnTimerEpleased(object sender, System.Timers.ElapsedEventArgs e) 
{ 
    Console.WriteLine("Timer event fired: " + DateTime.Now); 
    while (listOfChanges.Count > 0) 
    { 
     string item; 
     bool b = listOfChanges.TryTake(out item); 
     if (b) 
     { 
      Console.WriteLine(item); 
     } 
    } 
    Console.WriteLine(); 

    timer.Interval = interval; 
    timer.Start(); 
} 

回答

0

林不知道如果FileSystemWatcher对象使用一个以上的线程,但只是要你访问列表中

lock (listOfChanges) 
{ 
    //Code that reads or writes to the listOfChanges. 
} 
安全包
0

你不应该假设,那些事件处理程序将从单个线程中调用。 FileSystemWatcher和Timer的文档都没有提到这些处理程序是如何被调用的,所以我会在这里选择安全的方式,并确保我自己对这个列表的访问是同步的。