2010-01-29 10 views
8

उदाहरण के लिए, मेरे पास बेस इवेंट प्रकाशन विधि है:.NET: घटना हर बार एक अच्छा अभ्यास आग लगने पर नया EventArgs बना रहा है?

 protected virtual OnSomeEvent(EventArgs e) 
    { 
     var handler = SomeEvent; 
     if (handler != null) 
     { 
      handler(this, e); 
      // handler(this, new EventArgs());// EDIT: Yes it should be 
              // handler(this, e), 
              // ignore this one :D 
     } 
    } 

एक व्युत्पन्न वर्ग के लिए जो OnSomeEvent को ओवरराइड करता है और जब यह आग लग जाता है तो एक अतिरिक्त ईवेंट उठाता है:

 protected override OnSomeEvent(EventArgs e) 
    { 
     base.OnSomeEvent(e); 

     if (ExtendedEvent != null) 
     { 
      OnExtendedEvent(e); 
     } 
    } 

    protected void OnExtendedEvent(EventArgs e) 
    { 
     // some stuff done 
     // new information the ExtendedEventArgs object needs 
     // is not available until this point 

     ExtendedEvent(this, new ExtendedEventArgs(someStuff, someOtherStuff)); 
    } 

और अगर व्युत्पत्ति इस तरह से चलती है, यह व्युत्पन्न कक्षा की प्रत्येक पीढ़ी के लिए एक नया व्युत्पन्न EventArgs बनाएगा जिसके लिए इसकी आवश्यकता है। हालांकि ऐसा लगता है कि .NET ढांचे पर EventArgs के विभिन्न व्युत्पन्न को उत्परिवर्तनीय (कोई सेटर्स) नहीं बनाया गया है, यह किसी ऑब्जेक्ट को EventArgs का एक उदाहरण रखने से रोकता है और इसे संशोधित करता है।

तो हर बार इस तरह की आग की तरह एक घटना, यह सभी शामिल EventArgs वस्तुओं के लिए स्मृति आवंटित करेगा। एक ग्राफिक तीव्र अनुप्रयोग में जहां एक घटना प्रति सेकंड दर्जनों बार ट्रिगर की जा सकती है (जैसे नियंत्रण पर OnPaint घटना), क्या यह वाकई एक अच्छा अभ्यास है?

क्या मुझे OnExtendedEvent() में कुछ बदलाव करना चाहिए और ExtendedEventArgs mutable बनाना चाहिए ताकि निम्नलिखित संभव हो?

 protected ExtendedEventArgs extendedArgs = ExtendedEventArgs.Empty; 
    protected void OnExtendedEvent(EventArgs e) 
    { 
     // some stuff done 
     // new information the ExtendedEventArgs object needs 
     // is not available until this point 

     extendedArgs.someProperty1 = someStuff; 
     extendedArgs.someProperty2 = someOtherStuff; 

     ExtendedEvent(this, extendedArgs); 
    } 

संपादित करें: उदाहरण कोड फिक्स्ड, अब स्पष्ट होना चाहिए।

+1

व्युत्पन्न कोई समस्या नहीं है, व्युत्पन्न वर्ग केवल बेस कॉल कर सकता है। EventArgs.Empty के साथ EXExtendedEvent। सामान्य रूप से, अल्पकालिक कचरा बनाने से डरो मत। –

+0

मुझे लगता है कि आप mutable के बजाय अपरिवर्तनीय मतलब है। अपरिवर्तनीय मतलब है कि आप इसे बदल नहीं सकते हैं। – aaronb

उत्तर

3

प्रत्येक बार इसे निकाला जाने पर एक नई अपरिवर्तनीय वस्तु उत्पन्न होगी, क्योंकि घटना तर्कों में मूल्य हैं।

मुख्य कारण यह है कि यदि कोई मौजूदा घटना संभाली जा रही है तो एक नई घटना को फिर से निकाल दिया जाएगा तो क्या होगा?

