Boost logo

Boost Users :

Subject: Re: [Boost-users] [Fusion] Associate arbitrary compile/runtime annotations with members of fusion sequence
From: Kozlov Taras (kozlov.taras_at_[hidden])
Date: 2013-02-23 18:38:51


17.02.2013 2:36, Joel de Guzman wrote:
> On 2/16/13 5:51 AM, Kozlov Taras wrote:
>> Started to use Boost.Fusion in my project I quick realized that it
>> would be very
>> convenient if fusion adapt macroses like BOOST_FUSION_DEFINE_STRUCT
>> would give ability to
>> associate additional information with members.
>> Second problem is that BOOST_FUSION_DEFINE_STRUCT and such doesn`t
>> support inheritance.
>>
>> So I did a small utility library that allow to define fusion sequences
>> with arbitrary list
>> of annotations associated with each member, and want to share it with
>> community :)
>>
>> http://tarasko.github.com/cppan/
>>
>> Will appreciate for any comments
>
> Very interesting. I think that the extension to support inheritance is
> nice. I would definitely love to see such adapters in Fusion. I'd
> love to see both intrusive and non-intrusive adapters though, not just
> the intrusive ones. As for the "annotations", well, that's a nice touch,
> but I think that's best done by associating members with keys. If you
> have a key, MK, for a member of type T, then you can write non-intrusive
> traits such as:
>
> traits::has_hash<T, MK>
>
> the biggest advantage with this approach is that it is open ended. You
> can add as much introspection 'traits' as you want anytime.
>
> Regards,

Hi Joel,
Thanks for ideas on "annotations". I`m going to apply them, but first I
want to clearify some points, fix me were I`m wrong

1. Having structure A defined like following
struct A
{
     CPPAN_DECLARE_AND_ANNOTATE(
         ((int, int_field_,
             ((int_annotation, 42))
             ((string_annotation, "Hello world"))
         ))
         ((std::string, string_field_,
             ((no_serialization, std::true_type()))
             ((no_hash, std::true_type()))
         ))
     )
};

you want to see it as fusion Associative Sequence, where int_field_ will
have key type, something like A::key_int_field_, right?

2. Iterator for A struct will sequentally dereference to
fusion::pair<key_int_field_, int>
fusion::pair<key_string_field_, std::string>

3. Members can be accessed directly or using fusion::at_key
A a;
at_key<key_int_field_>(a);

4. I guess the most straightforward way to assign runtime values for
annotations is to make them as members in key type.
struct A
{
     struct key_int_field_
     {
         int int_annotation;
         const char* string_annotation;

         key_int_field_() :
             int_annotation(42), string_annotation("Hello world") {}
     };
...
};
Do you have any objections here?

5.
CPPAN_DEFINE_MEMBER_DETECTOR(no_hash);
defines metafunction that will accept key type.

     has_no_hash<A::key_int_field_>

This metafunction can be specialized for any other key type. Is it ok?
The question arise because you wrote

        traits::has_no_hash<T, MK> where

T - is member type
MK - is key type

I haven`t got the idea behind passing member type here, from my point of
view, passing key type is sufficient. Could you explain it?

6. Regarding non-intrusive version. This should be something like

     CPPAN_ADAPT_STRUCT_WITH_BASE(
         A,
         (base_type1)(base_type2)
         ((int, int_field_,
             ((int_annotation, 42))
             ((string_annotation, "Hello world"))
         ))
         ((std::string, string_field_,
             ((no_serialization, std::true_type()))
             ((no_hash, std::true_type()))
         ))
     )

Right?
One thing bother me here, is it ok to define key type in namespace scope
by CPPAN_ADAPT_STRUCT_WITH_BASE?

BOOST_FUSION_ADAPT_ASSOC_STRUCT and BOOST_FUSION_DEFINE_ASSOC_STRUCT go
another way, it just takes structure name as parameter and left user to
define key types itself. But I feel that when dealing with annotations
this is not so convenient as inline annotations description in
CPPAN_ADAPT_STRUCT_WITH_BASE.

7. Generic question about adapt macroses in fusion.

I used BOOST_MPL_HAS_XXX_TRAIT_NAMED_DEF to define has_annotations
metafunction that determine if type members were defined with
CPPAN_DECLARE_AND_ANNOTATE.
Then I wrote fusion extension which enables for arbitraty type if
has_annotations<T> is true.

This approach allowed to move CPPAN_DECLARE_AND_ANNOTATE inside of
struct definition.

Can BOOST_FUSION_DEFINE_STRUCT be reimplemented in that way? This will
allow to get rid of namespaces sequence and struct_name parameters. I
believe this will also make needless _TPL and _INLINE versions of
BOOST_FUSION_DEFINE_STRUCT macroses.

Are there any compiler portability or design problems with such approach.

Thanks in advance.


Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net