Thread overview
Converting member variables to strings with using reflection from base class
Dec 22, 2017
kerdemdemir
Dec 22, 2017
H. S. Teoh
Dec 22, 2017
Mengu
December 22, 2017
I want to make a logging function for member variables by using reflection.

import std.stdio;

class D : B
{
    override void foo() {
        a  = 4.0;
        b  = 3.0;
    }
    double a;
    double b;
}

class B
{
    void Log()
    {
        auto a = [__traits(derivedMembers, D)];
        foreach(memberName; a) {
            // Somehow write only member variables with their names
            // Result should be : a = 4.0, b = 3.0
        }
    }

    void foo()
    {
    }
}

void main()
{
     auto b = new D;
     b.Log();
}

As I wrote in the comments I want to see member variable's name and its value.
What is the best way to achieve that?

Erdem
December 22, 2017
On Fri, Dec 22, 2017 at 09:13:31PM +0000, kerdemdemir via Digitalmars-d-learn wrote:
> I want to make a logging function for member variables by using reflection.
[...]
> class B
> {
>     void Log()
>     {
>         auto a = [__traits(derivedMembers, D)];
>         foreach(memberName; a) {
>             // Somehow write only member variables with their names
>             // Result should be : a = 4.0, b = 3.0

Try this:

	import std.traits : FieldNameTuple;
	foreach (memberName; FieldNameTuple!B) {
		writefln("%s = %s", memberName, mixin("this." ~ memberName));
	}


T

-- 
People walk. Computers run.
December 22, 2017
On Friday, 22 December 2017 at 22:09:05 UTC, H. S. Teoh wrote:
> On Fri, Dec 22, 2017 at 09:13:31PM +0000, kerdemdemir via Digitalmars-d-learn wrote:
>> I want to make a logging function for member variables by using reflection.
> [...]
>> class B
>> {
>>     void Log()
>>     {
>>         auto a = [__traits(derivedMembers, D)];
>>         foreach(memberName; a) {
>>             // Somehow write only member variables with their names
>>             // Result should be : a = 4.0, b = 3.0
>
> Try this:
>
> 	import std.traits : FieldNameTuple;
> 	foreach (memberName; FieldNameTuple!B) {
> 		writefln("%s = %s", memberName, mixin("this." ~ memberName));
> 	}
>
>
> T

and then turn it into a LoggerMixin with a mixin template and re-use it any time you want.

import std.stdio : writeln, writefln;
import std.traits : FieldNameTuple;

mixin template LoggerMixin() {
  void Log() {
    foreach (memberName; FieldNameTuple!(typeof(this))) {
      writefln("%s = %s", memberName, mixin("this." ~ memberName));
    }

  }
}

struct S {
  int x;
  bool y;
  double z;

  mixin LoggerMixin;
}

void main() {

  S s1 = S(int.min, true, 6666);
  S s2 = S(int.max, false, 6666);
  s1.Log();
  s2.Log();
}