1st draft of complete class-based std.random successor

monarch_dodra monarchdodra at gmail.com
Thu Mar 20 01:51:07 PDT 2014


On Thursday, 20 March 2014 at 00:09:51 UTC, bearophile wrote:
> Joseph Rushton Wakeling:
>>   * std.random2.adaptor, random "adaptors" such as 
>> randomShuffle,
>>     randomSample, etc.
>
> Please don't use stuttering names like 
> "std.random2.randomShuffle". "std.random2.shuffle" is enough.

Agreed.

`randomShuffle` can be made a deprecated alias: This way, 
"random2" should still be mostly "drop in replacement", but we 
won't drag along the bad names.

>> My own feeling is that ultimately it is a responsibility of 
>> the language to offer nice ways to allocate classes without 
>> necessarily relying on new or the GC.
>
> I don't think the language is yet there. So I think currently 
> this is not a good idea.

I think there is 0 doubt that reference semantics is the way to 
go. An advantage of using class is that it is still *possible* to 
place them on the stack with Scoped, or with some future language 
mechanic. On the other hand, if we implement as reference 
structs, then that's that.

Furthermore, even in terms of performance, I think a heap 
allocated PRNG will still flat-out beat the value based one, if 
only because of the size of the damn thing.

That said, being able to allocate them on the malloc heap, and 
not the GC heap, would be (IMO) also a valid design.

A simple and dumb design might be to still implement them with 
value semantic but:
1. Disable postblit.
2. Make .save() return a "Random*"
This would mean
1. No dangers of accidental copy.
2. Range* is a ForwardRange.
3. Trivially allows GC/malloc/stack allocation.
With good aliases ("alias Random = RadomImpl*;"), and a "make!" 
template we could make the "default useage" transparent to this 
mechanism yet make it easy to get our hands under the hood.

But at this point, we are really beating around the bush on this 
issue. There are two things for sure:
1. Reference semantics by default.
2. There comes a point where we have to move forward.

I didn't check the code yet, but a "middle ground" could be to 
make all constructors private, and disable T.init. Then, we force 
construction through a make! template.

This might not be what's most convenient, but it would allow us 
to potentially change the design at a later stage, without 
breaking user code.

> Do you have a simple but very fast function that generates 
> uniforms in [0.0, 1.0]? :-)

AFAIK, the allocation issue is only for ranges? "uniform" is just 
a function, I don't think it affected by the issue. Even if you 
are operating on a "passed range", either ranges are reference 
semantics, and you take by value, or they are value semantic, and 
you take by ref. Either way, you have to pay for the indirection.


More information about the Digitalmars-d-announce mailing list