Initializing a subset of state

D

Dave

Hello all,

I have a class that contains a large number of discrete pieces of state
information. Any combination of these member variables might be valid for a
given object. Any given member variable might be used or unused in a given
object. For each field, there is a FieldIsValid() member function that must
be called before accessing or mutating a given field. If a field is
reported as not valid, it must not be accessed or mutated.

Let me take a quick detour here. I think this is a terrible design, but
it's what I've been tasked to work with. I am the maintainer, not the
original implementer. This class is heavily used, so extricating it and
replacing it with something better designed is not an option. OK, detour
over.

Constructors have been defined for the combinations of fields that have been
needed so far. Now, more combinations of fields are needed. The number of
constructors is liable to grow exponentially. Rather than continuing to
tack on additional constructors in this manner, I would like to come up with
a general scheme to initialize any subset of member variables. Note that I
said "initialize", not "assign". The object needs to be in a usable state
after construction. It is not acceptable to construct it half-baked and
then go call a bunch of mutators for the fields I care about.

I have had some thoughts on this, but I would also like to solicit
suggestions. Any and all suggestions will be appreciated!

Thanks,
Dave
 
D

davidrubin

Dave said:
Hello all,

I have a class that contains a large number of discrete pieces of state
information. Any combination of these member variables might be valid for a
given object. Any given member variable might be used or unused in a given
object. For each field, there is a FieldIsValid() member function that must
be called before accessing or mutating a given field. If a field is
reported as not valid, it must not be accessed or mutated.

This is a really terrible idea. It is perfectly okay to have a
constructor that initializes a subset of the object's value, but every
contructor should construct the object "having default values for
unspecified fields."
Let me take a quick detour here. I think this is a terrible design, but
it's what I've been tasked to work with. I am the maintainer, not the
original implementer. This class is heavily used, so extricating it and
replacing it with something better designed is not an option. OK, detour

Okay.

Constructors have been defined for the combinations of fields that have been
needed so far. Now, more combinations of fields are needed. The number of
constructors is liable to grow exponentially. Rather than continuing to
tack on additional constructors in this manner, I would like to come up with
a general scheme to initialize any subset of member variables.

One straightforward method is to default-construct the object "in a
valid, but unspecified state," (meaning each field has some valid
default value), and then use a "set" manipulator to set each data
member. Initializing a subset of the object's value becomes a matter of
calling the appropriate subset of manipulators. This is more typing,
but it is scalable. If your class has value-semantics, you need all
these manipulators anyway to have any hope of writing reasonable test
cases for 'operator==' and 'operator!='.
Note that I
said "initialize", not "assign". The object needs to be in a usable state
after construction.

If you cannot default-construct the object in a valid state, you cannot
do what you want to do very easily.

That said, another method is to provide a variant data type conforming
to a schema known to the object. You specify the data object and the
schema, and the object constructor initializes the appropriate data
members. Schemas can be generated automatically by the build system.
The constructor can even use a utility function to initialize the data
members through assignment via the manipulators. But at this point,
you're just adding unneccessary complexity.
It is not acceptable to construct it half-baked and
then go call a bunch of mutators for the fields I care about.

Can you provide a technical reason why this is not feasible?

/david
 
J

Jonathan Turkanis

Dave said:
Hello all,

I have a class that contains a large number of discrete pieces of
state information. Any combination of these member variables might
be valid for a given object. Any given member variable might be used
or unused in a given object. For each field, there is a
FieldIsValid() member function that must be called before accessing
or mutating a given field. If a field is reported as not valid, it
must not be accessed or mutated.

Boost will soon has a named parameters library which will allow you to constuct
an object like so:

Thing t(height = 6, width =12.3, name = "stanley",
favorite_movie="splash");

Here the keywords height, weight, .. are labels which can be specified in any
order.

Unfortunately I can't find a link to the documentation.
Thanks,
Dave

Jonathan
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,999
Messages
2,570,243
Members
46,836
Latest member
login dogas

Latest Threads

Top