On Thursday, 9 May 2013 at 00:10:48 UTC, Byron Heads wrote:
I have a variant associative array. In the example below I am
wondering
if there is a way to create the array without having to
indicate the
variant type on all of the values. Would like to be able to
write code
like #2, or something cleaner/better for #1. This is intended
for a
library. Other option would be variable parameters, not sure
how the
function signature would look for this.
Any ideas, complaints?
import std.stdio,
std.variant;
alias Algebraic!(string, long) HDType;
void main()
{
// #1 This works
foo(["first" : HDType("John"),
"last" : HDType("Doe"),
"phone" : HDType(1234546)]);
// #2 Wont compile, type mismatch string and long
foo(["first" : "John",
"last" : "Doe",
"phone" : 1234546]);
// #3 Other idea
bar("first", "John", "last", "Doe", "phone", 12345678);
}
void foo(HDType[string] attr)
{
foreach(string k, ref HDType v; attr)
{
writeln(k, ". ", v.toString());
}
}
first doesn't compile with DMD 2.062 as int implicitly not
converted to long.
foo func takes associative array, within this example you can use
type Variant[string] to make life a bit easier(but i can't
recommend it for ur real code cause we don't know the usage).
and for third func here is example code, though it doesn't takes
associative array you can rewrite it to suit ur needs, also
notice that it's a bit dirty and not very readable cause i'm
superlazy and quite in a hurry, so you can improve it yourself
---------------
void bar(...)
{
import core.vararg;
enum string handler = `.visit! (
// string type handler
(string s) => write(s, pos %2 == 0 ? ':' : '\n'),
// long type handler
(long l) => write(l, pos %2 == 0 ? ':' : '\n')
)();`;
for( int pos = 0; pos < _arguments.length ; pos++ )
{
if ( _arguments[pos] == typeid(HDType) )
mixin(`(va_arg!(HDType)(_argptr))` ~ handler );
else if ( _arguments[pos] == typeid(string) )
mixin(`HDType(va_arg!(string)(_argptr))` ~ handler );
else if ( _arguments[pos] == typeid(long) )
mixin(`HDType(va_arg!(long)(_argptr))` ~ handler );
else
throw new Exception("wrong type");
}
}