    <rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:admin="http://webns.net/mvcb/" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:content="http://purl.org/rss/1.0/modules/content/">
     <channel>
        <title>ACCU  :: counted_ptr&lt;type&gt; revisited</title>
        <link>https://members.accu.org/index.php/articles/575</link>
        <description>Professionalism in Programming</description>
        <dc:language>en-us</dc:language> 
        <dc:creator>Administrator</dc:creator> 
        <admin:generatorAgent rdf:resource="http://www.xaraya.org" /> 
        <admin:errorReportsTo rdf:resource="mailto:webeditor@accu.org" />
       <sy:updatePeriod>hourly</sy:updatePeriod>
       <sy:updateFrequency>1</sy:updateFrequency>
       <docs>http://backend.userland.com/rss</docs>




<div class="xar-mod-head"><span class="xar-mod-title">Programming Topics + Overload Journal #29 - Dec 1998</span></div>

<table border="0" cellpadding="1" cellspacing="0">
    <tbody>
    <tr>
        <td valign="top">
            Browse in :
       </td>
       <td valign="top">

                                            <a href="https://members.accu.org/index.php/articles/">All</a>

                     &gt;                         <a href="https://members.accu.org/index.php/articles/c13/">Topics</a>

                     &gt;                         <a href="https://members.accu.org/index.php/articles/c65/">Programming</a>
<br />

                                            <a href="https://members.accu.org/index.php/articles/">All</a>

                     &gt;                         <a href="https://members.accu.org/index.php/articles/c76/">Journals</a>

                     &gt;                         <a href="https://members.accu.org/index.php/articles/c78/">Overload</a>

                     &gt;                         <a href="https://members.accu.org/index.php/articles/c199/">29</a>
<br />

                                            <a href="https://members.accu.org/index.php/articles/c65-199/">Any of these categories</a>

                    -                        <a href="https://members.accu.org/index.php/articles/c65+199/">All of these categories</a>
<br />
</td>
   </tr>
   </tbody>
</table>




<div class="xar-error">
   <p>
 <strong>Note:</strong> when you create a new publication type,
the articles module will automatically use the templates
<em>user-display-[publicationtype].xt</em>
and <em>user-summary-[publicationtype].xt</em>.
If those templates do not exist when you try to preview or display a new article,
you'll get this warning :-)  Please place your own templates in themes/<em>yourtheme</em>/modules/articles . The templates will get the extension .xt there. </p>
</div>
<div class="xar-norm xar-standard-box-padding">
   <h1><strong>Title:</strong>&nbsp;counted_ptr&lt;type&gt; revisited</h1>
<p><strong>Author:</strong>&nbsp;</p>
<p>
<strong>Date:</strong> 27 December 1999 17:23:23 +00:00 or Mon, 27 December 1999 17:23:23 +00:00</p>
<p><strong>Summary:</strong>&nbsp;</p>
<p><strong>Body:</strong>&nbsp;<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e18" id="d0e18"></a></h2>
</div>
<p>In Overload 25 I looked at <tt class=
"classname">counted_ptr&lt;type&gt;</tt>. Specifically I used it to
implement a <tt class="classname">string</tt> class, which was able
to share common state.</p>
<pre class="programlisting">
namespace accu
{
  class string
  {
  public:
    string(const char *literal = &quot;&quot;);
    char &amp;operator[](size_t index);
    ...
  private:
    struct body;
    counted_ptr&lt;body&gt; ptr;
  };
}
...
</pre>
<p>Towards the end of that article I hinted at problem with
<tt class="classname">counted_ptr&lt;type&gt;</tt> that remained
unresolved&hellip;</p>
<pre class="programlisting">
using accu::string;

