Re: CT filtering of class members

2019-08-11 Thread Sjoerd Nijboer via Digitalmars-d-learn

On Sunday, 11 August 2019 at 16:32:20 UTC, Simen Kjærås wrote:

[...] Something like this:

import std.meta : Filter;
import std.traits : isFunction;
import std.algorithm.searching : canFind;

enum isNonspecialMemberFunction(string name) = 
!ctorAndDtor.canFind(name) &&
   
isFunction!(__traits(getMember, T, name));
enum memberFunctions = Filter!(isNonspecialMemberFunction, 
__traits(derivedMembers, T));


Filter operates on AliasSeqs, not arrays. That's why I restated 
the __traits(derivedMembers, T) part, but this could just as 
easily be done by changing this line:


enum members = [__traits(derivedMembers, T)];

to:

alias members = __traits(derivedMembers, T);

--
  Simen


Works beautiful, thank you very much!



Re: CT filtering of class members

2019-08-11 Thread Simen Kjærås via Digitalmars-d-learn

On Sunday, 11 August 2019 at 15:27:54 UTC, Sjoerd Nijboer wrote:

The following snippet doesn't compile

I am trying to reflect on a class and only do an operation with 
all member functions of a class.
But I can't seem to use a filter to only get the member 
functions out of a type T.


I understand that there are two errors in my snippet.
1) It cannot mixin a `name` because it is a variable from the 
lambda that `filter()` is using.
2) members.filter!(name => !ctorAndDtor.canFind(name)) does not 
filter on symbols defined in ctorAndDtor


How can I fix these problems and return all member functions 
whitout ctor and dtor of a type T?


This is classic D mix of compile-time and compile-time (no typo). 
I suggest reading H.S. Teoh's text on the topic: 
https://wiki.dlang.org/User:Quickfur/Compile-time_vs._compile-time


Now, as for what can actually be done: you should probably use 
std.meta.Filter (https://dlang.org/library/std/meta/filter.html) 
to filter the members list. This will require you to define a 
template to operate on each element. Something like this:


import std.meta : Filter;
import std.traits : isFunction;
import std.algorithm.searching : canFind;

enum isNonspecialMemberFunction(string name) = 
!ctorAndDtor.canFind(name) &&
   
isFunction!(__traits(getMember, T, name));
enum memberFunctions = Filter!(isNonspecialMemberFunction, 
__traits(derivedMembers, T));


Filter operates on AliasSeqs, not arrays. That's why I restated 
the __traits(derivedMembers, T) part, but this could just as 
easily be done by changing this line:


enum members = [__traits(derivedMembers, T)];

to:

alias members = __traits(derivedMembers, T);

--
  Simen


CT filtering of class members

2019-08-11 Thread Sjoerd Nijboer via Digitalmars-d-learn

The following snippet doesn't compile

I am trying to reflect on a class and only do an operation with 
all member functions of a class.
But I can't seem to use a filter to only get the member functions 
out of a type T.


I understand that there are two errors in my snippet.
1) It cannot mixin a `name` because it is a variable from the 
lambda that `filter()` is using.
2) members.filter!(name => !ctorAndDtor.canFind(name)) does not 
filter on symbols defined in ctorAndDtor


How can I fix these problems and return all member functions 
whitout ctor and dtor of a type T?


Code snippet:

void main()
{
GetFunctionMembers!Foo();
}

void GetFunctionMembers(T)()
{
enum members = [__traits(derivedMembers, T)];
pragma(msg, "Functions: " ~ members.stringof);

enum ctorAndDtor = ["this", "__ctor", "__dtor"];
enum memberFunctions = members.filter!(name => 
!ctorAndDtor.canFind(name)

&& mixin("isFunction!(T." ~ name ~ ")"))();

pragma(msg, memberFunctions);
}

class Foo
{
bool myBool;
int k;

this()
{
}

~this()
{
}

void bar(int k)
{
this.k = k;
}

void qux()
{
}
}