williamr@4: 
williamr@4: #ifndef BOOST_MPL_IF_HPP_INCLUDED
williamr@4: #define BOOST_MPL_IF_HPP_INCLUDED
williamr@4: 
williamr@4: // Copyright Aleksey Gurtovoy 2000-2004
williamr@4: //
williamr@4: // Distributed under the Boost Software License, Version 1.0. 
williamr@4: // (See accompanying file LICENSE_1_0.txt or copy at 
williamr@4: // http://www.boost.org/LICENSE_1_0.txt)
williamr@4: //
williamr@4: // See http://www.boost.org/libs/mpl for documentation.
williamr@4: 
williamr@4: // $Source: /cvsroot/boost/boost/boost/mpl/if.hpp,v $
williamr@4: // $Date: 2004/09/07 08:51:31 $
williamr@4: // $Revision: 1.25 $
williamr@4: 
williamr@4: #include <boost/mpl/aux_/value_wknd.hpp>
williamr@4: #include <boost/mpl/aux_/static_cast.hpp>
williamr@4: #include <boost/mpl/aux_/na_spec.hpp>
williamr@4: #include <boost/mpl/aux_/lambda_support.hpp>
williamr@4: #include <boost/mpl/aux_/config/integral.hpp>
williamr@4: #include <boost/mpl/aux_/config/ctps.hpp>
williamr@4: #include <boost/mpl/aux_/config/workaround.hpp>
williamr@4: 
williamr@4: namespace boost { namespace mpl {
williamr@4: 
williamr@4: #if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION)
williamr@4: 
williamr@4: template<
williamr@4:       bool C
williamr@4:     , typename T1
williamr@4:     , typename T2
williamr@4:     >
williamr@4: struct if_c
williamr@4: {
williamr@4:     typedef T1 type;
williamr@4: };
williamr@4: 
williamr@4: template<
williamr@4:       typename T1
williamr@4:     , typename T2
williamr@4:     >
williamr@4: struct if_c<false,T1,T2>
williamr@4: {
williamr@4:     typedef T2 type;
williamr@4: };
williamr@4: 
williamr@4: // agurt, 05/sep/04: nondescriptive parameter names for the sake of DigitalMars
williamr@4: // (and possibly MWCW < 8.0); see http://article.gmane.org/gmane.comp.lib.boost.devel/108959
williamr@4: template<
williamr@4:       typename BOOST_MPL_AUX_NA_PARAM(T1)
williamr@4:     , typename BOOST_MPL_AUX_NA_PARAM(T2)
williamr@4:     , typename BOOST_MPL_AUX_NA_PARAM(T3)
williamr@4:     >
williamr@4: struct if_
williamr@4: {
williamr@4:  private:
williamr@4:     // agurt, 02/jan/03: two-step 'type' definition for the sake of aCC 
williamr@4:     typedef if_c<
williamr@4: #if defined(BOOST_MPL_CFG_BCC_INTEGRAL_CONSTANTS)
williamr@4:           BOOST_MPL_AUX_VALUE_WKND(T1)::value
williamr@4: #else
williamr@4:           BOOST_MPL_AUX_STATIC_CAST(bool, BOOST_MPL_AUX_VALUE_WKND(T1)::value)
williamr@4: #endif
williamr@4:         , T2
williamr@4:         , T3
williamr@4:         > almost_type_;
williamr@4:  
williamr@4:  public:
williamr@4:     typedef typename almost_type_::type type;
williamr@4:     
williamr@4:     BOOST_MPL_AUX_LAMBDA_SUPPORT(3,if_,(T1,T2,T3))
williamr@4: };
williamr@4: 
williamr@4: #else
williamr@4: 
williamr@4: // no partial class template specialization
williamr@4: 
williamr@4: namespace aux {
williamr@4: 
williamr@4: template< bool C >
williamr@4: struct if_impl
williamr@4: {
williamr@4:     template< typename T1, typename T2 > struct result_
williamr@4:     {
williamr@4:         typedef T1 type;
williamr@4:     };
williamr@4: };
williamr@4: 
williamr@4: template<>
williamr@4: struct if_impl<false>
williamr@4: {
williamr@4:     template< typename T1, typename T2 > struct result_
williamr@4:     { 
williamr@4:         typedef T2 type;
williamr@4:     };
williamr@4: };
williamr@4: 
williamr@4: } // namespace aux
williamr@4: 
williamr@4: template<
williamr@4:       bool C_
williamr@4:     , typename T1
williamr@4:     , typename T2
williamr@4:     >
williamr@4: struct if_c
williamr@4: {
williamr@4:     typedef typename aux::if_impl< C_ >
williamr@4:         ::template result_<T1,T2>::type type;
williamr@4: };
williamr@4: 
williamr@4: // (almost) copy & paste in order to save one more 
williamr@4: // recursively nested template instantiation to user
williamr@4: template<
williamr@4:       typename BOOST_MPL_AUX_NA_PARAM(C_)
williamr@4:     , typename BOOST_MPL_AUX_NA_PARAM(T1)
williamr@4:     , typename BOOST_MPL_AUX_NA_PARAM(T2)
williamr@4:     >
williamr@4: struct if_
williamr@4: {
williamr@4:     enum { msvc_wknd_ = BOOST_MPL_AUX_MSVC_VALUE_WKND(C_)::value };
williamr@4: 
williamr@4:     typedef typename aux::if_impl< BOOST_MPL_AUX_STATIC_CAST(bool, msvc_wknd_) >
williamr@4:         ::template result_<T1,T2>::type type;
williamr@4: 
williamr@4:     BOOST_MPL_AUX_LAMBDA_SUPPORT(3,if_,(C_,T1,T2))
williamr@4: };
williamr@4: 
williamr@4: #endif // BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION
williamr@4: 
williamr@4: BOOST_MPL_AUX_NA_SPEC(3, if_)
williamr@4: 
williamr@4: }}
williamr@4: 
williamr@4: #endif // BOOST_MPL_IF_HPP_INCLUDED