From: Robert Klemme Date: 2007-05-18T17:40:18+09:00 Subject: Re: "Crystallizing" Objects On 17.05.2007 11:55, Sven Suska wrote: > in this post, I'd like to make a proposal to contribute > to Ruby's fitness for the challenges of parallelization. > > The problem with sharing objects between threads > is concurrent write access. > If the objects were frozen, > everything would be OK ... but also boring. :) > > Now, I think it should be possible > to freeze the "already existing" data of an object > and at the same time leave it open for "further growth". > Especially, I have Hashes and Arrays in mind: > New key/value pairs could be added to Hashes, > objects could be appended to Arrays. Do you envision this added state to be shared by threads or thread local? > So, I think it would be beneficial to introduce a third state of objects > between frozen and normal, like "growing" or "crystallizing" or > "monotonous" or "incrementally_freezing" or "partially_frozen" ... > > In this state, all methods that would > modify the already "crystallized" data of the object > should throw an exception. > E.g. for strings, only appending would be allowed. I do not believe that it would be beneficial and here's why: on an abstract level the state of the object still changes, so you need proper synchronization mechanisms in place. Now, if you can *identify* the subset of the state that does not change, you can put it into another instance (probably of another class). Now you have a clean separation of constant state and mutable state - even better: you do not have *any* locking issues at all if you use the mutable instance only in one thread and share the constant only. Implementation complexity (of the interpreter) and efficiency wise this is much better than having a single instance with split state where read write synchronization has to take place. You will have to define the constant and mutable part for any class individually anyway so you can as well build concrete collaborating classes in Ruby that will handle this. Concrete: if you want Arrays with common immutable prefixes, just create a class SharedImmutablePrefixArray (possibly using Delegator or such) that refers a shared constant Array and a local mutable Array and implements methods like #[], #[]=, #each, #size etc. accordingly. You could even create this class in a way that the mutable state is stored via Thread#[] (i.e. thread local storage) so a single instance can actually be shared by multiple threads. Other advantages of this approach: it is *explicit*, i.e. in code you create an instance of SharedImmutablePrefixArray per thread and it becomes apparent what's going on. Also, with a single instance that would combine mutable and immutable state for multiple threads internally garbage collection will be much harder, since you will not have an object reference for the per thread state. This again will make the implementation of GC much more complex and likely less efficient. > Has a similar idea been discussed before? I am not aware of something like this. But it's good to discuss suggestions like this from time to time. :-) Kind regards robert