"Reprint" C + + Application reference counting technology

Source: Internet
Author: User

Original posts: http://www.cnblogs.com/chain2012/archive/2010/11/12/1875578.html

Because the kernel objects of Windows also use reference counts, it is not useless to understand them a little.

Reference counting allows multiple objects to share a single piece of data, and removes the burden of tracking control, allowing the object to manage itself, which can be deleted automatically when not in use, or as a simple garbage collection mechanism.

On the other hand, if there are more than n identical objects: 0=0=0=0=...=0=0 The practice is bloated and boring, so a good practice is to let the object share this data. You can save memory and increase efficiency to make the program less burdensome, without having to construct and deconstruct copies of the value object.

1 String A, B, C, D, E;
2 a=b=c=d=e= "Hello";
1 string& string::operator= (const String &RHS)
2 {
3 if (DATA==&RHS) return *this; Prevent self-assignment
4 Delete [] data;
5 data = new Char[strlen (rhs.data) +1)];
6 strcpy (data, rhs.data);
7 return *this;
8}

As shown in the figure, that is:

When a is given an additional value, a= "World"; At this time cannot delete this hello, should still exist bcde,4 objects in the sharing of this data; In addition, when only 1 object x is in use of this Hello, and X has exceeded its lifetime, no other object points to this Hello, We need to remove this hello to ensure that no resource leaks occur. This means that when a reference count is introduced, the diagram will change to this:

    • Implementing reference counting

Should be a count value for each string value, not a reference count for the string object. Next, create a new nested class StringValue to hold the count and its tracked values.

String.h
1 #include <string>

3 class String {
4 Public:
5 String (const char *initvalue= "");
6 string& string::operator= (const String &RHS);

8 Private:
9 //StringValue's main purpose is to provide a space for a particular value and a total
The number of objects that have this value linked together
struct StringValue //nested class, reference count
12
int refcount;//Count value
*data Char;
stringvalue (const char* initvalue);
~stringvalue ();
n};
StringValue *value;
19};
String.cpp
1 #include "String.h"

3 String::stringvalue::stringvalue (const char* InitValue)
4 : RefCount (1)
5 {
6 data = new Char[strlen (initvalue) +1];
7 strcpy (data, initvalue);
8}

Ten String::stringvalue::~stringvalue ()
11 {
Delete [] data;
13}

string::string (const char *initvalue)
: Value (New StringValue (InitValue))
17 {

19}

And doing this usually creates a problem,

String S1 ("more effective C + +");

String S2 ("more effective C + +");

will become such a data structure:

Find a way to improve:

simple implementation of control replicas
1 list<string> string::stringvalue::independobj; Standalone objects
2 String::stringvalue::stringvalue (const char* InitValue)
3 : RefCount (1)
4 {
5 typedef list<string>::iterator LSP;
6 LSP p = Find (Independobj.begin (), Independobj.end (), String (InitValue));
7 if (p==independobj.end () | | | Independobj.empty ())
8 {//No objects found, new
9 data = new Char[strlen (initvalue) +1];
Ten strcpy (data, initvalue);
independobj.push_back (string data);
-- }
All Else
{
/ /do something ...
+ }
17}

Next look at the copy constructor of the string class





When you construct 2 objects like this:

String S1 ("more effective C + +");

String S2 (S1);

The resulting data structure is very inexpensive, eliminating the need for new objects to be constructed (without having to allocate new memory and copying the contents into this memory) and after the destruction (not having to release that memory), just to make the Count +1 and copy the next pointer

After copying the constructor, look at the destructor

String::~string ()
{
if (--value->refcount = = 0)
{
Delete value;
}
}

That is, when the referenced object has other shared objects, only the count-1 is counted-and when there are no other shared objects, the reference object is completely destroyed. Then, the overloaded assignment operator, a little bit more complex

string& string::operator= (const String &RHS)
{
if (value = = rhs.value)//assignment is its own
return *this; I don't do anything.
if (--value->refcount = = 0) //If only the current object is sharing that data
Delete value; is removed because a new reference will be given. If not, only the count-1
Value = Rhs.value; Assignment operation
++value->refcount; Counter +1
return *this;
}
    • Write-time copy

The subscript operation of the const version is only read-only and does not modify the referenced object

Const char& string::operator[] (int index) const  //CONST version
{
Subscript overflow Check Required
Return value->data[index];
}

A non-const version of the subscript operation needs to be considered because the C + + compiler cannot tell us whether the non-const operator[] will be used for read or write operations. So we conservatively believe that all operations are "written".

char& string::operator[] (int index)  //non-const version
{
if (value.refcount>1)//If more than one reference object
{
--value.refcount; The count minus one is equivalent to removing the reference.
Value = new StringValue (value->data); Re-apply for a new copy
}
Return value->data[index];
}

The idea is that "a value shared with other objects will not have its own copy until the write operation." That is, a special case of the lazy principle.

    • pointers, references, and write-time copies

These applications can be met in most cases, but the only case is tricky, such as

String S1 ("more effective C + +");

char* p=&s1;

String s2 = S1;

The copy constructor lets S2 and S1 share this object, when the data structure is

If you write down this sentence: p[1]= ' X '; The contents of S1 and S2 will be modified at the same time! The copy constructor of String cannot detect the existence of a pointer to stringvalue that S1 has. One way to solve this problem is to add a flag to each stringvalue that indicates whether the object can be shared. is set to False after the initial ture state, and after the non-const operator[] is called, and is permanently placed in the false state.

append string for shared flag bit
    • Base class with reference count

Reference counting applies not only to string classes, but to classes where multiple objects share the same value.

Building a base class (Rcobject), any class that requires a reference count must inherit from this class. The reference count feature is encapsulated by the Rcobject class.

RCObject.hRCObject.cpp
    • Automatic reference counting processing

The Rcobject class gives us a place to store reference counts, and provides member functions for us to manipulate reference counts, but the actions that call these functions must also be manually added to other classes. You still need to call StringValue's addreference and removereference functions in the copy constructor and assignment operation functions of String. It's awkward.

StringValue *value; You must manipulate the RefCount field of the StringValue object. Is it possible for the pointer itself to detect a copy, assignment, or destructor of such an event, and for a row modified operation? The answer is in the negative. The alternative is to use smart pointers.

Analysis

When I started looking at the functional treap, I saw ...

Does the function treap consume so much memory? Also use reference counting.

Indicates that only memory pools are used.

By the way, I enclose an online functional treap template ...

Http://ideone.com/kbSjPp

"Reprint" C + + Application reference counting technology

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.