2017-06-02 13 views
23

के बीच अंतर मैं कुछ UI संबंधित संचालन करने के लिए लंबे समय से DispatchQueue.main.async का उपयोग कर रहा हूं। लेकिन स्विफ्ट DispatchQueue.main.async और DispatchQueue.main.sync प्रदान करता है और दोनों मुख्य कतार में किए जाते हैं। तो क्या कोई मुझे उनके बीच अंतर बता सकता है? और मुझे उनका उपयोग कब करना चाहिए? अग्रिम धन्यवाद।DispatchQueue.main.async और DispatchQueue.main.sync

 DispatchQueue.main.async { 
      self.imageView.image = imageView 
      self.lbltitle.text = "" 

     } 
     DispatchQueue.main.sync { 
      self.imageView.image = imageView 
      self.lbltitle.text = "" 

     } 

उत्तर

44

क्यों संगामिति? जैसे ही आप अपने ऐप में जोड़ते हैं, डेटा लोडिंग जैसे भारी कार्यों में यह आपके यूआई काम को धीमा कर देता है या यहां तक ​​कि इसे फ्रीज करता है। Concurrency आपको 2 या अधिक कार्यों को "एक साथ" करने देता है। इस दृष्टिकोण का नुकसान एक थ्रेड सुरक्षा है जो हमेशा नियंत्रण में आसान नहीं होता है। उदा जब विभिन्न कार्य समान संसाधनों तक पहुंचना चाहते हैं जैसे एक ही चर को एक अलग थ्रेड पर बदलने या विभिन्न थ्रेडों द्वारा पहले से अवरुद्ध संसाधनों तक पहुंचने का प्रयास करना चाहते हैं।

कुछ ऐसे अवतार हैं जिन्हें हमें जागरूक करने की आवश्यकता है।

  • पंक्तियां।
  • तुल्यकालिक/असीमित कार्य प्रदर्शन।
  • प्राथमिकताएं।
  • आम समस्याएं।

कतार

धारावाहिक या समवर्ती होना चाहिए। साथ ही साथ वैश्विक या निजी एक ही समय में।

धारावाहिक कतार कार्यों पर एक-एक करके समाप्त हो जाएगा जबकि समवर्ती कतार कार्यों पर एक साथ प्रदर्शन किया जाएगा और अप्रत्याशित अनुसूची के साथ समाप्त हो जाएगा। कार्यों के समान समूह समवर्ती की तुलना में सीरियल कतार पर अधिक लंबा समय लगेगा।

आप बना सकते हैं अपने खुद के निजी कतारों (दोनों धारावाहिक या समवर्ती) या का उपयोग पहले से ही उपलब्ध वैश्विक (सिस्टम) कतार। केवल मुख्य कतारसीरियलवैश्विक कतार में से एक है।

यह बेहद भारी कार्यों के लिए जो यूआई काम के साथ (नेटवर्क से फ़े डेटा लोड) मुख्य कतार पर नहीं भेजा है प्रदर्शन करने के लिए नहीं की सिफारिश की है, लेकिन अन्य कतारों पर यूआई unfrozen और के लिए उत्तरदायी रखने के लिए उपयोगकर्ता क्रियाएं यदि हम अन्य कतारों पर UI को बदलते हैं तो परिवर्तनों को एक अलग अप्रत्याशित शेड्यूल और गति के साथ बनाया जा सकता है, इसलिए कुछ UI तत्वों को इसकी आवश्यकता से पहले खींचा जा सकता है या जब बहुत देर हो चुकी है। यह यूआई को दुर्घटनाग्रस्त कर सकता है।यह भी ध्यान में रखना चाहिए कि वैश्विक कतारसिस्टम कतार पर कुछ अन्य कार्य सिस्टम द्वारा चलाए जा सकते हैं।


सेवा/प्राथमिकता की गुणवत्ता। मुख्य कतार
.userInitiated - - के लिए
.userInteractive:

कतार भी अलग QoS (सेवा की गुणवत्ता) जो कार्य (यहाँ उच्चतम से न्यूनतम) प्राथमिकता प्रदर्शन सेट है उपयोगकर्ता द्वारा आरंभ किए कार्यों उपयोगकर्ता कुछ प्रतिक्रिया
.utility के लिए इंतजार कर रहा है, जिस पर - कार्यों के लिए जो कुछ समय लगता है और डेटा
.background के साथ काम कर तत्काल प्रतिक्रिया, जैसे की आवश्यकता नहीं है के लिए - उन कार्यों के लिए जो दृश्य भाग से संबंधित नहीं हैं और जो पूर्ण होने के समय के लिए सख्त नहीं हैं)।

वहाँ भी