string theory(&quot;hello&quot;);
string vest(theory);
theory[0] = 'J';
cout &lt;&lt; vest &lt;&lt; endl; // must print &quot;hello&quot; and not &quot;jello&quot;
</pre>
<p>The basic problem is that sometimes you have to stop sharing
data. What should happen when you attempt to change the shared
data? There is no right or wrong answer. It depends on the context.
It depends why you are sharing. You have to decide whether the
sharing is an externally visible feature or an internal
implementation detail. For my fledgling string class I was sharing
state because it gave lazy evaluation. It saved me having to make a
deep copy of the state during a copy construction or a copy
assignment. In other words it was an internal implementation
detail.</p>
</div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e39" id="d0e39"></a>const
overloading</h2>
</div>
<p>There are a number of ways to solve this problem. In case you
haven't got the previous article (it was a while ago) and because
it's not the focus of this article I'll unwrap the counted pointer.
Ok, to get things started the first thing to notice is that we can
make use of const overloading:</p>
<pre class="programlisting">
namespace accu
{
  class string
  {
  public:
    string(const char *literal = &quot;&quot;);
    ...  
          char &amp;operator[](size_t index);
    const char &amp;operator[](size_t index) const;
     ...
  private:
    char   *text;
    size_t *count;
  };
}
</pre>
<p>An alternative version of the const array-subscript operator
could return a plain char (by value). There is not much to choose
between the two, but you might consider using the one that gives
the clearest (least obscure) error message when misused (if they
differ). The implementation of the const version is simple and does
not need to make a deep copy since the data cannot change. The
implementation of the non-const version is not so simple since it
may need to make a deep copy.</p>
<pre class="programlisting">
namespace accu // string
{
  string::string(const char *literal)
    : text(new char[strlen(literal)+1],
     count(new size_t(1))
  {
    strcpy(text, literal);
  }

  char &amp;string::operator[](size_t index)
  {
     bounds_check(index);
     unshare_state();
      return text[index];
  }
}
</pre>
<p>And <tt class="methodname">string::unshare_state()</tt> will
need to ensure its state is not shared by any other string objects.
There are a number of details to remember when writing <tt class=
"methodname">unshare_state</tt>. Firstly there is no need to make a
deep copy if the state is already unshared, in other words if the
reference count is one. Secondly, if a deep copy is required then a
new reference count will also need to be allocated. That's two
allocations inside a single function. Ensuring such a function is
exception safe can be tricky...</p>
<pre class="programlisting">
namespace accu
{
 void string::unshare_state()
 {
  if (*count != 1)
  {
   auto_ptr&lt;size_t&gt; new_count(new size_t(1));
   char *new_text = new char[strlen(text)+1];
   strcpy(new_text, text);
    --*count;
    count = new_count.release();;
    text = new_text;
  }
}
}
</pre>
<p>With this in place we can now check the following example cases
are well-behaved</p>
<pre class="programlisting">
string writeable(&quot;hello&quot;);
string another(writeable);
writable[0] = 'J';    // 0
cout &lt;&lt; writeable &lt;&lt; endl;   // 1
cout &lt;&lt; another &lt;&lt; endl;  // 2
const string readonly(&quot;Pat&quot;);
readonly[0] = 'C';    // 3
</pre>
<p>Line 1 should print &quot;Jello&quot; because writeable is modified in
line 0. Line 2 should print &quot;hello&quot;. Line 3 should give a compiler
error. Fine.</p>
</div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e66" id="d0e66"></a>But consider
this...</h2>
</div>
<pre class="programlisting">
writeable[0] = 'J';            // 0
cout &lt;&lt; writeable[0] &lt;&lt; endl;  // 4
</pre>
<p>The point to note is that a read access of a modifiable string
will cause the method <tt class=
"methodname">string::unshare_state()</tt> to be invoked. That's a
pity seeing as the statement on line 4 is not modifying the string.
Many of you will have read Jim Coplien's book Advanced C++
Programming Styles and Idioms and will know a way of solving this.
The trick is not to return a &quot;real&quot; char reference from the non
const version of <tt class="methodname">string::operator[]</tt> but
to return something that looks like, acts like, feels like, smells
like and behaves like char reference. A proxy. I'll call it
char_reference<sup>[<a name="d0e79" href="#ftn.d0e79" id=
"d0e79">1</a>]</sup>.</p>
</div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e85" id=
"d0e85"></a>string::char_reference</h2>
</div>
<pre class="programlisting">
namespace accu
{
class string
{
public: // types

  class char_reference
  {
  public:
    ...
    void operator=(char new_ch); 
    operator char() const;
    ...
  private:
    ...
  };

