it-swarm-vi.tech

Làm thế nào để giết một chủ đề ngay lập tức trong C #?

Tôi đang sử dụng phương thức thread.Abort để giết luồng, nhưng nó không hoạt động. Có cách nào khác để chấm dứt chủ đề?

private void button1_Click(object sender, EventArgs e)
{
    if (Receiver.IsAlive == true)
    {
        MessageBox.Show("Alive");
        Receiver.Abort();
    }
    else
    {
        MessageBox.Show("Dead");
        Receiver.Start();
    }
}

Tôi đang sử dụng nhưng mỗi khi tôi nhận được trạng thái Alive, Receiver là chủ đề toàn cầu của tôi.

46
Mobin

Lý do thật khó để giết một luồng là vì các nhà thiết kế ngôn ngữ muốn tránh vấn đề sau: luồng của bạn bị khóa và sau đó bạn giết nó trước khi nó có thể giải phóng nó. Bây giờ bất cứ ai cần khóa đó sẽ bị mắc kẹt.

Những gì bạn phải làm là sử dụng một số biến toàn cục để báo luồng dừng lại. Bạn phải thủ công, trong mã chủ đề của mình, kiểm tra biến toàn cục đó và trả về nếu bạn thấy nó cho biết bạn nên dừng lại.

64
redtuna

Bạn có thể giết ngay lập tức theo cách đó:

private Thread _myThread = new Thread(SomeThreadMethod);

private void SomeThreadMethod()
{
   // do whatever you want
}

[SecurityPermissionAttribute(SecurityAction.Demand, ControlThread = true)]
private void KillTheThread()
{
   _myThread.Abort();
}

Tôi luôn sử dụng nó và làm việc cho tôi :)

31
Nickon

Trước tiên bạn nên có một số phương pháp kết thúc chủ đề. Ví dụ, một running_ có giá trị mà luồng có thể kiểm tra và tuân thủ. 

Mã chủ đề chính của bạn phải được gói trong một khối ngoại lệ bắt cả ThreadInterruptException và ThreadAbortException sẽ dọn dẹp sạch sẽ luồng khi thoát.

Trong trường hợp của ThreadInterruptException, bạn có thể kiểm tra biến running_ để xem bạn có nên tiếp tục không. Trong trường hợp của ThreadAdortException, bạn nên dọn dẹp ngay lập tức và thoát khỏi thủ tục luồng.

Mã cố gắng dừng chuỗi nên làm như sau:

running_ = false;
threadInstance_.Interrupt();
if(!threadInstance_.Join(2000)) { // or an agreed resonable time
   threadInstance_.Abort();
}
19
Adrian Regan

luồng sẽ bị giết khi hoàn thành công việc, vì vậy nếu bạn đang sử dụng các vòng lặp hoặc một cái gì đó khác, bạn nên truyền biến cho luồng để dừng vòng lặp sau khi chuỗi đó kết thúc.

6
Wael Dalloul

C # Thread.Abort KHÔNG được đảm bảo hủy bỏ chuỗi ngay lập tức. Nó có thể sẽ hoạt động khi một luồng gọi Abort trên chính nó chứ không phải khi một luồng gọi vào một luồng khác. 

Vui lòng tham khảo tài liệu: http://msdn.Microsoft.com/en-us/l Library/type8d3wta.aspx

Tôi đã phải đối mặt với vấn đề này bằng cách viết các công cụ tương tác với phần cứng - bạn muốn dừng ngay lập tức nhưng nó không được bảo đảm. Tôi thường sử dụng một số cờ hoặc logic khác để ngăn chặn việc thực thi các phần của mã đang chạy trên một luồng (và điều mà tôi không muốn được thực thi khi hủy bỏ - khó khăn). 

4
Sesh
    private void ResumeButton_Click(object sender, RoutedEventArgs e)
    {
        Task.Factory.StartNew(() =>
        {
            Application.Current.Resources["AutoPilotThreadStatus"] = true;
            Thread.CurrentThread.Name = "ResumeAutoPilot";
            Thread.CurrentThread.IsBackground = true;
            AutoPilotHandler.ResumeAutoPilot();
        });
    }

    public static void ResumeAutoPilot()
    {
        while ((bool)Application.Current.Resources["AutoPilotThreadStatus"])
        {
            CheckAutoPilotThreadStatus();
            var searchYoutube = YoutubeHandler.Search("small truck");
            CheckAutoPilotThreadStatus();
            SaveVideosToDatabase(searchYoutube);
            CheckAutoPilotThreadStatus();
        }
    }

    public static void CheckAutoPilotThreadStatus()
    {
        if (!(bool)Application.Current.Resources["AutoPilotThreadStatus"])
        {
            KillCurrentThread();
        }
    }

    public static void KillCurrentThread()
    {
        Thread.CurrentThread.Abort();
    }
0
Erçin Dedeoğlu