5

मैं BackgroundWorker साथ धागा बनाते हैं, और पाश में मैं हर बार की जाँच करता है, तो CancellationPending सच है या नहीं, इस तरह:एप्लिकेशन निष्क्रिय होने पर पृष्ठभूमिवर्कर थ्रेड कितना करीब है?

public MainPage() 
    { 
     InitializeComponent(); 

     bw = new BackgroundWorker(); 
     bw.WorkerReportsProgress = true; 
     bw.WorkerSupportsCancellation = true; 
     bw.DoWork += new DoWorkEventHandler(bw_DoWork); 
     bw.ProgressChanged += new ProgressChangedEventHandler(bw_ProgressChanged); 
     bw.RunWorkerCompleted += new RunWorkerCompletedEventHandler(bw_RunWorkerCompleted); 
    } 

    private void ButtonStart_Click(object sender, RoutedEventArgs e) 
    { 
     if (bw.IsBusy != true) 
     { 
      bw.RunWorkerAsync(); 
     } 
    } 

    private void ButtonCancel_Click(object sender, RoutedEventArgs e) 
    { 
     if (bw.WorkerSupportsCancellation) 
     { 
      bw.CancelAsync(); 
     } 
    } 

    private void bw_DoWork(object sender, DoWorkEventArgs e) 
    { 
     BackgroundWorker worker = sender as BackgroundWorker; 

     for (int i = 1; i <= 100; i++) 
     { 
      Debug.WriteLine("The tread is working"); 
      if (worker.CancellationPending) 
      { 
       e.Cancel = true; 
       bw.CancelAsync(); 
       break; 
      } 
      else 
      { 

       System.Threading.Thread.Sleep(500); 
       worker.ReportProgress(i); 
      } 
     } 
    } 

    private void bw_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e) 
    { 
     if (e.Cancelled) 
     { 
      tbProgress.Text = "Canceled"; 
     } 
     else if (e.Error != null) 
     { 
      tbProgress.Text = "Error: " + e.Error.Message; 
     } 
     else 
     { 
      tbProgress.Text = "Done"; 
     } 
    } 

    private void bw_ProgressChanged(object sender, ProgressChangedEventArgs e) 
    { 
     tbProgress.Text = e.ProgressPercentage.ToString() + "%"; 
    } 

जब आवेदन कर दिया गया है, धागा, बंद नहीं किया गया था यह निरस्त किया जाता है और अपवाद होता है। आवेदन निष्क्रिय होने पर BackgroundWorker के साथ कितने करीब धागे?

+0

क्या आपने इसे आजमाया है? क्या आपको वह चाहिए जो आपको चाहिए? –

+0

@ liho1ey हां, मैंने कोशिश की और whet अनुप्रयोग निष्क्रिय मैं अपवाद प्राप्त किया। मैं इन कोड को पृष्ठ xaml.cs में आवेदन स्तर पर नहीं लिखता हूं। –

+0

ठीक है, लेकिन क्या आप 'CancelAsync() 'को कॉल कर रहे हैं? –

उत्तर

5

क्या आपने BackgroundWorker को रद्द करने योग्य सेट किया था?

var bg= new BackgroundWorker(); 
bg.WorkerSupportsCancellation = true; 

प्रलेखन से:

सेट को सही पर WorkerSupportsCancellation संपत्ति आप BackgroundWorker रद्द समर्थन करने के लिए चाहते हैं। जब यह संपत्ति सत्य होती है, तो आप पृष्ठभूमि ऑपरेशन को बाधित करने के लिए CancelAsync विधि को कॉल कर सकते हैं।

इसके अलावा अपने कोड गलत हो रहा है, तो आप अपने धागा कोड की CancelAsync() बाहर बुलाना चाहिए, इस CancellationPending झंडा है कि आप पाश बाहर निकलने के लिए उपयोग कर सकते हैं सेट हो जाएगा।