यह संभवतः मल्टी-थ्रेडेड अनुप्रयोगों में क्या होगा लेकिन फिर भी जैसा कि निम्न उदाहरण द्वारा दिखाए गए किसी एकल थ्रेड पर हो सकता है:

सबसे पहले घटना के बाद मूल्यों के साथ निकाल दिया जाता है:

extendedArgs.someProperty1 = "Fire 1"; 
extendedArgs.someProperty2 = "Fire 1 Other Stuff"; 
किसी भी तरह

फिर पहला इवेंट हैंडलर कुछ तर्कों को फिर से निम्नलिखित तर्कों के साथ निकाल दिया जाता है:

extendedArgs.someProperty1 = "Fire 2"; 
extendedArgs.someProperty2 = "Fire 2 Other Stuff"; 

सभी ईवेंट हैंडलर ar दूसरी घटना के लिए ई संसाधित हो रहे हैं, और अब हम पहले आयोजन के लिए बाकी ईवेंट हैंडलर को संसाधित करने के लिए वापस आ गए हैं।

अब उसी ऑब्जेक्ट का उपयोग किया जाता है क्योंकि पहले ईवेंट के लिए सभी ईवेंट हैंडलर अब अपने कुछ प्रॉपर्टी 1 के रूप में "फायर 2" होंगे, क्योंकि दूसरी घटना मूल्यों को ओवरराइट करती है।

जैसा कि @ नोबगज़ ने उल्लेख किया है कि अल्पकालिक कचरा बनाने से डरो मत।

1

मैं आपके OnExtendedEvent कोड से थोड़ा उलझन में हूं - क्या आप इस घटना को SomeEvent के रूप में पुनः खोजना चाहते हैं?

एक ग्राहक एक ईवेंट हैंडलर जोड़ता है तो वे उम्मीद करते हैं कि वे जबकि घटना से निपटने ईवेंट हैंडलर दूर करने के लिए, इस तरह सक्षम हैं:

someObject.SomeEvent += OnSomeEvent; 
// ... 
private void OnSomeEvent(object sender, EventArgs e) 
{ 
    someObject.SomeEvent -= OnSomeEvent; 
} 

आप मानक भेजने अभ्यास का पालन नहीं करते हैं, तो इस कोड को होगा अपने कोड का उपयोग कर व्यक्ति के आश्चर्य के लिए एक अपवाद बहुत फेंक दें।

+0

हाय, क्षमा करें कोड उलझन में है। अब फिक्स्ड: डी – Dan7

5

सबसे पहले, अगर आप इसे अभी भी अनदेखा कर रहे हैं तो अपने फायरिंग विधि पर EventArgs तर्क क्यों लें? यह वास्तविक अपशिष्ट है, लेकिन संसाधन की खपत झूठ की तुलना में कम समस्याग्रस्त है कि आपकी विधि अपने कॉलर्स को बता रही है। बस के माध्यम से पर तर्क गुजरती हैं, अपने फायरिंग विधि संभावना प्रासंगिक जानकारी सुलभ बनाने के लिए नहीं होगा EventArgs वैसे भी वस्तु:

protected virtual OnSomeEvent(EventArgs e) 
{ 
    var handler = SomeEvent; 
    if (handler != null) 
    { 
     handler(this, e); 
    } 
} 

तो, अब हम चाहते हैं कि सीधे, यदि आपका EventArgs आपत्ति बताने के लिए कोई सार्थक जानकारी नहीं है कि अपने ग्राहक, बस EventArgs.Empty का उपयोग करें, यही वह है जो इसके लिए है। आप अपने कस्टम EventArgs कक्षाओं के लिए एक ही पैटर्न का पालन कर सकते हैं, लेकिन ईमानदारी से, आप कुछ भी नहीं के बारे में चिंता कर रहे हैं। EventArgs ऑब्जेक्ट्स बनाना आपके एप्लिकेशन में कभी भी बाधा नहीं होगा, और यदि ऐसा है, तो आपके पास डिज़ाइन समस्याएं हैं।

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