【问题标题】:Suspending a thread in a wpf application在 wpf 应用程序中挂起线程
【发布时间】:2014-01-13 08:37:36
【问题描述】:

我有一个 WPF 应用程序,其中我有这个类:

public partial class Global : UserControl
    {
        public static List<Thread> listofthreads = new List<Thread>();
        public Global()
        {
            InitializeComponent();
           Thread windowThread = new Thread(delegate() { verifing(); });
           listofthreads.Add(windowThread);
            windowThread.Start();

        }

        public void verifing()
        {
            if (Global2.Pat_pathregfile.Length > 5 && Global2.Pat_pathcalibfile.Length > 5) {
                if (utilisation.Dispatcher.CheckAccess())
                {
                    utilisation.Visibility = Visibility.Visible;
                }
                else
                {

                    utilisation.Dispatcher.Invoke(DispatcherPriority.Normal, (Action)(() =>
                    {
                        utilisation.Visibility = Visibility.Visible;
                    }));

                }
                foreach (Thread t in listofthreads) {
                    try
                    {
                        t.Suspend();
                    }
                    catch { }
                }

            }
            else {
                if (utilisation.Dispatcher.CheckAccess())
                {
                    utilisation.Visibility = Visibility.Hidden;
                }
                else
                {

                    utilisation.Dispatcher.Invoke(DispatcherPriority.Normal, (Action)(() =>
                    {
                        utilisation.Visibility = Visibility.Hidden;
                    }));

                }
                Thread windowThread = new Thread(delegate() { verifing(); });
                windowThread.Start();
                listofthreads.Add(windowThread);
            }

        }


    }

我需要杀死properly我使用过的所有线程

 foreach (Thread t in listofthreads) {
                        try
                        {
                            t.Suspend();
                        }
                        catch { }
                    }

但程序提示不推荐使用suspend方法。

  1. 为什么?
  2. 似乎有些线程在关闭窗口后仍在工作,为什么会出现这种情况?我该如何解决?
  3. wpf 中是否存在另一种杀死线程的方法?

【问题讨论】:

  • Suspend 方法已被标记为过时。你应该使用ManualResetEvent 来同步线程。
  • 更好地解释一下,你想达到什么目的。您对线程的使用和Visibility 的设置表明您做错了事。您是否尝试执行某种验证?
  • 你不想挂起一个线程。您希望将线程置于等待状态,或发出信号让线程自行终止。但是你不想挂起,也不想杀死一个线程。

标签: c# wpf multithreading thread-safety threadpool


【解决方案1】:

你想做什么?您创建线程只是为了检查某些条件?当条件为真时,您更改可见性并阻止所有线程(!)进一步执行。当条件不成立时,您将创建另一个执行相同操作的线程。为什么要暂停所有线程(包括活动线程)而不是让它终止?如果您想定期检查某个条件,请改用计时器或等待事件。

顺便说一句:您的 foreach 循环最终会抛出 InvalidOperationException,因为您正在更改没有锁定的集合。

然后,不要试图杀死线程。改用标志或信号。任何杀死线程的尝试都是 a) 糟糕的设计和 b) 容易出错和意外行为。

【讨论】:

  • 你说Why are you suspending all threads (including the active one) instead of just letting it terminate :我需要线程无限,直到条件为真
  • 您的线程将永远不会结束或立即结束(并产生一个新线程)。如果你想等待一个条件,你需要在你的线程中添加一个循环。对于您要实现的目标,您的代码 复杂。除此之外,您正在执行多线程忙等待。使用一个带循环的线程,或者更好的是,在条件发生变化时发出信号。
  • 感谢@PMF 和@Rohit Vats:你的方法比我的好。我在线程中添加了循环,并使其成为windowThread.IsBackground = true;,所以我得到了一个很好的结果:)
【解决方案2】:

1) 为什么?

Suspend 方法已被Microsoft 标记为Obsolete。错误状态本身:

Thread.Suspend 已被弃用。请使用其他类 System.Threading,例如 Monitor、Mutex、Event 和 Semaphore,以 同步线程或保护资源。


2) 似乎有些线程在关闭后仍在工作 窗户,为什么会这样?我该如何解决?

您已以foreground thread 启动所有线程,当主线程完成执行时不会自动停止。如果您想在所有前台线程停止后停止所有线程,则应将线程标记为background thread

windowThread.IsBackground = true;

3) wpf中是否存在另一种杀死线程的方法?

使用Thread.Abort()。但是,关闭主线程会自动停止所有后台线程(IsBackground 在线程上设置为 true),您不必担心会杀死它们。

【讨论】:

    猜你喜欢
    • 2011-02-10
    • 1970-01-01
    • 2013-03-04
    • 2011-03-13
    • 1970-01-01
    • 2011-09-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多