Cloning in D

dsimcha dsimcha at yahoo.com
Mon Sep 6 17:55:16 PDT 2010


== Quote from Michel Fortin (michel.fortin at michelf.com)'s article
> I'm under the impression that a too permissive generic implementation
> of cloning is going to break things in various scenarios.

In general you raise some very good issues, but IMHO the right way to do cloning
is to have permissive generic cloning that works in the 90% of cases and can be
easily overridden in the 10% of cases, not to require writing tons of boilerplate
in the 90% of cases just to make sure it doesn't do the wrong thing by default in
the 10% of cases.

A second point is that the thing that brought this whole cloning issue to my mind
was making std.concurrency's message passing model less obtuse.  Right now it's
hard to use for non-trivial things because there's no safe way to pass complex
state between threads.  If we start allowing all kinds of exceptions to the "clone
the **entire** object graph" rule, cloning will rapidly become useless for safely
passing complex object graphs between threads.

> What if your
> object or structure is part of a huge hierarchy where things contains
> pointers to their parent (and indirectly to the whole hierarchy), will
> the whole hierarchy be cloned?

Isn't that kind of the point?

> What happens if your object or structure
> maintains a reference to a singleton, will we get two instances of a
> singleton?

Very good point.  I guess the reasonable use case for holding a reference to a
singleton (instead of just using the globally accessible one) would be if it's
polymorphic with some other object type?  If you're using message passing
concurrency, most of your mutable singletons are probably thread-local, and what
you probably really want to do is use the thread-local singleton of the thread
you're passing to.

> What if your object or structure implements the observer
> pattern and contains a list of objects to notify when something
> happens, will all the observers be cloned as well?

Yes.  There's no other way to make message passing safe.

> My understanding is that a data structure containing a pointer cannot
> be cloned safely unless it contains some specific code to perform the
> cloning. That's because the type system can't tell you which pointers
> point to things owned by the struct/class and which one need to be
> discarded when cloning (such as a list of observers, or the parents of
> a hierarchy).

This discussion is making me think we really need two kinds of cloning:  Physical
cloning would clone the entire object graph no matter what, such that the cloned
object could be safely passed to another thread via std.concurrency and be given a
unique type.  Logical cloning would be more like what you describe.  In general,
this discussion has been incredibly useful because I had previously only
considered physical cloning.

> As for pointers to immutable things, the clone can keep pointing to the
> same immutable data without affecting semantics, so there's no problem
> there.

Right.  There aren't too many good reasons to clone immutable data.


More information about the Digitalmars-d mailing list