2012-06-13 14 views
6

का उपयोग करता है I ArrayBlockingQueue और LinkedBlockingQueue के स्रोत कोड से गुजर रहा था। लिंक्डब्लॉकिंग क्यूयू में क्रमशः सम्मिलन और हटाने के लिए एक पुल लॉक और टेक लॉक है लेकिन ऐरेब्लॉकिंग क्यूयू केवल 1 लॉक का उपयोग करता है। मेरा मानना ​​है कि LinkedBlockingQueue को Simple, Fast, and Practical Non-Blocking and Blocking Concurrent Queue Algorithms में वर्णित डिज़ाइन के आधार पर कार्यान्वित किया गया था। इस पेपर में, वे उल्लेख करते हैं कि वे एक डमी नोड रखते हैं ताकि एनक्यूवर को कभी भी सिर तक पहुंच न हो और डेक्यूवर को पूंछ तक पहुंचने की ज़रूरत न हो जो डेडलॉक परिदृश्यों से बचा जाए। मैं सोच रहा था कि क्यों ArrayBlockingQueue एक ही विचार उधार नहीं लेता है और इसके बजाय 2 ताले का उपयोग करता है।ArrayBlockingQueue सम्मिलन और हटाने के लिए एक एकल लॉक का उपयोग करता है लेकिन LinkedBlockingQueue 2 अलग ताले

उत्तर

8

ऐरेब्लॉकिंगक्यूयू को ओवरराइटिंग प्रविष्टियों से बचना है ताकि इसे पता चल सके कि शुरुआत और अंत कहां है। एक LinkedBlockQueue को यह जानने की आवश्यकता नहीं है क्योंकि यह कतार में नोड्स को साफ करने के बारे में जीसी की चिंता करने देता है।

+0

सही दिशा में मुझे इंगित करने के लिए धन्यवाद। मैं फिर से कोड के माध्यम से चला गया और पाया कि ArrayBlockingQueue और LinkedBlockingQueue दोनों चर "गिनती" बनाए रखते हैं। यह LinkedBlockingQueue में एटमिकइंटर है (डालकर हटाए गए और हटाए गए अनुसार) और ArrayBlockingQueue में एक int। और मुझे लगता है कि यह ArrayBlockingQueue में एक परमाणु इंटेगर नहीं हो सकता है क्योंकि इसे चारों ओर लपेटना है। – user1168577

+0

@ पीटर यह वास्तव में बहुत अच्छा होगा अगर आप समझा सकते हैं कि क्यों दो लॉक कतार एल्गोरिदम काम नहीं करेगा। एबीक्यू के मामले में गणना बहुत अच्छी तरह से परमाणु इंटेगर हो सकती है, और ओवरराइडिंग को बहुत अच्छी तरह से गिनती == max_capacity से बचा जा सकता है। – veritas

+0

@veritas क्या आप समझा सकते हैं कि मैं दो लॉक कतार एल्गोरिदम का उल्लेख कहां से कहूं? मैंने यह दो साल पहले लिखा था और मैं नहीं ढूंढ सकता कि आप किस बारे में बात कर रहे हैं। –

7

मैं सोच रहा था कि क्यों ArrayBlockingQueue एक ही विचार उधार नहीं लेता है और इसके बजाय 2 ताले का उपयोग करता है।

क्योंकि ArrayBlockingQueue कतार वस्तुओं को पकड़ने के लिए एक बहुत ही सरल डेटा संरचना का उपयोग करता है।

ArrayBlockingQueue अपने डेटा को एक private final E[] items; सरणी में संग्रहीत करता है। इस थ्रेड स्टोरेज स्पेस से निपटने के लिए कई धागे के लिए, या तो अगर जोड़ना या हटाना, तो उन्हें एक ही लॉक का उपयोग करना होगा। यह केवल स्मृति बाधा के कारण नहीं बल्कि म्यूटेक्स सुरक्षा के कारण है क्योंकि वे एक ही सरणी को संशोधित कर रहे हैं।

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

0

मुझे लगता है कि एबीक्यू के लिए एलबीक्यू के समान विचार उधार लेना संभव है। कृपया मेरे कोड http://pastebin.com/ZD1uFy7S और इसी तरह के प्रश्न का संदर्भ लें जो मैंने SO ArrayBlockingQueue: concurrent put and take पर पूछा था।

मुख्य कारण यह है कि उन्होंने इसका उपयोग नहीं किया, मुख्य रूप से कार्यान्वयन की जटिलता के कारण विशेष रूप से इटरेटर और जटिलता और प्रदर्शन लाभ के बीच व्यापार बंद करना आकर्षक नहीं था।

अधिक संदर्भ के लिए कृपया http://jsr166-concurrency.10961.n7.nabble.com/ArrayBlockingQueue-concurrent-put-and-take-tc1306.html पर एक नज़र डालें।

1

एलबीक्यू में 2 ताले का उपयोग सिर तक पहुंच प्रतिबंधित करने और समवर्ती रूप से लॉक करने के लिए किया जाता है। हेड लॉक दो तत्वों को समवर्ती रूप से हटाए जाने से रोकता है और पूंछ ताला दो तत्वों को कतार में समवर्ती रूप से जोड़ा जाने से रोकता है। दोनों लॉक एक साथ दौड़ को रोकते हैं।