www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.announce - SuperStruct v0.2.0

For those that missed the first announcement 
(http://forum.dlang.org/thread/jiucsrcvkfdzwinqpzxg forum.dlang.org?page=1),
SuperStruct is a struct that acts like a class; basically, a value type that
exposes a common interface from its 'subtypes'.

Code on github: https://github.com/rcorre/superstruct

Anyways, I was having enough fun with this slightly ridiculous 
idea to make a v0.20, so with no further ado, here's whats new:

Operators get passed through just like any other common members.

You can try to cast a SuperStruct to a subtype (throws on 

If members have a common signature but uncommon return types, the 
member _is_ forwarded and the return type is a SuperStruct of the 
possible return types (this means it has any behavior common to 
the return types). Thanks to Timon Gehr for the suggestion! 
(http://forum.dlang.org/thread/jiucsrcvkfdzwinqpzxg forum.dlang.org?page=2#post-n09600:241gel:241:40digitalmars.com)

A SuperStruct can now satisfy a range interface (this required 
using mixed-in members instead of opDispatch).

Create a SuperStruct on the fly with pick or pickAmong (similar 
to std.range's choose/chooseAmong, but works for any types, not 
just ranges).

unittest {
   import std.range, std.algorithm, std.container;

   alias Container(T) = SuperStruct!(SList!T, Array!T);

   Container!int slist = SList!int();

   // We can call any members that are common among containers
   assert(slist.front == 1);

   // opSlice is supported on all the subtypes, but each returns a 
different type
   // Container.opSlice will return a SuperStruct of these types
   auto slice = slist[];     // [1,2,3,4]
   assert(slice.front == 1);
   slice.popFront();         // [2,3,4]
   assert(slice.front == 2);

   // as slice is a SuperStruct of range types, it still works as 
a range
   slist.insert(slice); // [2,3,4] ~ [1,2,3,4]
Nov 24 2015