|
Boost : |
Subject: Re: [boost] Reflection?
From: Jean-Louis Leroy (jl_at_[hidden])
Date: 2008-11-04 15:47:35
> I've merged several of Your posts so I can reply in one message,
> lazy me, sorry ;-P
>
Excellent idea :-)
I have renamed my library 'introspection' (to avoid clashing with
Jeremy's work) and committed it to the sandbox.
Today I wet my feet with Boost.Mirror. Using the doc (and the source
code ;-)) I was able to make the code at the bottom of this message
work. After a couple of hours 1/ I was very impressed 2/ I had a
headache 3/ I was convinced that building runtime reflection on top of
your work will be easy and 4/ I had found a bug ;-)
> But I was thinking (suprisingly enough) about gcc2xml being used
> as an optional support for automated registering of things into mirror,
> on those platforms where it is available.
>
Sure, we must write the backend in such a way that it is useable
stand-alone then write generators. My experience is that generators are
fine as long as you have only one of them in a project but two won't
coexist well, usually.
I'm running out of time, I have to work on serious things, namely
preparing my trip to ... Slovakia !
Here's my Mirror hello-world, with the bug report:
#include <iostream>
#include <boost/mirror/meta_class.hpp>
#include <boost/mirror/meta_inheritance.hpp>
#include <boost/mirror/algorithm/for_each.hpp>
using namespace std;
using namespace boost;
using namespace boost::mirror;
struct animal {
int age;
};
struct mammal : virtual animal {
};
struct carnivore : virtual animal {
};
struct dog : mammal, carnivore {
};
namespace boost { namespace mirror {
BOOST_MIRROR_REG_TYPE_GLOBAL_SCOPE(animal)
BOOST_MIRROR_REG_CLASS_ATTRIBS_BEGIN(animal)
BOOST_MIRROR_REG_SIMPLE_CLASS_ATTRIB(_, int, age)
BOOST_MIRROR_REG_CLASS_ATTRIBS_END
BOOST_MIRROR_REG_TYPE_GLOBAL_SCOPE(mammal)
BOOST_MIRROR_REG_BASE_CLASSES_BEGIN(mammal)
BOOST_MIRROR_REG_VIRTUAL_BASE_CLASS(0, public, animal)
BOOST_MIRROR_REG_BASE_CLASSES_END
// watch out: BOOST_MIRROR_REG_SINGLE_BASE_CLASS_VIRTUAL(mammal, public,
animal)
// doesn't work because it calls BOOST_MIRROR_REG_BASE_CLASS_VIRTUAL
// instead of BOOST_MIRROR_REG_VIRTUAL_BASE_CLASS
BOOST_MIRROR_REG_TYPE_GLOBAL_SCOPE(carnivore)
BOOST_MIRROR_REG_BASE_CLASSES_BEGIN(carnivore)
BOOST_MIRROR_REG_VIRTUAL_BASE_CLASS(0, public, animal)
BOOST_MIRROR_REG_BASE_CLASSES_END
BOOST_MIRROR_REG_TYPE_GLOBAL_SCOPE(dog)
BOOST_MIRROR_REG_BASE_CLASSES_BEGIN(dog)
BOOST_MIRROR_REG_BASE_CLASS(0, public, mammal)
BOOST_MIRROR_REG_BASE_CLASS(1, public, carnivore)
BOOST_MIRROR_REG_BASE_CLASSES_END
} }
struct print_attribute {
template<typename ATTRIBUTE> void operator()(ATTRIBUTE) {
cout << ATTRIBUTE::get_name(mpl::false_(), std::char_traits<char>())
<< endl;
}
};
struct print_base {
template<typename CLASS> void display(CLASS, virtual_base_) {
cout << "virtual " <<
CLASS::meta_base_class::get_name(mpl::false_(),
std::char_traits<char>()) << endl;
}
template<typename CLASS> void display(CLASS, nonvirtual_base_) {
cout << CLASS::meta_base_class::get_name(mpl::false_(),
std::char_traits<char>()) << endl;
}
template<typename CLASS> void operator()(CLASS c) {
display(c, CLASS::inheritance_specifier());
}
};
int main() {
mirror::for_each< meta_class<animal>::attributes >(print_attribute());
mirror::for_each< meta_class<mammal>::base_classes >(print_base());
mirror::for_each< meta_class<dog>::base_classes >(print_base());
return 0;
}
Cordially,
Jean-Louis
Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk