Container templates and constancy of elements
Stewart Gordon
smjg_1998 at yahoo.com
Wed Mar 14 11:51:54 PDT 2012
With some containers, such as lists and trees (binary search trees aside), it doesn't
matter if the elements can change state, since the data structure remains well-formed.
However, with others, such as sets and AAs, it's desirable if the keys don't mutate. Any
operations on them won't work right if there are keys in the wrong hash slots or out of
order (depending on the underlying data structure) because they have changed since being
put into the container. Of course, this doesn't apply to _values_ in an AA, since these
can safely mutate.
In Java and D1, it seems you just have to go on trust if you want your container to accept
key types other than strict value types. But can we do better in D2 - short of forcing
the key type to be immutable, which would hinder the container's usefulness?
But it seems D2 has taken one step in that general direction by automatically
tail-consting the key type of an AA. But it doesn't stop modifications to the key through
mutable references to the data. And if the key is of class type, you can still modify the
object, since D2 conflates constancy of an object reference with constancy of the object
itself. This is in itself silly. Really, D should have tail-const built in for stuff
like this. OK, so there's Rebindable, but I've found it to be a PITA when trying to do
generic programming with it, as well as leading to this AA key anomaly because it isn't a
built-in feature.
I suppose there are a few possibilities for what constancy to apply to elements of a data
structure to which changes might affect the structure's integrity:
(a) force the type to be tail-const if it's an array, otherwise don't add any constancy
(b) force the type to be tail-const if it's an array, or fully const if it's a class
(c) force the type to be tail-immutable if it's an array, otherwise don't add any constancy
(d) force the type to be tail-immutable if it's an array, or fully immutable if it's a class
(e) don't add any constancy, but just rely on trust
Currently, AAs implement (a). (d) guarantees that changes to the data that mess up the
data structure will never happen, at least if the programmer doesn't bypass the const
system. (e) is the route D1 and Java are forced to take. Am I right in thinking that
sets and maps in the C++ STL take the same path?
Anyway, what are people's thoughts on the right way to go here?
Stewart.
More information about the Digitalmars-d
mailing list