Craig Kuhnert wrote:
downs Wrote:
Craig Kuhnert wrote:
Hi
I am trying to convert some code I wrote in C++ to D to give it a try and I
have come across some code that I dont know how to convert.
I have simplified the code to illustrate the problem I have.
How do I do this in D?
class IFieldSetter
{
public:
virtual void SetValue(void * object, const void * value) = 0;
};
template <class C, class T>
class FieldSetter : public IFieldSetter
{
private:
typedef T (C::* MemberField);
MemberField field;
public:
FieldSetter(MemberField afield)
: field(afield)
{}
void SetTypedValue(C * object, const T& value)
{
object->*field = value;
}
void SetValue(void * object, const void * value)
{
SetTypedValue((C*) object, (const T&) value);
}
};
class MySampleClass
{
public:
int Status;
std::string Name;
};
void main(void)
{
IFieldSetter * StatusSetter = new
FieldSetter<MySampleClass,int>(&MySampleClass::Status);
IFieldSetter * NameSetter = new
FieldSetter<MySampleClass,std::string>(&MySampleClass::Name);
MySampleClass * a = new MySampleClass();
MySampleClass * b = new MySampleClass();
StatusSetter->SetValue(a, (void*)20);
StatusSetter->SetValue(b, (void*)40);
NameSetter->SetValue(a, "2002");
NameSetter->SetValue(b, "2002");
}
Thanks
Craig
If I'm getting this correctly, here's one way to do it ..
module test;
import std.stdio, tools.ctfe: ctReplace; // easy to write your own ctReplace
function
template Init(T) { T Init; }
interface IFieldSetter {
void setValue(Object obj, void* value);
}
class FieldSetter(T: Object, string Name) : IFieldSetter {
override void setValue(Object obj, void* value) {
auto tee = cast(T) obj;
mixin("tee.%NAME = *cast(typeof(tee.%NAME)*) value; ".ctReplace("%NAME",
Name));
}
void setValue(T obj, typeof(mixin("Init!(T)."~Name)) value) {
mixin("obj.%NAME = value; ".ctReplace("%NAME", Name));
}
}
class Sample {
int status;
string name;
}
void main() {
auto statSetter = new FieldSetter!(Sample, "status");
auto nameSetter = new FieldSetter!(Sample, "name");
auto sample = new Sample;
int i = 20;
statSetter.setValue(sample, &i);
statSetter.setValue(sample, 40);
nameSetter.setValue(sample, "Fooblr");
}
Thanks
Thats brilliant! D rocks!
I never though of using mixin for that purpose.
There's almost NOTHING which is impossible with string mixins. With just
recursive string mixins, coupled with .stringof and is(typeof()), you
can get access to most of the compiler's semantic analysis, and its
symbol table.
Deep in the final semantic pass, just before code generation, when you
have access to all the type information, you can generate new source
code for the compiler to start again at the beginning with parsing.
It's insanely powerful.