deba@1993: /* -*- C++ -*-
deba@1993:  *
deba@1993:  * This file is a part of LEMON, a generic C++ optimization library
deba@1993:  *
deba@1993:  * Copyright (C) 2003-2006
deba@1993:  * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
deba@1993:  * (Egervary Research Group on Combinatorial Optimization, EGRES).
deba@1993:  *
deba@1993:  * Permission to use, modify and distribute this software is granted
deba@1993:  * provided that this copyright notice appears in all copies. For
deba@1993:  * precise terms see the accompanying LICENSE file.
deba@1993:  *
deba@1993:  * This software is provided "AS IS" with no warranty of any kind,
deba@1993:  * express or implied, and with no claim as to its suitability for any
deba@1993:  * purpose.
deba@1993:  *
deba@1993:  */
deba@1993: 
deba@1993: // This file contains a modified version of the enable_if library from BOOST.
deba@1993: // See the appropriate copyright notice below.
deba@1993: 
deba@1993: // Boost enable_if library
deba@1993: 
deba@1993: // Copyright 2003 © The Trustees of Indiana University.
deba@1993: 
deba@1993: // Use, modification, and distribution is subject to the Boost Software
deba@1993: // License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
deba@1993: // http://www.boost.org/LICENSE_1_0.txt)
deba@1993: 
deba@1993: //    Authors: Jaakko Järvi (jajarvi at osl.iu.edu)
deba@1993: //             Jeremiah Willcock (jewillco at osl.iu.edu)
deba@1993: //             Andrew Lumsdaine (lums at osl.iu.edu)
deba@1993: 
deba@1993: 
deba@1993: #ifndef LEMON_BITS_UTILITY_H
deba@1993: #define LEMON_BITS_UTILITY_H
deba@1993: 
deba@1993: ///\file
deba@1993: ///\brief Miscellaneous basic utilities
deba@1993: ///
deba@1993: ///\todo Please rethink the organisation of the basic files like this.
deba@1993: ///E.g. this file might be merged with invalid.h.
deba@1993: 
deba@1993: 
deba@1993: namespace lemon
deba@1993: {
deba@1993: 
deba@1993:   /// Basic type for defining "tags". A "YES" condition for \c enable_if.
deba@1993: 
deba@1993:   /// Basic type for defining "tags". A "YES" condition for \c enable_if.
deba@1993:   ///
deba@1993:   ///\sa False
deba@1993:   ///
deba@1993:   /// \todo This should go to a separate "basic_types.h" (or something)
deba@1993:   /// file.
deba@1993:   struct True {
deba@1993:     ///\e
deba@1993:     static const bool value = true;
deba@1993:   };
deba@1993: 
deba@1993:   /// Basic type for defining "tags". A "NO" condition for \c enable_if.
deba@1993: 
deba@1993:   /// Basic type for defining "tags". A "NO" condition for \c enable_if.
deba@1993:   ///
deba@1993:   ///\sa True
deba@1993:   struct False {
deba@1993:     ///\e
deba@1993:     static const bool value = false;
deba@1993:   };
deba@1993: 
deba@1993: 
deba@1993:   class InvalidType {
deba@1993:   private:
deba@1993:     InvalidType();
deba@1993:   };
deba@2077: 
deba@1993:   template <typename T>
deba@1993:   struct Wrap {
deba@1993:     const T &value;
deba@1993:     Wrap(const T &t) : value(t) {}
deba@1993:   };
deba@1993: 
deba@1993:   /**************** dummy class to avoid ambiguity ****************/
deba@1993: 
deba@1993:   template<int T> struct dummy { dummy(int) {} };
deba@1993: 
deba@1993:   /**************** enable_if from BOOST ****************/
deba@1993:  
deba@1993:   template <bool B, class T = void>
deba@1993:   struct enable_if_c {
deba@1993:     typedef T type;
deba@1993:   };
deba@1993: 
deba@1993:   template <class T>
deba@1993:   struct enable_if_c<false, T> {};
deba@1993: 
deba@1993:   template <class Cond, class T = void> 
deba@1993:   struct enable_if : public enable_if_c<Cond::value, T> {};
deba@1993: 
deba@1993:   template <bool B, class T>
deba@1993:   struct lazy_enable_if_c {
deba@1993:     typedef typename T::type type;
deba@1993:   };
deba@1993: 
deba@1993:   template <class T>
deba@1993:   struct lazy_enable_if_c<false, T> {};
deba@1993: 
deba@1993:   template <class Cond, class T> 
deba@1993:   struct lazy_enable_if : public lazy_enable_if_c<Cond::value, T> {};
deba@1993: 
deba@1993: 
deba@1993:   template <bool B, class T = void>
deba@1993:   struct disable_if_c {
deba@1993:     typedef T type;
deba@1993:   };
deba@1993: 
deba@1993:   template <class T>
deba@1993:   struct disable_if_c<true, T> {};
deba@1993: 
deba@1993:   template <class Cond, class T = void> 
deba@1993:   struct disable_if : public disable_if_c<Cond::value, T> {};
deba@1993: 
deba@1993:   template <bool B, class T>
deba@1993:   struct lazy_disable_if_c {
deba@1993:     typedef typename T::type type;
deba@1993:   };
deba@1993: 
deba@1993:   template <class T>
deba@1993:   struct lazy_disable_if_c<true, T> {};
deba@1993: 
deba@1993:   template <class Cond, class T> 
deba@1993:   struct lazy_disable_if : public lazy_disable_if_c<Cond::value, T> {};
deba@1993: 
deba@1993: } // namespace lemon
deba@1993: 
deba@1993: #endif