2014-07-18 8 views
6

सीडी + स्ट्रिंग में आंतरिक रूप से std :: स्ट्रिंग का प्रतिनिधित्व कैसे किया जाता है (libstdC++)?सी ++ 11 आंतरिक std :: स्ट्रिंग प्रस्तुति (libstdC++)

कार्यान्वयन के अंदर खुदाई करते समय, मैंने पाया:

/* A string looks like this: 
* 
*          [_Rep] 
*          _M_length 
* [basic_string<char_type>]   _M_capacity 
* _M_dataplus       _M_refcount 
* _M_p ---------------->    unnamed array of char_type 
* 
* Where the _M_p points to the first character in the string, and 
* you cast it to a pointer-to-_Rep and subtract 1 to get a 
* pointer to the header. 
* 
* This approach has the enormous advantage that a string object 
* requires only one allocation. All the ugliness is confined 
* within a single %pair of inline functions, which each compile to 
* a single @a add instruction: _Rep::_M_data(), and 
* string::_M_rep(); and the allocation function which gets a 
* block of raw bytes and with room enough and constructs a _Rep 
* object at the front. 
* 
* The reason you want _M_data pointing to the character %array and 
* not the _Rep is so that the debugger can see the string 
* contents. (Probably we should add a non-inline member to get 
* the _Rep for the debugger to use, so users can check the actual 
* string length.) 
* 
* Note that the _Rep object is a POD so that you can have a 
* static <em>empty string</em> _Rep object already @a constructed before 
* static constructors have run. The reference-count encoding is 
* chosen so that a 0 indicates one reference, so you never try to 
* destroy the empty-string _Rep object. 
*/ 
    // _Rep: string representation 
    // Invariants: 
    // 1. String really contains _M_length + 1 characters: due to 21.3.4 
    //  must be kept null-terminated. 
    // 2. _M_capacity >= _M_length 
    //  Allocated memory is always (_M_capacity + 1) * sizeof(_CharT). 
    // 3. _M_refcount has three states: 
    //  -1: leaked, one reference, no ref-copies allowed, non-const. 
    //  0: one reference, non-const. 
    //  n>0: n + 1 references, operations require a lock, const. 
    // 4. All fields==0 is an empty string, given the extra storage 
    //  beyond-the-end for a null terminator; thus, the shared 
    //  empty string representation needs no constructor. 
    struct _Rep_base 
    { 
    size_type  _M_length; 
    size_type  _M_capacity; 
    _Atomic_word _M_refcount; 
    }; 

मैं उन टिप्पणियों समझ में नहीं आता बहुत ज्यादा:

  • एसटीडी है :: स्ट्रिंग रेफरी गिना? कैसे? मेरा मतलब है _M_refcount एक सूचक नहीं है, इसलिए यदि एक स्ट्रिंग इसे संशोधित करती है, तो दूसरा इसे नहीं देख सकता है।
  • बफर हेडर के तुरंत बाद झूठ बोलता है? अगर ऐसा है तो मैं वास्तव में क्यों नहीं समझता।
+5

सी ++ 11 संदर्भित 'std :: string' गैर-अनुपालन के कार्यान्वयन की गणना की गई। आप शायद libstdC++ कार्यान्वयन को देख रहे हैं जो अभी भी रेफ गिनती कार्यान्वयन का उपयोग करता है। – Praetorian

+0

हां, आप सही हैं। – Borzh

+0

@ बोर्ज़ - अगर आप जानते हैं कि खुद को उत्तर दें तो प्रेटोरियन का जवाब सही है ... – NirMH

उत्तर

0

जीसीसी सी ++ 11 मानक का पालन करने के लिए refcounted स्ट्रिंग से दूर चला गया, लेकिन ध्यान दें कि यह संभव है कि आपका प्रोग्राम एबीआई संगतता कार्यान्वयन के हिस्से के रूप में इसका उपयोग करेगा।

यह कैसे refcounted है

std::string एक _Rep_Base सदस्य लेकिन _Rep_Base

से इनहेरिट _Rep साथ _Rep के लिए सूचक यह है क्या यहाँ से समझाया गया है नहीं है:

* Where the _M_p points to the first character in the string, and 
* you cast it to a pointer-to-_Rep and subtract 1 to get a 
* pointer to the header. 

बफर शीर्षलेख के बाद निहित है ...

हाँ, लेकिन _Rep ऑब्जेक्ट के शीर्षलेख के बाद, और आपकी स्ट्रिंग में केवल एक पॉइंटर है।

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