is there a merge for associative arrays

Daniel Davidson nospam at spam.com
Sat Nov 9 08:28:24 PST 2013


On Tuesday, 5 November 2013 at 17:47:16 UTC, bearophile wrote:
> TV[TK] mergeAAs(TK, TV)(TV[TK] aas...) {
>
> It seems even fit for Phobos.
>
> Bye,
> bearophile

I have something I would appreciate feedback/criticism on. My 
first stab at it worked, but had no support for passing in 
const/immutable.

AA mergeAAs(alias fun = "a + b", AA)(AA[] aas...) 
if(isAssociativeArray!AA) {
   AA result;
   ...
}

Not sure if this is a good way or if there are better idiomatic 
ways, but here is what I have got. Any suggestions/improvements 
to make it more idiomatic would be appreciated. Is there already 
a DeepUnqual equivalent in phobos?

Thanks
Dan

import std.stdio;
import std.traits;
import std.algorithm;
import std.functional;

template DeepUnqual(T) {
   static if(isAssociativeArray!T) {
     alias Unqual!(Unqual!(ValueType!T)[Unqual!(KeyType!T)]) 
DeepUnqual;
   } else static if(isDynamicArray!T) {
     alias Unqual!(Unqual!(ArrayElementType!T)[]) DeepUnqual;
   } else static if(isPointer!T) {
     alias Unqual!(PointerTarget!T) * DeepUnqual;
   } else {
     alias Unqual!T DeepUnqual;
   }
}

DeepUnqual!AA
mergeAAs(alias fun = "a + b", AA)(AA[] aas...) 
if(isAssociativeArray!AA) {
   DeepUnqual!AA result;
   if(aas.length) {
     foreach( aa ; aas ) {
       foreach( k , v ; aa ) {
         auto found = k in result;
         if(found) {
           *found = binaryFun!fun(*found, v);
         } else {
           result[k] = v;
         }
       }
     }
   }
   return result;
}

void main() {
   alias double[string] AA;
   AA a = [ "foo":1.1, "bar":2.2 ];
   AA b = [ "foo":1.1, "bard":2.2 ];
   writeln(mergeAAs(a, b));
   writeln(mergeAAs!q{a*b}(a, b));

   {
     const AA ca = a.dup;
     const AA cb = b.dup;
     writeln(mergeAAs(ca,cb));
   }

   {
     immutable AA ia = [ "foo":1.1, "bar":2.2 ];
     immutable AA ib = [ "foo":1.1, "bard":2.2 ];
     writeln(mergeAAs(ia,ib));
   }
}


More information about the Digitalmars-d-learn mailing list