2012-12-19 33 views
8

मैं संदर्भ काउंटर के लिए std::atomic एस का उपयोग कर एक सूचक/कमजोर सूचक तंत्र लागू कर रहा हूं (जैसे this)। एक मजबूत एक करने के लिए एक कमजोर सूचक परिवर्तित करने के लिए मैं atomically कोसी ++ वृद्धि एसडी :: atomic_int अगर nonzero

  • जांच करता है, तो मजबूत संदर्भ काउंटर अशून्य
  • यदि ऐसा है तो है की जरूरत है, को बढ़ा देते यह
  • बताती है कि कुछ बदल गया है या नहीं।

क्या std::atomic_int का उपयोग करके ऐसा करने का कोई तरीका है? मुझे लगता है कि इसे compare_exchange में से एक का उपयोग करना संभव है, लेकिन मैं इसे समझ नहीं सकता।

+3

'std :: shared_ptr' परमाणु संदर्भ काउंटर का उपयोग करता है, तुम्हें पता है। आप हमेशा स्रोत की जांच कर सकते हैं। – Pubby

+1

"पता है कि कुछ बदल गया है" भाग का क्या अर्थ है? – inf

+0

चाहे यह nonzero था == चाहे वह वृद्धि हुई हो। –

उत्तर

3

परिभाषा std::atomic<int> ref_count;

int previous = ref_count.load(); 
for (;;) 
{ 
    if (previous == 0) 
     break; 
    if (ref_count.compare_exchange_weak(previous, previous + 1)) 
     break; 
} 

previous को देखते हुए पिछले मान का आयोजन करेगा। ध्यान दें कि compare_exchange_weak पिछली बार अपडेट हो जाएगा यदि यह विफल हो जाता है।

+0

refopount.load() लूप के लिए नहीं होना चाहिए? मैं गलत हो सकता हूं, क्योंकि मुझे परमाणु ओप के रास्ते में वास्तव में कठिन समय लगता है। :) – NoSenseEtAl

+2

@NoSenseEtAl 'compar_exchange_weak' संदर्भ द्वारा 'पिछला' लेता है और इसे अपडेट करता है, इसलिए कोई अन्य' ref_count.load() 'करने की आवश्यकता नहीं है। – ymett

1

यह करना चाहिए:

bool increment_if_non_zero(std::atomic<int>& i) { 
    int expected = i.load(); 
    int to_be_loaded = expected; 

    do { 
     if(expected == 0) { 
      to_be_loaded = expected; 
     } 
     else { 
      to_be_loaded = expected + 1; 
     } 
    } while(!i.compare_exchange_weak(expected, to_be_loaded)); 

    return expected; 
} 
+0

तुलनात्मक रूप से आगे बढ़ने के लिए अनावश्यक लगता है यदि आपने पहले ही मान को बदलने का फैसला नहीं किया है। – ymett

+0

@ymett मैं आपसे सहमत हूं लेकिन मैं किसी भी तरह से अनिश्चित हूं, क्योंकि मैं अपने निर्णय को आधारभूत करता हूं कि 'i' के दो अलग-अलग राज्यों में वृद्धि या नहीं। – inf

+0

आपको केवल एक बार फैसला करने की आवश्यकता है। एक बार निर्णय लेने के बाद ('if' में) आप समाप्त हो गए हैं। – ymett

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

  • कोई संबंधित समस्या नहीं^_^