Accessor Methods (Was: Re: An evangelist's handbook?)

Hung Jung Lu hungjunglu at yahoo.com
Wed Nov 13 10:00:19 EST 2002


Alex Martelli <aleax at aleax.it> wrote in message news:<owWy9.11842$XO.493367 at news2.tin.it>...
> >    What is the benefit of "public by default"?
> 
> Minimizing boilerplate.  90% of exposed properties in languages and
> object models which don't support that lead to a lot of boilerplate:
> ... 
> or (in COM/C++):
> 
>     HRESULT get_Pliffo(WhateverType* pVal) {
>         if(!pVal) return E_POINTER;
>         *pVal = m_Pliffo;
>     }
>
> and so on, and so forth.  There is no benefit whatsoever in all that
> boilerplate.  Maybe, if one has been educated to such strict discipline,
> there is a "feel-good factor" -- "See, Mum, I'm being a good boy and
> only accessing Pliffo via an accessor method!".  

I agree with accessor methods being boilerplate in Python. But in C++,
under some circumstances, it's a real necessity.

The one place that I find it necessary to use accesor methods is for
base classes to access attributes of derived classes.

An object often need to access attributes from four places: (a)
attributes from its own-level class, (b) attributes from its base
class(es), (c) attributes from another object belonging to another
class, (d) attributes from a subclass, this last point because a
method is implemented at the base class level.

Python can do all of (a), (b), (c) and (d).

C++ cannot do (d), at least not in a simple manner. (And you don't
want to have circular "#include"s.)

In Python, I often would check the existence of an attribute before
proceeding:

    if hasattr(self, 'x'):
        .... do something with self.x

This is great for methods implemented at the base class level that
need to access attributes of subclasses. C++ can't do this, in a
straightforward manner. To fix idea, the base class could be "Person",
the derived class could be "USTaxablePerson", and "x" be U.S. tax-id
or social security number.

One way out is for C++ to implement the variable 'x' at the base class
level. But this means that objects that don't have the 'x' attributes
still need to carry that data field. (e.g: infants don't have tax-id).
This is not a problem when the number of data fields is small, or when
the number of person is small. It becomes a problem when you have many
data fields and many persons.

What I have found out is, for some problems in C++, you often want to
make powerful subclasses with minimum data attributes. That is, base
classes will have a lot of methods, but only a few data members. On
the other hand, subclasses add more data attributes, but not more
methods.

It is in these types of problems that accessor methods are necessary.
It is much more economical and natural for objects in the class
hierarchy to share methods than to share data attributes. The getX()
method at the base class would simply raise an error, because 'x' does
not exist at the base class level. The getX() in the subclass would
return the appropriate value of x. Not just because U.S. tax-id is
needed for one particular purpose, would we implement that data field
for all persons (or martians), and put value NULL there. If there are
10 billion persons/martians, you'd be wasting many billion bytes, for
nothing. Again, the problem is small if that's the only data field we
are talking about, but in a complex class hierarchy tree with many
subclasses and many instances, you'll have to start to pay attention
as to where to put the data members.

C++ has virtual methods, but no virtual data members.

And, that to me, is the main reason why C++ needs accessor methods.

Hung Jung



More information about the Python-list mailing list