Skip to content

Instantly share code, notes, and snippets.

@telescreen
Created February 6, 2013 06:22
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save telescreen/4720747 to your computer and use it in GitHub Desktop.
Save telescreen/4720747 to your computer and use it in GitHub Desktop.
Reference counted string (example of handle-body idiom)
#include <iostream>
class StringRep {
friend class String;
private:
StringRep() { *(rep = new char[1]) = '\0'; }
~StringRep() { delete[] rep; }
StringRep(const StringRep& s) { ::strcpy((rep = new char[::strlen(s.rep)+1]), s.rep); }
StringRep& operator=(const StringRep& s) {
if (rep != s.rep) {
delete[] rep;
::strcpy((rep = new char[::strlen(s.rep)+1]), s.rep);
}
return *this;
}
StringRep(const char* s) { ::strcpy((rep = new char[::strlen(s) + 1]), s); }
int length() const { return ::strlen(rep); };
StringRep operator+(const StringRep& s) const;
private:
char *rep;
int count;
};
StringRep StringRep::operator+(const StringRep& s) const {
char *tmp = new char[length() + s.length() + 1];
::strcpy(tmp, rep);
::strcat(tmp, s.rep);
StringRep tmpret(tmp);
delete[] tmp;
return tmpret;
}
class String {
public:
String() { rep = new StringRep; rep->count = 1; }
String(const String& s) { rep = s.rep; rep->count++; }
String& operator=(const String& s) {
s.rep->count++;
if (--rep->count <= 0) delete rep;
rep = s.rep;
return *this;
}
~String() { if (--rep->count <= 0) delete rep; }
String(const char *s) { rep = new StringRep(s); rep->count = 1;}
int length() const { return rep->length(); }
String operator+(const String& s) {
StringRep t = *rep + *s.rep;
String retval(t.rep);
return retval;
}
const char *c_str() const {
return rep->rep;
}
// for debug
int count() const { return rep->count; }
private:
StringRep *rep;
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment