Mirror reflection library - Lagoon run-time layer 0.5.13

lagoon/polymorph_factory.hpp

Go to the documentation of this file.
00001 
00011 #ifndef LAGOON_POLYMORPH_FACTORY_1011291729_HPP
00012 #define LAGOON_POLYMORPH_FACTORY_1011291729_HPP
00013 
00014 #include <lagoon/lagoon_fwd.hpp>
00015 #include <lagoon/utils.hpp>
00016 #include <lagoon/auxiliary/range_maker.hpp>
00017 #include <mirror/utils/polymorph_factory.hpp>
00018 
00019 #if LAGOON_FACT_WITH_CREATE
00020 #include <boost/any.hpp>
00021 #endif
00022 
00023 #include <vector>
00024 
00025 LAGOON_NAMESPACE_BEGIN
00026 
00037 // TODO: add a compile time switch between this and a real range
00038 // of meta-objects representing the context of the factory
00039 struct polymorph_factory_context
00040 {
00041 private:
00042     // the meta-object interface used by the context
00043     typedef meta_named_scoped_object mo_interface;
00044     // holder of the composite of meta-objects in the context
00045     struct item_list_holder
00046     {
00047         // the composite of context meta-object
00048         std::vector<shared<mo_interface> > item_list;
00049 
00050         template <class Context>
00051         item_list_holder(Context)
00052         {
00053             mirror::mp::for_each<Context>
00054             (aux::range_maker<mo_interface>(item_list));
00055         }
00056     } holder;
00057 public:
00058     template <class Context>
00059     polymorph_factory_context(Context context)
00060      : holder(context)
00061     { }
00062 
00063     inline range<mo_interface> all(void) const
00064     {
00065         return range<mo_interface>(
00066             holder.item_list.begin(),
00067             holder.item_list.end()
00068         );
00069     }
00070 };
00071 
00073 
00079 struct polymorph_factory_manager
00080 {
00081     virtual ~polymorph_factory_manager(void)
00082     { }
00083 
00084     virtual raw_ptr data(void)
00085     {
00086         return raw_ptr();
00087     }
00088 
00089     virtual raw_ptr add_constructor(
00090         raw_ptr data,
00091         const shared<meta_constructor>& constructor,
00092         const polymorph_factory_context& context,
00093         bool backward_iteration
00094     )
00095     {
00096         return raw_ptr();
00097     }
00098 
00099     virtual void finish(raw_ptr data)
00100     { }
00101 
00102     virtual int index(void) = 0;
00103 };
00104 
00106 
00111 struct polymorph_factory_composite
00112 {
00113     virtual ~polymorph_factory_composite(void)
00114     { }
00115 
00116     virtual raw_ptr data(void)
00117     {
00118         return raw_ptr();
00119     }
00120 
00121     virtual void finish(raw_ptr data)
00122     { }
00123 
00124     virtual void on_create(void)
00125     { }
00126 };
00127 
00129 
00134 struct polymorph_factory_arrayer
00135 {
00136     virtual ~polymorph_factory_arrayer(void)
00137     { }
00138 
00139     virtual raw_ptr data(void)
00140     {
00141         return raw_ptr();
00142     }
00143 
00144     virtual void finish(raw_ptr data)
00145     { }
00146 
00148     struct element_producer
00149     {
00150         virtual ~element_producer(void)
00151         { }
00152 
00154         virtual void reset(void) = 0;
00155 
00157         virtual void make_next(void) = 0;
00158     };
00159 
00161     virtual void assign_producer(element_producer& producer)
00162     { }
00163 
00165 
00168     virtual void create(element_producer& producer) = 0;
00169 };
00170 
00172 
00179 template <typename Product>
00180 struct polymorph_factory_manufacturer
00181 {
00182     virtual ~polymorph_factory_manufacturer(void)
00183     { }
00184 
00185     virtual void finish(raw_ptr parent_data)
00186     { }
00187 
00188     virtual Product create(void) = 0;
00189 };
00190 
00192 
00197 struct polymorph_factory_suppliers
00198 {
00199     virtual ~polymorph_factory_suppliers(void)
00200     { }
00201 
00202     virtual void finish(raw_ptr parent_data)
00203     { }
00204 
00206 
00208     virtual raw_ptr get(void) = 0;
00209 };
00210 
00212 
00219 struct polymorph_factory_enumerator
00220 {
00221     virtual ~polymorph_factory_enumerator(void)
00222     { }
00223 
00224     virtual void finish(raw_ptr parent_data)
00225     { }
00226 
00227     virtual int create(void) = 0;
00228 };
00229 
00230 //  Builder's helper subinterface for instantiating manufacturers of a Product
00231 /*  The individual builder units are composed together based on the
00232  *  native types type range by the means of polymorph_factory_builder_units
00233  *
00234  *  @ingroup lagoon_polymorphic_factories
00235  */
00236 template <typename Product>
00237 class polymorph_factory_builder_unit
00238 {
00239 protected:
00240     virtual ~polymorph_factory_builder_unit(void)
00241     { }
00242 public:
00243     virtual std::shared_ptr<polymorph_factory_manufacturer<Product> >
00244     make_manufacturer(
00245         raw_ptr parent_data,
00246         const shared<meta_parameter>& ctr_param,
00247         const polymorph_factory_context& context
00248     ) = 0;
00249 };
00250 
00251 //  Forward declaration of the builder unit composer
00252 template <template <class> class Unit, class Range>
00253 struct polymorph_factory_builder_units;
00254 
00255 //  Implementation of builder unit composer
00256 template <template <class> class Unit, typename ... P>
00257 class polymorph_factory_builder_units<Unit, mirror::mp::range<P...> >
00258  : virtual public Unit<P>...
00259 {
00260 private:
00261     template <class Product>
00262     Unit<Product>* this_unit(void)
00263     {
00264         return this;
00265     }
00266 public:
00267     template <typename Product>
00268     inline std::shared_ptr<polymorph_factory_manufacturer<Product> >
00269     make_manufacturer(
00270         raw_ptr parent_data,
00271         const shared<meta_parameter>& ctr_param,
00272         const polymorph_factory_context& context,
00273         mirror::mp::identity<Product>
00274     )
00275     {
00276         return this_unit<Product>()->make_manufacturer(
00277             parent_data,
00278             ctr_param,
00279             context
00280         );
00281     }
00282 };
00283 
00285 
00297 struct polymorph_factory_builder
00298  : public polymorph_factory_builder_units<
00299     polymorph_factory_builder_unit,
00300     mirror::util_native_types
00301 >
00302 {
00303     virtual ~polymorph_factory_builder(void)
00304     { }
00305 
00306     virtual std::shared_ptr<polymorph_factory_manager>
00307     make_manager(
00308         raw_ptr parent_data,
00309         const polymorph_factory_context& context
00310     ) = 0;
00311 
00312     virtual std::shared_ptr<polymorph_factory_composite>
00313     make_composite(
00314         raw_ptr parent_data,
00315         const shared<meta_parameter>& func_param,
00316         const polymorph_factory_context& context
00317     ) = 0;
00318 
00319     virtual std::shared_ptr<polymorph_factory_composite>
00320     make_composite(
00321         raw_ptr parent_data,
00322         const shared<meta_type>& product,
00323         const polymorph_factory_context& context
00324     ) = 0;
00325 
00326     virtual std::shared_ptr<polymorph_factory_arrayer>
00327     make_arrayer(
00328         raw_ptr parent_data,
00329         const shared<meta_type>& element,
00330         const polymorph_factory_context& context
00331     ) = 0;
00332 
00333     virtual std::shared_ptr<polymorph_factory_suppliers>
00334     make_suppliers(
00335         raw_ptr parent_data,
00336         const shared<meta_parameter>& ctr_param,
00337         const polymorph_factory_context& context
00338     ) = 0;
00339 
00340     virtual std::shared_ptr<polymorph_factory_enumerator>
00341     make_enumerator(
00342         raw_ptr parent_data,
00343         const shared<meta_parameter>& ctr_param,
00344         const polymorph_factory_context& context
00345     ) = 0;
00346 };
00347 
00348 template <
00349     template <class> class ConcreteUnit,
00350     class Range
00351 > class concrete_polymorph_factory_bldr_hlpr;
00352 
00353 template <
00354     template <class> class ConcreteUnit,
00355     typename T,
00356     typename ... P
00357 > class concrete_polymorph_factory_bldr_hlpr<
00358     ConcreteUnit,
00359     mirror::mp::range<T, P...>
00360 >: public ConcreteUnit<T>
00361  , public concrete_polymorph_factory_bldr_hlpr<
00362     ConcreteUnit,
00363     mirror::mp::range<P...>
00364 >{ };
00365 
00366 template <
00367     template <class> class ConcreteUnit
00368 > class concrete_polymorph_factory_bldr_hlpr<
00369     ConcreteUnit,
00370     mirror::mp::range<>
00371 >: public polymorph_factory_builder
00372 { };
00373 
00374 template <template <class> class BaseUnit>
00375 struct concrete_polymorph_factory_builder_unit
00376 {
00377 public:
00378     template <class Product>
00379     class impl
00380      : virtual public polymorph_factory_builder_unit<Product>
00381      , public BaseUnit<Product>
00382     {
00383     private:
00384         BaseUnit<Product>& base_unit(void)
00385         {
00386             return *this;
00387         }
00388     public:
00389         std::shared_ptr<polymorph_factory_manufacturer<Product> >
00390         make_manufacturer(
00391             raw_ptr parent_data,
00392             const shared<meta_parameter>& param,
00393             const polymorph_factory_context& context
00394         )
00395         {
00396             return std::shared_ptr<
00397                 polymorph_factory_manufacturer<Product>
00398             >(base_unit().make_manufacturer(
00399                 parent_data,
00400                 param,
00401                 context
00402             ));
00403         }
00404     };
00405 };
00406 
00407 template <class BaseBuilder, template <class> class BaseUnit>
00408 class concrete_polymorph_factory_builder
00409  : public BaseBuilder
00410  , public concrete_polymorph_factory_bldr_hlpr<
00411     concrete_polymorph_factory_builder_unit<BaseUnit>::template impl,
00412     mirror::util_native_types
00413 >
00414 {
00415 private:
00416     BaseBuilder& base_builder(void)
00417     {
00418         return *this;
00419     }
00420 public:
00421     std::shared_ptr<polymorph_factory_manager>
00422     make_manager(
00423         raw_ptr parent_data,
00424         const polymorph_factory_context& context
00425     )
00426     {
00427         return std::shared_ptr<polymorph_factory_manager>(
00428             base_builder().make_manager(parent_data, context)
00429         );
00430     }
00431 
00432     std::shared_ptr<polymorph_factory_composite>
00433     make_composite(
00434         raw_ptr parent_data,
00435         const shared<meta_type>& product,
00436         const polymorph_factory_context& context
00437     )
00438     {
00439         return std::shared_ptr<polymorph_factory_composite>(
00440             base_builder().make_composite(
00441                 parent_data,
00442                 product,
00443                 context
00444             )
00445         );
00446     }
00447 
00448     std::shared_ptr<polymorph_factory_composite>
00449     make_composite(
00450         raw_ptr parent_data,
00451         const shared<meta_parameter>& param,
00452         const polymorph_factory_context& context
00453     )
00454     {
00455         return std::shared_ptr<polymorph_factory_composite>(
00456             base_builder().make_composite(
00457                 parent_data,
00458                 param,
00459                 context
00460             )
00461         );
00462     }
00463 
00464     std::shared_ptr<polymorph_factory_arrayer>
00465     make_arrayer(
00466         raw_ptr parent_data,
00467         const shared<meta_type>& element,
00468         const polymorph_factory_context& context
00469     )
00470     {
00471         return std::shared_ptr<polymorph_factory_arrayer>(
00472             base_builder().make_arrayer(
00473                 parent_data,
00474                 element,
00475                 context
00476             )
00477         );
00478     }
00479 
00480     std::shared_ptr<polymorph_factory_suppliers>
00481     make_suppliers(
00482         raw_ptr parent_data,
00483         const shared<meta_parameter>& param,
00484         const polymorph_factory_context& context
00485     )
00486     {
00487         return std::shared_ptr<polymorph_factory_suppliers>(
00488             base_builder().make_suppliers(
00489                 parent_data,
00490                 param,
00491                 context
00492             )
00493         );
00494     }
00495 
00496     std::shared_ptr<polymorph_factory_enumerator>
00497     make_enumerator(
00498         raw_ptr parent_data,
00499         const shared<meta_parameter>& param,
00500         const polymorph_factory_context& context
00501     )
00502     {
00503         return std::shared_ptr<polymorph_factory_enumerator>(
00504             base_builder().make_enumerator(
00505                 parent_data,
00506                 param,
00507                 context
00508             )
00509         );
00510     }
00511 
00512 };
00513 
00515 
00522 struct polymorph_factory
00523 {
00524     virtual ~polymorph_factory(void)
00525     { }
00526 
00528 
00532     virtual raw_ptr new_(void) = 0;
00533 
00534 #if LAGOON_FACT_WITH_CREATE || \
00535     MIRROR_DOCUMENTATION_ONLY
00536 
00537 
00544     virtual boost::any create(void) = 0;
00545 #endif
00546 };
00547 
00548 LAGOON_NAMESPACE_END
00549 
00550 #endif // include guard
00551 

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.