  char_reference operator[]
    (size_t index);
 const char &amp;operator[]
    (size_t index) const;
  ...
private:
  ...
};
}
</pre>
<p>I've made the char_reference assignment operator a void function
for simplicity of exposition. The return type is not the focus of
this article. With this sleight of hand in place we can look at
lines 0 and 4. Here's line 0 with the peel removed bit by
bit...</p>
<pre class="programlisting">
writeable[0] = 'J';
writeable.operator[](0) = 'J';
writeable.operator[](0).operator=('J');
</pre>
<p>And here's the expression in line 4 with the peel removed bit by
bit...</p>
<pre class="programlisting">
writeable[0] 
writeable.operator[](0)
writeable.operator[](0).operator char()
</pre></div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e98" id="d0e98"></a>Implementing
string::char_reference</h2>
</div>
<p>Fine, but I'm going to explore this a little further: in
particular, the implementation of the two char_reference methods. A
first attempt might look like this (implemented inline to save
space)</p>
<pre class="programlisting">
class char_reference
{
public:
  char_reference(char &amp;it) : ch(it) 
 {}
  void operator=(char new_ch) 
 { ch = new_ch; }
  operator char() const 
 { return ch; }
private:
  char &amp;ch;
};
</pre>
<p>However, this is flawed. Once again we need to remember to
unshare the string state when it is being modified. Changing an
element of a string is something that should be done by a method of
string. Here's another attempt:</p>
<pre class="programlisting">
class char_reference
{
public:
  char_reference
    (string &amp;s, size_t index);
  void operator=(char new_char); 
  operator char() const;    
private:
  string &amp;s;
  size_t index;
};
</pre>
<p>This leaves the interesting question of what methods of string
the methods of char_reference should delegate to. The conversion
operator can be implemented like this (in a conforming
compiler):</p>
<pre class="programlisting">
string::char_reference::operator char() const
{
  const string &amp;ro = s;
  return ro[index];
}
</pre>
<p>Note that s must be used as a read only string reference, to
avoid infinite recursion. But, how can the assignment operator be
implemented? Not like this, because we're back to infinite
recursion again.</p>
<pre class="programlisting">
void string::char_reference::operator=
  (char new_ch)
{
  s[index] = new_ch;
}
</pre></div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e117" id="d0e117"></a>A new string
method: public or private?</h2>
</div>
<p>One way to solve this is to create a new string method. For
example</p>
<pre class="programlisting">
void string::assign
  (size_t index, char new_ch)
{
  bounds_check(index);
  unshare_state();
  text[index] = new_ch;
}
</pre>
<p>The question is whether to make <tt class=
"methodname">string::assign</tt> public or private<sup>[<a name=
"d0e129" href="#ftn.d0e129" id="d0e129">2</a>]</sup>. There are
conflicting forces. On the one hand you might want to make it
private, viewing it as an implementation detail. You might also
want to make it private so that a string client has just one syntax
for assignment. But, how does <tt class=
"classname">char_reference</tt> gain access to this private method?
The usual solution is as a friend.</p>
<pre class="programlisting">
namespace accu
{
class string
{
public: // types

  class char_reference
  {
  public:
    ...
    void operator=(char new_ch) 
      {
      s.assign(index, new_ch);
      }
  };
  ...
private:
  friend char_reference;
  void assign(size_t index, char new_ch);
  ...
};
}
</pre>
<p>On the other hand you might consider that the cure is worse than
the symptoms. Granting char_reference total friendship when limited
friendship (to assign) was all that was required might be seen as
something of a large sledge-hammer cracking a small nut. If this is
your view, you'd probably make the primitive public, and accept a
choice of assignment syntax.</p>
</div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e140" id="d0e140"></a>A new string
method: public but uncallable!</h2>
</div>
<p>However, there is an alternative. You can remove the friendship,
and make <tt class="methodname">string::assign</tt> public but
uncallable! Bizarre<sup>[<a name="d0e148" href="#ftn.d0e148" id=
"d0e148">3</a>]</sup>. The trick is to use an opaque type.</p>
<pre class="programlisting">
namespace accu
{
class string
{
public: // types

  class char_reference
  {
  public:
    ...
    void operator=(char new_ch); 
  };

  char_reference operator[]
    (size_t index);
  ...
public: // but uncallable!

  struct position; // HERE
  void assign(position index, char new_ch);

private:
  ...
};
}
</pre>
<pre class="programlisting">
namespace accu
{
struct string::position
{
  size_t index;
};
...
void string::char_reference::operator=
  (char new_ch)
{
  position p = { index };  
  s.assign(p, new_ch);
}
...
void string::assign
  (position pos, char new_ch)
{
  bounds_check(pos.index);
  unshare_state();
  text[pos.index] = new_ch;
}
...
}
</pre>
<p>That's all for now. Cheers</p>
</div>
<div class="footnotes"><br>
<hr class="c2" width="100">
<div class="footnote">
<p><sup>[<a name="ftn.d0e79" href="#d0e79" id=
"ftn.d0e79">1</a>]</sup> Note that char_reference will also be
valuable when implementing <tt class=
"methodname">string::iterator::operator*()</tt></p>
</div>
<div class="footnote">
<p><sup>[<a name="ftn.d0e129" href="#d0e129" id=
"ftn.d0e129">2</a>]</sup> There was a long thread on ACCU.general
essentially boiling down to this recently</p>
</div>
<div class="footnote">
<p><sup>[<a name="ftn.d0e148" href="#d0e148" id=
"ftn.d0e148">3</a>]</sup> There is also another solution. It is
possible to grant limited friendship. Mark Radford showed me how.
Perhaps I'll cover that in another article.</p>
</div>
</div>
</p>
<p><strong>Notes:</strong>&nbsp;</p>
<p><em>More fields may be available via dynamicdata ..</em></p>
</div>
</channel>
</rss>
