2012-01-03 20 views
6

mam aplikację, która wywołuje mój DLL z InvokeMember() tak:C# zabić wszystkich wątków

Assembly OCA = Assembly.LoadFrom("./Modules/ProcessFiles.dll"); 
Type[] types = OCA.GetTypes(); 
foreach (var type in types) 
{ 
    //MethodInfo[] methods = type.GetMethods(); 
    if (type.Name == "Converter") 
    { 
     var tmpType = type; 
     var obj = Activator.CreateInstance(tmpType); 
     Thread t = new Thread(
      () => 
      tmpType.InvokeMember("Run", BindingFlags.Default | BindingFlags.InvokeMethod, null, obj, 
      null)); 
     t.Start(); 
     break; 
    } 

} 

Moje DLL następnie tworzy nowy wątek i rozpoczyna przetwarzanie. W mojej bibliotece DLL utworzę nowy wątek:

Thread thread = new Thread(
    delegate(){ 
     while(true) 
     { 
      GetFilesInFolder(); 
      Thread.Sleep(120000); 
     } 
    }); 
ne.Start(); 

Celem jest okresowe sprawdzanie folderu. Problem polega na tym, że kiedy zamykam aplikację, która wywołuje moją bibliotekę DLL, proces nie jest zamykany. Czy istnieje sposób na zamknięcie wszystkich wątków?

NB: Nie mogę zmodyfikować aplikacji, mogę tylko modyfikować moją bibliotekę DLL.

Odpowiedz

8

Ustaw właściwość IsBackground wątku na true. Spowoduje to zabicie wątku po zakończeniu aplikacji.

Ponadto: Dlaczego nie używasz jednego licznika czasu (lub tylko jednego wątku), który budzi i wyłudza dane. To powinno być bardziej przyjazne dla zasobów.

+0

Próbowałem użyć timera, ale nie mogłem dostać Threading.Timer pracy. – hs2d

+0

Jest też Timers.Timer –

+0

Tak, wiem o tym wszystkim. Może możesz dać mi działający przykład wykorzystania timera w mojej sytuacji? – hs2d

6

Czy próbowałeś użyć System.IO.FileSystemWatcher? to powoduje zdarzenia, gdy coś się zmienia w folderze. Wygląda na to, że uprości to twoje rozwiązanie.

+0

Tak, jestem przy użyciu 'FileSystemWatcher' allso dla nowych plików i chenges. Ale jest nieco bardziej skompilowany. Niektóre pliki po prostu nie są gotowe do przetworzenia i muszę je zostawić w tym folderze, a potem przejrzę je później. – hs2d

0

Można używać wątek tła wymienionych powyżej lub czasowy:

Timer checkTimer; 
public void StartTimer() 
{ 
    checkTimer = new Timer(s => GetFilesInFolder(), null, 0, 120000); 
} 

Nie zapomnij go wyrzucić.

1

Jak o wdrożenie bezpiecznych Rezygnacja z here

class RulyCanceler 
{ 
    object _cancelLocker = new object(); 
    bool _cancelRequest; 
    public bool IsCancellationRequested 
    { 
    get { lock (_cancelLocker) return _cancelRequest; } 
    } 

    public void Cancel() { lock (_cancelLocker) _cancelRequest = true; } 

    public void ThrowIfCancellationRequested() 
    { 
    if (IsCancellationRequested) throw new OperationCanceledException(); 
    } 
} 

test

class Test 
{ 
    static void Main() 
    { 
    var canceler = new RulyCanceler(); 
    new Thread (() => { 
         try { Work (canceler); } 
         catch (OperationCanceledException) 
         { 
          Console.WriteLine ("Canceled!"); 
         } 
         }).Start(); 
    Thread.Sleep (1000); 
    canceler.Cancel();    // Safely cancel worker. 
    } 

    static void Work (RulyCanceler c) 
    { 
    while (true) 
    { 
     c.ThrowIfCancellationRequested(); 
     // ... 
     try  { OtherMethod (c); } 
     finally { /* any required cleanup */ } 
    } 
    } 

    static void OtherMethod (RulyCanceler c) 
    { 
    // Do stuff... 
    c.ThrowIfCancellationRequested(); 
    } 
} 
Powiązane problemy