source: NonGTP/Boost/boost/parameter/keyword.hpp @ 857

Revision 857, 4.0 KB checked in by igarcia, 18 years ago (diff)
Line 
1// Copyright Daniel Wallin, David Abrahams 2005. Use, modification and
2// distribution is subject to the Boost Software License, Version 1.0. (See
3// accompanying file LICENSE_1_0.txt or copy at
4// http://www.boost.org/LICENSE_1_0.txt)
5
6#ifndef KEYWORD_050328_HPP
7#define KEYWORD_050328_HPP
8
9#include <boost/parameter/aux_/unwrap_cv_reference.hpp>
10#include <boost/parameter/aux_/tag.hpp>
11#include <boost/parameter/aux_/default.hpp>
12#include <boost/noncopyable.hpp>
13
14namespace boost { namespace parameter {
15
16// Instances of unique specializations of keyword<...> serve to
17// associate arguments with parameter names.  For example:
18//
19//    struct rate_;           // parameter names
20//    struct skew_;
21//    namespace
22//    {
23//      keyword<rate_> rate;  // keywords
24//      keyword<skew_> skew;
25//    }
26//
27//    ...
28//
29//    f(rate = 1, skew = 2.4);
30//
31template <class Tag>
32struct keyword : noncopyable
33{
34    template <class T>
35    typename aux::tag<Tag, T>::type
36    operator=(T& x) const
37    {
38        typedef typename aux::tag<Tag, T>::type result;
39        return result(x);
40    }
41
42    template <class Default>
43    aux::default_<Tag, Default>
44    operator|(Default& default_) const
45    {
46        return aux::default_<Tag, Default>(default_);
47    }
48
49    template <class Default>
50    aux::lazy_default<Tag, Default>
51    operator||(Default& default_) const
52    {
53        return aux::lazy_default<Tag, Default>(default_);
54    }
55
56#if !BOOST_WORKAROUND(BOOST_MSVC, < 1300)  // avoid partial ordering bugs
57    template <class T>
58    typename aux::tag<Tag, T const>::type
59    operator=(T const& x) const
60    {
61        typedef typename aux::tag<Tag, T const>::type result;
62        return result(x);
63    }
64#endif
65
66#if !BOOST_WORKAROUND(BOOST_MSVC, < 1300)  // avoid partial ordering bugs
67    template <class Default>
68    aux::default_<Tag, const Default>
69    operator|(const Default& default_) const
70#if BOOST_WORKAROUND(BOOST_MSVC, == 1300)
71        volatile
72#endif
73    {
74        return aux::default_<Tag, const Default>(default_);
75    }
76
77    template <class Default>
78    aux::lazy_default<Tag, Default>
79    operator||(Default const& default_) const
80#if BOOST_WORKAROUND(BOOST_MSVC, == 1300)
81        volatile
82#endif
83    {
84        return aux::lazy_default<Tag, Default>(default_);
85    }
86#endif
87
88 public: // Insurance against ODR violations
89   
90    // People will need to define these keywords in header files.  To
91    // prevent ODR violations, it's important that the keyword used in
92    // every instantiation of a function template is the same object.
93    // We provide a reference to a common instance of each keyword
94    // object and prevent construction by users.
95   
96    static keyword<Tag>& get()
97    {
98        static keyword<Tag> result;
99        return result;
100    }
101   
102 private:
103    keyword() {}
104};
105
106// Reduces boilerplate required to declare and initialize keywords
107// without violating ODR.  Declares a keyword tag type with the given
108// name in namespace tag_namespace, and declares and initializes a
109// reference in an anonymous namespace to a singleton instance of that
110// type.
111
112#if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
113
114# define BOOST_PARAMETER_KEYWORD(tag_namespace,name)                \
115    namespace tag_namespace { struct name; }                        \
116    static ::boost::parameter::keyword<tag_namespace::name>& name   \
117       = ::boost::parameter::keyword<tag_namespace::name>::get();
118
119#else
120
121#define BOOST_PARAMETER_KEYWORD(tag_namespace,name)                 \
122    namespace tag_namespace { struct name; }                        \
123    namespace                                                       \
124    {                                                               \
125       ::boost::parameter::keyword<tag_namespace::name>& name       \
126       = ::boost::parameter::keyword<tag_namespace::name>::get();   \
127    }
128
129#endif
130
131}} // namespace boost::parameter
132
133#endif // KEYWORD_050328_HPP
134
Note: See TracBrowser for help on using the repository browser.