Convenient debug printing
ezneh
petitv.isat at gmail.com
Sat Feb 2 14:58:42 UTC 2019
On Friday, 1 February 2019 at 15:49:24 UTC, Per Nordlöw wrote:
> [...]
Alright, after quite some work I finally managed to do the
following code printing also nested variable names from classes &
structs. I am not sure it's quite the same as the Rust AST macro
for that, but I guess it's still interesting:
import std.stdio;
template dbg(args...)
{
alias dbgImpl!(args).print dbg;
}
template dbgImpl(args...)
{
import std.traits;
void print(string file = __FILE__, uint line = __LINE__, string
fun = __FUNCTION__)
{
static foreach (_; args)
{
static if(isBuiltinType!(typeof(_)))
debug stderr.writefln("[%s:%s (%s)] %s = %s", file, line, fun,
__traits(identifier, _), _);
static if(isAggregateType!(typeof(_)))
{
debug stderr.writefln("[%s:%s (%s)] %s = %s", file, line,
fun, __traits(identifier, _), toDbgString(_));
}
}
}
string toDbgString(Arg)(Arg o)
{
string dbgstr = "(";
import std.format;
static foreach(f; FieldNameTuple!(typeof(o)))
{
static if(isBuiltinType!(typeof(__traits(getMember, o, f))))
{
dbgstr ~= format("%s:%s, ", f, __traits(getMember, o, f));
}
static if(isAggregateType!(typeof(__traits(getMember, o, f))))
{
dbgstr ~= format("%s = %s, ", f,
toDbgString(__traits(getMember, o, f)));
}
}
return dbgstr[0..$-2] ~ ")";
}
}
struct Foo{ int s = 2; bool b = false; Bar bar;}
struct Bar{ auto c = 'c';}
class FooBar{ int t; Foo f; }
void main()
{
int i;
float f = 3.14;
string s = "some string";
Foo foo;
Bar bar;
FooBar fb = new FooBar;
dbg!(i, f, s, foo, 1+3, foo, bar, fb);
// prints:
// [dbg.d:54 (dbg.main)] i = 0
// [dbg.d:54 (dbg.main)] f = 3.14
// [dbg.d:54 (dbg.main)] s = some string
// [dbg.d:54 (dbg.main)] foo = (s:2, b:false, bar = (c:c))
// [dbg.d:54 (dbg.main)] _ = 4
// [dbg.d:54 (dbg.main)] foo = (s:2, b:false, bar = (c:c))
// [dbg.d:54 (dbg.main)] bar = (c:c)
// [dbg.d:54 (dbg.main)] fb = (t:0, f = (s:2, b:false, bar =
(c:c)))
}
More information about the Digitalmars-d
mailing list