मैं हाल ही में डेटा संरचना में एक स्किप सूची के रूप में जाना जाता हूं । ऐसा लगता है कि द्विआधारी खोज पेड़ के लिए बहुत समान व्यवहार है।
आप बाइनरी सर्च ट्री पर स्किप लिस्ट का उपयोग क्यों करना चाहेंगे?
मैं हाल ही में डेटा संरचना में एक स्किप सूची के रूप में जाना जाता हूं । ऐसा लगता है कि द्विआधारी खोज पेड़ के लिए बहुत समान व्यवहार है।
आप बाइनरी सर्च ट्री पर स्किप लिस्ट का उपयोग क्यों करना चाहेंगे?
जवाबों:
समवर्ती पहुँच / संशोधन के लिए छोड़ें सूचियाँ अधिक उत्तरदायी हैं। हर्ब सटर ने एक लेख लिखा समवर्ती वातावरण में डेटा संरचना के बारे में । इसकी अधिक जानकारी है।
बाइनरी सर्च ट्री का सबसे अधिक उपयोग किया जाने वाला कार्यान्वयन लाल-काला पेड़ है । समवर्ती समस्याएं तब आती हैं जब पेड़ को संशोधित किया जाता है, इसे अक्सर असंतुलन की आवश्यकता होती है। असंतुलन ऑपरेशन पेड़ के बड़े हिस्से को प्रभावित कर सकता है, जिसके लिए पेड़ के कई नोड्स पर म्यूटेक्स लॉक की आवश्यकता होगी। नोड को एक स्किप सूची में सम्मिलित करना कहीं अधिक स्थानीय है, केवल नोड्स को सीधे प्रभावित नोड से जोड़ा जाता है जिसे लॉक करने की आवश्यकता होती है।
जॉन हैरोप्स टिप्पणियों से अपडेट
मैंने फ्रेजर और हैरिस के नवीनतम पेपर समवर्ती प्रोग्रामिंग को ताले के बिना पढ़ा । यदि आप लॉक-फ्री डेटा संरचनाओं में रुचि रखते हैं तो वास्तव में अच्छा सामान। पेपर ट्रांसेक्शनल मेमोरी और एक सैद्धांतिक ऑपरेशन मल्टीवर्ड-तुलना और स्वैप एमसीएएस पर केंद्रित है । सॉफ्टवेयर में इन दोनों का अनुकरण किया गया है क्योंकि कोई भी हार्डवेयर अभी तक इनका समर्थन नहीं करता है। मैं काफी प्रभावित हूं कि वे सॉफ्टवेयर में MCAS का निर्माण करने में सक्षम थे।
मुझे विशेष रूप से सम्मोहक मेमोरी सामान नहीं मिला, क्योंकि इसके लिए कचरा उठाने वाले की आवश्यकता होती है। इसके अलावा सॉफ्टवेयर लेनदेन स्मृति प्रदर्शन के मुद्दों से ग्रस्त है। हालाँकि, मैं बहुत उत्साहित होता अगर हार्डवेयर ट्रांसेक्शनल मेमोरी कभी आम हो जाती। अंत में यह अभी भी अनुसंधान है और एक और दशक के लिए उत्पादन कोड के लिए उपयोग का नहीं होगा।
खंड 8.2 में वे कई समवर्ती वृक्ष कार्यान्वयन के प्रदर्शन की तुलना करते हैं। मैं उनके निष्कर्षों को संक्षेप में बताऊंगा। यह पीडीएफ डाउनलोड करने के लिए लायक है क्योंकि इसमें 50, 53, और 54 पेजों पर कुछ बहुत जानकारीपूर्ण रेखांकन हैं।
अद्यतन
यहां लॉक-फ्री पेड़ों के बारे में पेपर है: कैस का उपयोग करते हुए लॉक-फ्री रेड-ब्लैक ट्रीज़ ।
मैंने इसे गहराई से नहीं देखा है, लेकिन सतह पर यह ठोस लगता है।
सबसे पहले, आप किसी ऐसे रैंडमाइज्ड डेटा स्ट्रक्चर की तुलना नहीं कर सकते हैं जो आपको सबसे खराब स्थिति की गारंटी देता है।
एक स्किप सूची एक बेतरतीब ढंग से संतुलित बाइनरी सर्च ट्री (RBST) के बराबर है जिस तरह से डीन और जोन्स में अधिक विस्तार से बताया गया है "स्किप लिस्ट्स और बाइनरी सर्च ट्रीट्स के बीच द्वैत का अन्वेषण" ।
दूसरे तरीके से, आप नियतात्मक स्किप सूची भी ले सकते हैं जो सबसे खराब स्थिति प्रदर्शन की गारंटी देता है, सीएफ। मुनरो एट अल।
उपरोक्त कुछ दावों के विपरीत, आपके पास बाइनरी सर्च ट्री (BST) का कार्यान्वयन हो सकता है जो समवर्ती प्रोग्रामिंग में अच्छी तरह से काम करता है। संगामिति-केंद्रित BSTs के साथ एक संभावित समस्या यह है कि आप आसानी से संतुलन के बारे में गारंटी नहीं ले सकते क्योंकि आप एक लाल-काले (RB) पेड़ से होंगे। (लेकिन "मानक", यानी यादृच्छिक रूप से, छोड़ें सूचियां आपको ये गारंटी नहीं देती हैं।) हर समय संतुलन बनाए रखने और (और कार्यक्रम के लिए आसान) समवर्ती पहुंच के बीच एक व्यापार बंद है, इसलिए आराम से आरबी पेड़ आमतौर पर उपयोग किए जाते हैं जब अच्छी संगति वांछित है। विश्राम में वृक्ष को फिर से संतुलित नहीं करना शामिल है। कुछ हद तक दिनांक (1998) के सर्वेक्षण के लिए हेंके का '' द परफॉर्मेंस ऑफ़ कॉनकंट्रेक्ट रेड-ब्लैक ट्री एल्गोरिदम '' [ps.gz] देखें ।
इन पर हाल के सुधारों में से एक तथाकथित रंगीन पेड़ है (मूल रूप से आपके पास कुछ वजन है जैसे कि काला 1 होगा और लाल शून्य होगा, लेकिन आप बीच-बीच में मान भी लेते हैं)। और स्किप सूची के खिलाफ एक रंगीन पेड़ का किराया कैसे होता है? आइए देखें कि ब्राउन एट अल क्या है। "गैर-अवरुद्ध पेड़ों के लिए एक सामान्य तकनीक" (2014) कहना है:
128 थ्रेड्स के साथ, हमारे एल्गोरिथ्म जावा के गैर-ब्लॉकिंग स्किपिस्ट को 13% से 156%, ब्रोंसन एट अल के लॉक-आधारित एवीएल पेड़ को बेहतर बनाते हैं। 63% से 224%, और एक RBT जो 13 से 134 बार सॉफ़्टवेयर ट्रांसेक्शनल मेमोरी (STM) का उपयोग करता है
जोड़ने के लिए संपादित करें: पुघ की लॉक-आधारित स्किप सूची, जिसे फ्रेजर और हैरिस (2007) में "समवर्ती प्रोग्रामिंग विदाउट लॉक" के रूप में बेंच दिया गया था, अपने स्वयं के लॉक-फ्री संस्करण के करीब आने के रूप में (एक बिंदु ने यहां शीर्ष उत्तर में जोर दिया), अच्छा समवर्ती ऑपरेशन के लिए भी ट्वीक किया जाता है, सीएफ। पुग का "समवर्ती रखरखाव छोड़ें सूचियों" , हालांकि हल्के तरीके से। फिर भी एक नया / 2009 का पेपर "ए सिंपल ऑप्टिमिस्टिक स्किप-लिस्ट एल्गोरिथ्म"हेरलहि एट अल।, जो समवर्ती स्किप सूचियों के एक कथित रूप से सरल (पुघ की तुलना में) लॉक-आधारित कार्यान्वयन का प्रस्ताव करता है, पुघ की आलोचना की कि उनके लिए पर्याप्तता का सही प्रमाण प्रदान नहीं करने के लिए। इसे छोड़कर (शायद बहुत पांडित्यपूर्ण) क्वालम, हेरलीह एट अल। दिखाते हैं कि एक स्किप लिस्ट का उनका सरल लॉक-आधारित कार्यान्वयन वास्तव में JDK के लॉक-फ्री कार्यान्वयन के साथ-साथ बड़े पैमाने पर विफल हो जाता है, लेकिन केवल उच्च विवाद (50% आवेषण, 50% हटाता है और 0% लुकअप) के लिए ... फ्रेजर और हैरिस ने बिल्कुल भी परीक्षण नहीं किया; फ्रेजर और हैरिस ने केवल 75% लुक्स, 12.5% आवेषण और 12.5% डिलीट (~ 500 मिलियन एलिमेंट्स के साथ स्किप लिस्ट पर) का परीक्षण किया। Herlihy एट अल का सरल कार्यान्वयन। कम विवाद के मामले में जेडीके से लॉक-फ्री समाधान के करीब आता है जो उन्होंने परीक्षण किया (70% लुकअप, 20% आवेषण, 10% हटाता है); वे वास्तव में इस परिदृश्य के लिए लॉक-फ्री समाधान को हराते हैं जब उन्होंने अपनी स्किप की सूची को काफी बड़ा कर दिया, अर्थात 200K से 2M तत्वों तक जा रहे थे, ताकि किसी भी लॉक पर विवाद की संभावना नगण्य हो जाए। अच्छा होता अगर हर्लीह एट अल। पुघ के प्रमाण पर उनके हैंगअप पर कब्जा कर लिया था और उनके कार्यान्वयन का परीक्षण भी किया था, लेकिन अफसोस कि उन्होंने ऐसा नहीं किया।
EDIT2: मुझे सभी बेंचमार्क का एक (2015 प्रकाशित) मदरलोड मिला: ग्रामोली का "अधिक से अधिक आप कभी भी सिंक्रनाइज़ेशन के बारे में जानना चाहते थे। Synchrobench, समवर्ती स्थान पर तुल्यकालन के प्रभाव को मापना" : यहाँ इस प्रश्न के लिए प्रासंगिक एक अंश है।
"Algo.4" ब्राउन एट अल के पूर्ववर्ती (पुराने, 2011 संस्करण) है। (मुझे नहीं पता कि 2014 संस्करण कितना बेहतर या बदतर है)। "एल्गो .२६" हर्ली के ऊपर उल्लिखित है; जैसा कि आप देख सकते हैं कि यह अपडेट पर ट्रैश हो गया है, और मूल सीपीयू से सूर्य सीपीयू की तुलना में यहां उपयोग किए जाने वाले इंटेल सीपीयू पर बहुत बुरा है। "Algo.28" JDK से समवर्तीSkipListMap है; यह अन्य कैस-आधारित स्किप सूची क्रियान्वयन की तुलना में आशा के अनुरूप नहीं है। उच्च-विवाद के तहत विजेता "एलगो ।2" हैं जो एक लॉक-आधारित एल्गोरिथ्म (!!) है जिसे कर्ट एट अल द्वारा वर्णित किया गया है। में "एक विवाद के अनुकूल द्विआधारी खोजें ट्री" और "Algo.30" से "घूर्णन skiplist" है "multicores के लिए लघुगणक डेटा संरचनाओं" । "। बता दें कि ग्रामोली इन तीनों विजेता-एल्गोरिदम पेपरों का सह-लेखक है। "Algo.27" फ्रेजर की स्किप सूची का C ++ कार्यान्वयन है।
ग्रामोली का निष्कर्ष यह है कि कैस-आधारित समवर्ती पेड़ कार्यान्वयन को पेंच करना बहुत आसान है, क्योंकि यह एक समान स्किप सूची को पेंच करना है। और आंकड़ों के आधार पर, इससे असहमत होना मुश्किल है। इस तथ्य के लिए उनकी व्याख्या है:
एक पेड़ को डिजाइन करने में कठिनाई जो लॉक-फ्री उपजी है, कई संदर्भों को परमाणु रूप से संशोधित करने की कठिनाई से उपजी है। छोड़ें सूचियों में उत्तराधिकारी बिंदुओं के माध्यम से एक दूसरे से जुड़े टॉवर शामिल हैं और जिसमें प्रत्येक नोड इसके नीचे नोड को तुरंत इंगित करता है। उन्हें अक्सर पेड़ों के समान माना जाता है क्योंकि प्रत्येक नोड में उत्तराधिकारी टॉवर में एक उत्तराधिकारी होता है और इसके नीचे, हालांकि, एक बड़ा अंतर यह है कि डाउनवर्ड पॉइंटर आमतौर पर अपरिवर्तनीय होता है इसलिए एक नोड के परमाणु संशोधन को सरल करता है। यह अंतर संभवतः यही कारण है कि स्किप को बेहतर प्रदर्शन के तहत आउटपरफॉर्म पेड़ों को सूचीबद्ध करता है जैसा कि चित्र [ऊपर] में देखा गया है।
ब्राउन एट अल के हालिया काम में इस कठिनाई को ओवरराइड करना एक महत्वपूर्ण चिंता थी। मल्टी-रिकॉर्ड एलएल / एससी कंपाउंड "प्रिमिटिव्स" के निर्माण के लिए उनके पास एक अलग (2013) पेपर "नॉन-ब्लॉकिंग डेटा स्ट्रक्चर्स के लिए व्यावहारिक प्रिमिटिव्स " है, जिसे वे एलएलएक्स / एससीएक्स कहते हैं, खुद (मशीन-लेवल) कैस का उपयोग करके लागू किया गया। ब्राउन एट अल। 2014 में (लेकिन उनके 2011 में नहीं) समवर्ती पेड़ कार्यान्वयन में इस एलएलएक्स / एससीएक्स बिल्डिंग ब्लॉक का इस्तेमाल किया।
मुझे लगता है कि शायद यहाँ "नो हॉट स्पॉट" / कंटेन्शन-फ्रेंडली (सीएफ) सूची के मूलभूत विचारों को संक्षेप में प्रस्तुत करने लायक है। यह आराम से आरबी पेड़ों (और इसी तरह के समसामयिक डेटा संरचनाओं) से एक आवश्यक विचार जोड़ता है: टावरों को अब सम्मिलन पर तुरंत नहीं बनाया जाता है, लेकिन कम विवाद होने तक देरी हो जाती है। इसके विपरीत, एक लंबा टॉवर को हटाने से कई सामग्री बन सकती हैं; यह पुघ के 1990 के समवर्ती स्किप-लिस्ट पेपर के रूप में बहुत पीछे देखा गया था, यही कारण है कि पुघ ने विलोपन पर सूचक रिवर्सल को पेश किया (स्किप सूचियों पर विकिपीडिया का पृष्ठ अभी भी इस दिन का उल्लेख नहीं करता है, अफसोस)। सीएफ स्किप लिस्ट इसे और आगे ले जाती है और एक ऊंचे टॉवर के ऊपरी स्तरों को हटाने में देरी करती है। सीएफ स्किप सूचियों में दोनों प्रकार के विलंबित संचालन एक (कैस आधारित) अलग-अलग कचरा-संग्राहक-जैसे धागे द्वारा किए जाते हैं, जिसे इसके लेखक "थ्रेडिंग थ्रेड" कहते हैं।
Synchrobench कोड (परीक्षण किए गए सभी एल्गोरिदम सहित) https://github.com/gramoli/synchrobench पर उपलब्ध है । नवीनतम ब्राउन एट अल। कार्यान्वयन (ऊपर शामिल नहीं) http://www.cs.toronto.edu/~tabrown/chromatic/ConcurrentChromaticTreeMap.java पर उपलब्ध है क्या किसी के पास 32+ कोर मशीन उपलब्ध है? J / K मेरा कहना है कि आप इन्हें स्वयं चला सकते हैं।
इसके अलावा, दिए गए उत्तरों के अलावा (कार्यान्वयन की आसानी एक संतुलित पेड़ के तुलनीय प्रदर्शन के साथ संयुक्त)। मुझे लगता है कि इन-ऑर्डर ट्रैवर्सल (फॉरवर्ड और बैकवर्ड) को लागू करना कहीं अधिक सरल है क्योंकि स्किप-लिस्ट प्रभावी रूप से इसके कार्यान्वयन के अंदर एक लिंक की गई सूची है।
def iterate(node): for child in iterate(left(node)): yield child; yield node; for child in iterate(right(node)): yield child;
:? =)। गैर-स्थानीय नियंत्रण iz awesom .. @Jon: CPS में लिखना एक दर्द है, लेकिन शायद आपका मतलब निरंतरता से है? जनरेटर मूल रूप से अजगर के लिए निरंतरता का एक विशेष मामला है।
व्यवहार में मैंने पाया है कि मेरी परियोजनाओं पर बी-ट्री के प्रदर्शन ने स्किप-लिस्ट से बेहतर काम किया है। छोड़ें सूचियों को समझना आसान लगता है लेकिन बी-ट्री को लागू करना उतना कठिन नहीं है ।
एक फायदा जो मुझे पता है वह यह है कि कुछ चतुर लोगों ने काम किया है कि लॉक-फ्री समवर्ती स्किप सूची को कैसे लागू किया जाए जो केवल परमाणु संचालन का उपयोग करता है। उदाहरण के लिए, Java 6 में समवर्तीSkipListMap वर्ग शामिल है, और यदि आप पागल हैं तो आप इसे स्रोत कोड पढ़ सकते हैं।
लेकिन समवर्ती बी-ट्री संस्करण को लिखना बहुत कठिन नहीं है - मैंने इसे किसी और के द्वारा देखा है - यदि आप पहले से ही "बस के मामले में" नोड को विभाजित करते हैं और विलय करते हैं जैसा कि आप पेड़ से नीचे चलते हैं तो आपको नहीं करना पड़ेगा गतिरोध के बारे में चिंता करना और केवल एक समय में पेड़ के दो स्तरों पर ताला लगाने की आवश्यकता है। सिंक्रनाइज़ेशन ओवरहेड थोड़ा अधिक होगा, लेकिन बी-पेड़ शायद तेज है।
आपके द्वारा उद्धृत विकिपीडिया लेख से :
Θ (एन) संचालन, जो हमें आरोही क्रम में प्रत्येक नोड पर जाने के लिए मजबूर करते हैं (जैसे पूरी सूची को प्रिंट करना) एक इष्टतम तरीके से स्किप-लिस्ट के स्तर संरचना के पीछे-पीछे के दृश्यों को निष्पादित करने का अवसर प्रदान करते हैं, खोज सूची को O (लॉग एन) खोज समय पर लाना। [...] एक स्किप सूची, जिस पर हमने हाल ही में [कोई भी] n (n) संचालन नहीं किया है, एक ही पूर्ण सबसे खराब स्थिति के प्रदर्शन की गारंटी नहीं देता है क्योंकि अधिक पारंपरिक संतुलित पेड़ डेटा संरचनाएं हैं , क्योंकि यह हमेशा संभव है (हालांकि बहुत कम संभावना के साथ) कि स्किप-लिस्ट का निर्माण करने के लिए उपयोग किए जाने वाले सिक्का-फ्लिप एक बुरी तरह से संतुलित संरचना का उत्पादन करेंगे
संपादित करें: तो यह एक व्यापार बंद है: छोड़ें सूचियाँ जोखिम पर कम स्मृति का उपयोग करती हैं जो कि असंतुलित पेड़ में पतित हो सकती हैं।
सूचियों का उपयोग करके सूची छोड़ दी जाती है।
लॉक फ्री सॉल्यूशंस एकल और दोगुनी लिंक्ड लिस्ट के लिए मौजूद हैं - लेकिन कोई भी लॉक फ्री सॉल्यूशन नहीं है जो सीधे किसी O (logn) डेटा संरचना के लिए केवल CAS का उपयोग करते हैं।
हालाँकि आप स्किप सूची बनाने के लिए CAS आधारित सूचियों का उपयोग कर सकते हैं।
(ध्यान दें कि MCAS, जो CAS का उपयोग करके बनाया गया है, मनमाने ढंग से डेटा संरचनाओं की अनुमति देता है और MCAS का उपयोग करके अवधारणा का प्रमाण लाल-काला पेड़ बनाया गया है)।
तो, अजीब के रूप में वे कर रहे हैं, वे बहुत उपयोगी हो :-)
स्किप लिस्ट में लॉक स्ट्रिपिंग का फायदा है। लेकिन, रनटाइम समय इस बात पर निर्भर करता है कि नए नोड का स्तर कैसे तय किया जाता है। आमतौर पर यह रैंडम () का उपयोग करके किया जाता है। 56000 शब्दों के एक शब्दकोष में, स्किप सूची में एक छीज पेड़ की तुलना में अधिक समय लगा और पेड़ को हैश तालिका की तुलना में अधिक समय लगा। पहले दो हैश टेबल के रनटाइम से मेल नहीं खा सके। साथ ही, हैश टेबल की सरणी को समवर्ती तरीके से लॉक किया जा सकता है।
संदर्भ की स्थानीयता की आवश्यकता होने पर सूची और समान आदेशित सूचियों का उपयोग किया जाता है। पूर्व के लिए: एक आवेदन में एक तारीख से पहले और उससे पहले की उड़ानें खोजना।
एक द्विध्रुवीय बाइनरी खोज स्प्ले ट्री महान और अधिक बार उपयोग किया जाता है।