Mirror reflection library 0.5.13

mirror/example/various_01.cpp

This example shows the usage of multiple utilities provided by Mirror.

More preciselly this example shows the usage of the reflection macros, the meta-object classification and tag dispatch facility, base name getter functions, the members<> meta-function and the mp::for_each run-time algorithm.

Copyright 2008-2010 Matus Chochlik. Distributed under the Boost Software License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)

#include <mirror/mirror.hpp>
#include <iostream>

namespace std {

// helper class for easy indenting in standard streams
struct indent
{
    size_t amount;
    size_t spaces;

    indent(size_t a)
     : amount(a)
     , spaces(2)
    { }
};

// the overload of the << operator for indentation
template <typename Out>
Out& operator << (Out& out, indent ind)
{
    size_t n = ind.amount * ind.spaces;
    while(n--) out << ' ';
    return out;
}

} // namespace std

MIRROR_NAMESPACE_BEGIN

template <typename MetaObject>
void print_info(size_t);

// Helper functor which is used together with mp::for_each
struct info_printer
{
    size_t indent;

    info_printer(size_t ind)
     : indent(ind)
    { }

    template <class MetaObject>
    void operator()(MetaObject) const
    {
        print_info<MetaObject>(indent);
    }
};

// Helper function printing the info about the members of a scope
template <class MetaScope>
void print_members_info(size_t indent)
{
    // get the members of the scope
    typedef typename members<MetaScope>::type mems;
    // call the info_printer on each member of the MetaScope
    mp::for_each<mems>(info_printer(indent+1));
}

// fallback function for printing info
template <class MetaObject>
void print_info(size_t indent, meta_object_tag)
{
    std::cout << std::indent(indent) << "unknown object" << ::std::endl;
}

// overload printing info about a type
template <class MetaType>
void print_info(size_t indent, meta_type_tag)
{
    std::cout << std::indent(indent) << "type "
        << MetaType::base_name() << ::std::endl;
}

// overload printing info about a class
template <class MetaClass>
void print_info(size_t indent, meta_class_tag)
{
    std::cout << std::indent(indent) << "class "
        << MetaClass::base_name() << ::std::endl;
}

// overload printing info about a type
template <class MetaTypedef>
void print_info(size_t indent, meta_typedef_tag)
{
    std::cout << std::indent(indent) << "typedef "
        << MetaTypedef::base_name() << ::std::endl;
}

// overload printing info about a template type
template <class MetaType>
void print_info(size_t indent, meta_type_template_tag)
{
    std::cout << std::indent(indent) << "template "
        << MetaType::base_name() << ::std::endl;
}

// overload printing info about a namespace
template <class MetaScope>
void print_info(size_t indent, meta_namespace_tag)
{
    std::cout << std::indent(indent) << "namespace "
        << MetaScope::base_name() << ::std::endl
        << std::indent(indent) << "{" << ::std::endl;
    // print information about the members of the namespace
    print_members_info<MetaScope>(indent);
    std::cout << std::indent(indent) << "}" << ::std::endl;
}

// overload printing info about the global scope
template <class MetaObject>
void print_info(size_t indent, meta_global_scope_tag)
{
    std::cout << std::indent(indent) << "the global scope" << ::std::endl
        << std::indent(indent) << "{" << ::std::endl;
    // print information about the members of the global scope
    print_members_info<MetaObject>(indent);
    std::cout << std::indent(indent) << "}" << ::std::endl;
}

// This version of print_info calls the proper overload based on
// MetaObject's category
template <typename MetaObject>
void print_info(size_t indent)
{
    // use the classification function to get the meta-object
    // category tag and call the proper overload of the print_info
    // function
    print_info<MetaObject>(
        indent,
        categorize_meta_object(MetaObject())
    );
}

MIRROR_NAMESPACE_END

int main(void)
{
    using namespace mirror;
    //
    // reflect the global scope
    typedef MIRRORED_GLOBAL_SCOPE() meta_gs;
    // and print the info about it
    print_info<meta_gs>(0);
    //
    return 0;
}

/* Example of output:
the global scope
{
  namespace std
  {
    class string
    class wstring
    class tm
    template pair
    template tuple
    template allocator
    template equal_to
    template not_equal_to
    template less
    template greater
    template less_equal
    template greater_equal
    template vector
    template list
    template deque
    template map
    template set
  }
  namespace boost
  {
  }
  namespace mirror
  {
  }
  type void
  type bool
  type char
  type unsigned char
  type wchar_t
  type short int
  type int
  type long int
  type unsigned short int
  type unsigned int
  type unsigned long int
  type float
  type double
  type long double
}
*/

Copyright © 2006-2011 Matus Chochlik, University of Zilina, Zilina, Slovakia.
<matus.chochlik -at- fri.uniza.sk>
<chochlik -at -gmail.com>
Documentation generated on Fri Dec 16 2011 by Doxygen (version 1.7.3).
Important note: Although the 'boostified' version of Mirror uses the Boost C++ libraries Coding Guidelines and is implemented inside of the boost namespace, it IS NOT an officially reviewed and accepted Boost library. Mirror is being developed with the intention to be submitted for review for inclusion to the Boost C++ libraries.