.DEFAULT कतार जो क्यूओएस जानकारी स्थानांतरित शामिल नहीं है। यदि यह क्यूओएसक्यूओएस उपयोग किया जाएगा के बीच .userInitiated और .utility पता लगाने के लिए संभव नहीं था।

कार्य तुल्यकालिक या एसिंक्रोनस रूप किया जा सकता है।

  • तुल्यकालिक समारोह वर्तमान कतार पर नियंत्रण के बाद ही कार्य समाप्त हो गया है देता है। यह कतार को अवरुद्ध करता है और कार्य पूरा होने तक प्रतीक्षा करता है।

  • असीमित फ़ंक्शन अलग कतार पर कार्य करने के बाद सही कतार पर नियंत्रण देता है। यह कार्य पूरा होने तक इंतजार नहीं करता है। यह कतार को अवरुद्ध नहीं करता है।

आम मुसीबतों।

सबसे लोकप्रिय गलतियों प्रोग्रामर जबकि समवर्ती क्षुधा पेश कर निम्नलिखित हैं:

  • दौड़ हालत - तब होता है जब एप्लिकेशन काम कोड भागों निष्पादन के आदेश पर निर्भर करता है।
  • प्राथमिकता उलट - छोटे प्राथमिकता कार्य की उच्च प्राथमिकता कार्य प्रतीक्षा की वजह से कुछ संसाधनों ब्लॉक किए गए हैं समाप्त हो गया है जब
  • डेडलॉक - कुछ कतारों असीम स्रोतों के लिए इंतजार कर रहे हैं जब (चर, डेटा आदि) पहले से ही इनमें से कुछ कतारों से अवरुद्ध है।

मुख्य कतार पर सिंक फ़ंक्शन को कभी भी कॉल न करें।
यदि आप मुख्य कतार पर सिंक फ़ंक्शन को कॉल करते हैं तो यह कतार को अवरुद्ध कर देगा और साथ ही कतार कार्य पूरा होने की प्रतीक्षा कर रही है लेकिन कार्य कभी समाप्त नहीं होगा क्योंकि यह भी शुरू नहीं हो पाएगा कतार पहले ही अवरुद्ध है। इसे डेडलॉक कहा जाता है।

सिंक का उपयोग कब करें? जब हमें कार्य पूरा होने तक प्रतीक्षा करने की आवश्यकता होती है। उदा जब हम यह सुनिश्चित कर रहे हैं कि कुछ फ़ंक्शन/विधि को डबल नहीं कहा जाता है। उदा हमारे पास सिंक्रनाइज़ेशन है और इसे पूरी तरह से समाप्त होने तक इसे डबल कॉल करने से रोकने की कोशिश कर रहा है। यहाँ 'इस चिंता के लिए कुछ कोड:
How to find out what caused error crash report on IOS device?

+0

मुझे सिंक कब कॉल करना चाहिए? –

+0

क्या आप कृपया उदाहरण के लिए उदाहरण प्रदान कर सकते हैं? –

+0

मैंने जवाब अपडेट किया है। कृपया, अद्यतन संस्करण को जांचने के लिए स्वतंत्र महसूस करें। – Alexander

9

जब आप async का उपयोग यह बुला कतार जब तक भेजा ब्लॉक निष्पादित होता है इंतजार किए बिना पर चलते हैं। इसके विपरीत sync कॉलिंग कतार बंद कर देगा और जब तक आप ब्लॉक में भेजे गए काम को पूरा नहीं कर लेते हैं। इसलिए sync डेडलॉक्स की ओर अग्रसर है। मुख्य पंक्ति से DispatchQueue.main.sync चलाने की कोशिश करें और क्योंकि बुला कतार जब तक भेजा ब्लॉक खत्म हो गया है इंतजार करेंगे एप्लिकेशन फ्रीज, लेकिन यह भी शुरू करने के लिए सक्षम नहीं होगा (क्योंकि कतार बंद कर दिया जाता है और प्रतीक्षा में)

जब उपयोग करने के लिए sync? जब आप कुछ एक अलग कतार पर किया के लिए प्रतीक्षा करने और उसके बाद ही जरूरत है अपने वर्तमान कतार पर काम जारी रखने के

सिंक का उपयोग करने का

उदाहरण: यदि आप क्रम में एक म्युटेक्स रूप sync इस्तेमाल कर सकते हैं

एक सीरियल कतार पर सुनिश्चित करने के लिए कि केवल एक धागा एक ही समय में कोड के संरक्षित टुकड़े को करने में सक्षम है।

+0

क्या आप कृपया उदाहरण के लिए उदाहरण प्रदान कर सकते हैं? –

+0

सिंक का उपयोग करने का उदाहरण? –

+0

हां। सिंक का उपयोग कैसे करें? –

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