हालांकि मुझे 100% यकीन नहीं है क्योंकि मुझे नहीं पता कि bw चर कहां से आ रहा है। `

+0

भी मिलता है मैं अपना कोड संपादित करता हूं। Plz देखो मेरा पूरा कोड है। और हां, मैंने वर्कर सपोर्ट्स कनेक्शन को सही/ –

+0

सेट किया है जैसा कि मैंने कहा था, अपनी do_Work विधि से 'bw.CancelAsync() 'पंक्ति को हटा दें। यह उपयोगी भी होगा यदि आप पोस्ट करते हैं तो आपको – thumbmunkeys

+0

कौन सा अपवाद मिलता है? और जब मैंने प्रोजेक्ट गुणों में डीबग में थंबस्ट सक्षम किया तो मुझे अपवाद मिलता है: mscorlib.dll में 'System.hreading.ThreadAbortException' का पहला मौका अपवाद हुआ। सिस्टम में 'सिस्टम। थ्रेडिंग। थ्रेडएबॉर्ट अपवाद' का पहला मौका अपवाद सिस्टम में हुआ। डीएल –

2

आपको अपने कार्यकर्ता विधि में रद्दीकरण को ध्वजांकित करना चाहिए और ध्वज सेट होने पर शानदार तरीके से बाहर निकलना चाहिए।
नौकरी रद्दीकरण की स्थिति क्या है? रद्द करें बटन क्लिक करें? फिर आपको CancelAsync (...) को कॉल करना चाहिए। यह आपके लिए रद्दीकरण प्लेसमेंट ध्वज सेट करेगा जो आप पहले से ही अपने कोड में जांच रहे हैं, ResetEvent ऑब्जेक्ट की तरह कुछ की आवश्यकता से परहेज करते हैं।

+0

@ 9 एस 6 रद्द करने के लिए कोई शर्त नहीं है आवेदन निष्क्रिय राज्य है। मैं बीडब्ल्यू को थ्रॉन्स्टन करना चाहता हूं जब आवेदन थंबनेल हो जाता है और एप्लिकेशन सक्रिय होने पर थ्रेड जारी रहता है। –

+0

जहां मुझे रद्द करना चाहते हैं? –

+0

आपको अपना ऐप निष्क्रिय होने पर CancelAysnc (...) पर कॉल करना चाहिए और ऐप सक्रिय होने पर पृष्ठभूमिवर्कर को फिर से शुरू करना चाहिए। CancelAsync (...) को कॉल करना रद्द करने के लिए ध्वज सेट करेगा। आप पहले से ही अपने कार्यकर्ता विधि में उस ध्वज की जांच कर रहे हैं --just वहां से CancelAsync (...) को कॉल हटा दें। – A9S6

10

जब कोई ऐप निष्क्रिय हो जाता है, तो मुख्य यूआई थ्रेड के अलावा प्रत्येक थ्रेड थ्रेडएबॉर्ट अपवाद को सक्रिय होने पर ही फेंक देगा। यह "डिजाइन द्वारा" प्रतीत होता है कि ऐप्स को तेज़ी से रोकने के लिए मजबूर करने के तरीके के रूप में वे क्या कर रहे हैं। थ्रेड ThreadAbortException को पकड़ सकते हैं और वे जो कर रहे हैं उसे लपेट सकते हैं, लेकिन ध्यान रखें कि थ्रेडएबॉर्ट अपवाद स्वचालित रूप से कैच ब्लॉक के अंत में फिर से उठाया जाएगा। अंत में ब्लॉक में कोई भी कोड निष्पादित किया जाएगा।

आपके विशिष्ट मुद्दे के लिए, जब ऐप निष्क्रिय हो जाता है तो BackgroundWorker को रद्द करने का कोई कारण नहीं है क्योंकि ThreadAbortException होगा और पृष्ठभूमि कार्यकर्ता को प्रभावी ढंग से रोक देगा। यदि आप ऐसा होने पर साफ करने के लिए कुछ करना चाहते हैं, तो आप bw_DoWork में ThreadAbortException को पकड़ते हैं, जो आपको करने की ज़रूरत है, और फिर इसे मरने दें।

सक्रियण के बाद इसे फिर से शुरू करने के लिए, आपको पृष्ठभूमि कार्यकर्ता को पुनरारंभ करना होगा, जैसा कि आपने पहली बार ऐप चलाया था।

+0

ठीक है, धन्यवाद। (15 वर्ण) –

+0

यह सबसे अच्छा जवाब है – Calanus

1

मैं अपने स्वयं के अवलोकनों के आधार पर उपरोक्त उत्तरों में एक स्पष्टीकरण बिंदु जोड़ना चाहता हूं। उदाहरण धागे संरक्षित होने पर पृष्ठभूमि धागे निष्क्रियता/सक्रियण से बचते हैं।

private void Application_Activated(object sender, ActivatedEventArgs e) 
{ 
    if (e.IsApplicationInstancePreserved) 
    { 
     Log.write("Activating, instance preserved"); 
     // restart long-running network requests 
     startBackground(); 
    } 
    else // start over again 
    { 
     AppSettings.init(); 
     Log.write("Activating, rehydrating"); 
     startBackground(); 
    } 
} 

मैं भी BackgroundWorker वस्तु की hashCode लॉग इन किया जब यह मार डाला:

मैं कोड है कि इस तरह देखा था।मैंने जो देखा वह था कि जब भी मुझे "सक्रियण, उदाहरण संरक्षित" संदेश मिला, तो मुझे अतिरिक्त BackgroundWorker चल रहा था।

इस पर आधारित यह कहने के लिए सटीक लगता है कि थ्रेड को टॉम्बस्टनिंग पर निरस्त कर दिया गया है, निष्क्रियता पर नहीं?

संबंधित मुद्दे