1 // Boost.Function library
3 // Copyright (C) 2001, 2002 Doug Gregor (gregod@cs.rpi.edu)
5 // Permission to copy, use, sell and distribute this software is granted
6 // provided this copyright notice appears in all copies.
7 // Permission to modify the code and to distribute modified code is granted
8 // provided this copyright notice appears in all copies, and a notice
9 // that the code was modified is included with the copyright notice.
11 // This software is provided "as is" without express or implied warranty,
12 // and with no claim as to its suitability for any purpose.
14 // For more information, see http://www.boost.org
16 // William Kempf, Jesse Jones and Karl Nelson were all very helpful in the
17 // design of this library.
19 #ifndef BOOST_FUNCTION_HPP
20 #define BOOST_FUNCTION_HPP
22 #if defined(__sgi) && defined(_COMPILER_VERSION) && _COMPILER_VERSION <= 730
23 // Work around a compiler bug.
24 // boost::python::detail::function has to be seen by the compiler before the
25 // boost::function class template.
26 namespace boost { namespace python { namespace detail {
31 #include <boost/function/function_base.hpp>
32 #include <boost/type_traits/function_traits.hpp>
33 #include <boost/type_traits/same_traits.hpp>
34 #include <boost/type_traits/transform_traits.hpp>
35 #include <boost/type_traits/ice.hpp>
36 #include <boost/function/function0.hpp>
37 #include <boost/function/function1.hpp>
38 #include <boost/function/function2.hpp>
39 #include <boost/function/function3.hpp>
40 #include <boost/function/function4.hpp>
41 #include <boost/function/function5.hpp>
42 #include <boost/function/function6.hpp>
43 #include <boost/function/function7.hpp>
44 #include <boost/function/function8.hpp>
45 #include <boost/function/function9.hpp>
46 #include <boost/function/function10.hpp>
48 // Don't compile any of this code if we've asked not to include the deprecated
49 // syntax and we don't have partial specialization, because none of this code
51 #if !defined (BOOST_FUNCTION_NO_DEPRECATED) || !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION)
56 // Choose the appropriate underlying implementation
57 template<int Args> struct real_get_function_impl {};
60 struct real_get_function_impl<0>
74 #ifndef BOOST_FUNCTION_NO_DEPRECATED
77 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
83 #ifndef BOOST_FUNCTION_NO_DEPRECATED
85 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
91 struct real_get_function_impl<1>
105 #ifndef BOOST_FUNCTION_NO_DEPRECATED
108 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
113 typedef function1<R, T1,
114 #ifndef BOOST_FUNCTION_NO_DEPRECATED
116 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
122 struct real_get_function_impl<2>
136 #ifndef BOOST_FUNCTION_NO_DEPRECATED
139 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
144 typedef function2<R, T1, T2,
145 #ifndef BOOST_FUNCTION_NO_DEPRECATED
147 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
153 struct real_get_function_impl<3>
167 #ifndef BOOST_FUNCTION_NO_DEPRECATED
170 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
175 typedef function3<R, T1, T2, T3,
176 #ifndef BOOST_FUNCTION_NO_DEPRECATED
178 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
184 struct real_get_function_impl<4>
198 #ifndef BOOST_FUNCTION_NO_DEPRECATED
201 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
206 typedef function4<R, T1, T2, T3, T4,
207 #ifndef BOOST_FUNCTION_NO_DEPRECATED
209 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
215 struct real_get_function_impl<5>
229 #ifndef BOOST_FUNCTION_NO_DEPRECATED
232 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
237 typedef function5<R, T1, T2, T3, T4, T5,
238 #ifndef BOOST_FUNCTION_NO_DEPRECATED
240 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
247 struct real_get_function_impl<6>
261 #ifndef BOOST_FUNCTION_NO_DEPRECATED
264 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
269 typedef function6<R, T1, T2, T3, T4, T5, T6,
270 #ifndef BOOST_FUNCTION_NO_DEPRECATED
272 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
279 struct real_get_function_impl<7>
293 #ifndef BOOST_FUNCTION_NO_DEPRECATED
296 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
301 typedef function7<R, T1, T2, T3, T4, T5, T6, T7,
302 #ifndef BOOST_FUNCTION_NO_DEPRECATED
304 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
310 struct real_get_function_impl<8>
324 #ifndef BOOST_FUNCTION_NO_DEPRECATED
327 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
332 typedef function8<R, T1, T2, T3, T4, T5, T6, T7, T8,
333 #ifndef BOOST_FUNCTION_NO_DEPRECATED
335 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
341 struct real_get_function_impl<9>
355 #ifndef BOOST_FUNCTION_NO_DEPRECATED
358 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
363 typedef function9<R, T1, T2, T3, T4, T5, T6, T7, T8, T9,
364 #ifndef BOOST_FUNCTION_NO_DEPRECATED
366 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
372 struct real_get_function_impl<10>
386 #ifndef BOOST_FUNCTION_NO_DEPRECATED
389 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
394 typedef function10<R, T1, T2, T3, T4, T5, T6, T7, T8, T9, T10,
395 #ifndef BOOST_FUNCTION_NO_DEPRECATED
397 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
402 #ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION
403 template<bool GetIt, typename Traits>
406 typedef unusable type;
409 template<typename Traits>
410 struct get_arg1_type<true, Traits>
412 typedef typename Traits::arg1_type type;
415 template<bool GetIt, typename Traits>
418 typedef unusable type;
421 template<typename Traits>
422 struct get_arg2_type<true, Traits>
424 typedef typename Traits::arg2_type type;
427 template<bool GetIt, typename Traits>
430 typedef unusable type;
433 template<typename Traits>
434 struct get_arg3_type<true, Traits>
436 typedef typename Traits::arg3_type type;
439 template<bool GetIt, typename Traits>
442 typedef unusable type;
445 template<typename Traits>
446 struct get_arg4_type<true, Traits>
448 typedef typename Traits::arg4_type type;
451 template<bool GetIt, typename Traits>
454 typedef unusable type;
457 template<typename Traits>
458 struct get_arg5_type<true, Traits>
460 typedef typename Traits::arg5_type type;
463 template<bool GetIt, typename Traits>
466 typedef unusable type;
469 template<typename Traits>
470 struct get_arg6_type<true, Traits>
472 typedef typename Traits::arg6_type type;
475 template<bool GetIt, typename Traits>
478 typedef unusable type;
481 template<typename Traits>
482 struct get_arg7_type<true, Traits>
484 typedef typename Traits::arg7_type type;
487 template<bool GetIt, typename Traits>
490 typedef unusable type;
493 template<typename Traits>
494 struct get_arg8_type<true, Traits>
496 typedef typename Traits::arg8_type type;
499 template<bool GetIt, typename Traits>
502 typedef unusable type;
505 template<typename Traits>
506 struct get_arg9_type<true, Traits>
508 typedef typename Traits::arg9_type type;
511 template<bool GetIt, typename Traits>
512 struct get_arg10_type
514 typedef unusable type;
517 template<typename Traits>
518 struct get_arg10_type<true, Traits>
520 typedef typename Traits::arg10_type type;
523 template<int X, int Y>
526 BOOST_STATIC_CONSTANT(bool, value = (X >= Y));
529 template<bool IsFunction,
541 #ifndef BOOST_FUNCTION_NO_DEPRECATED
544 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
545 typename InAllocator>
546 struct maybe_decode_function_args
548 typedef function_traits<InR> traits;
550 typedef typename traits::result_type R;
551 typedef typename get_arg1_type<(gte<(traits::arity), 1>::value),
553 typedef typename get_arg2_type<(gte<(traits::arity), 2>::value),
555 typedef typename get_arg3_type<(gte<(traits::arity), 3>::value),
557 typedef typename get_arg4_type<(gte<(traits::arity), 4>::value),
559 typedef typename get_arg5_type<(gte<(traits::arity), 5>::value),
561 typedef typename get_arg6_type<(gte<(traits::arity), 6>::value),
563 typedef typename get_arg7_type<(gte<(traits::arity), 7>::value),
565 typedef typename get_arg8_type<(gte<(traits::arity), 8>::value),
567 typedef typename get_arg9_type<(gte<(traits::arity), 9>::value),
569 typedef typename get_arg10_type<(gte<(traits::arity), 10>::value),
572 #ifndef BOOST_FUNCTION_NO_DEPRECATED
573 typedef typename ct_if<(is_same<InT1, unusable>::value),
574 empty_function_policy,
576 typedef typename ct_if<(is_same<InT2, unusable>::value),
577 empty_function_mixin,
579 typedef typename ct_if<(is_same<InT3, unusable>::value),
580 std::allocator<function_base>,
581 InT3>::type Allocator;
583 typedef typename ct_if<(is_same<InT1, unusable>::value),
584 std::allocator<function_base>,
585 InT1>::type Allocator;
586 #endif // BOOST_FUNCTION_NO_DEPRECATED
589 #ifndef BOOST_FUNCTION_NO_DEPRECATED
590 template<typename InR,
601 #ifndef BOOST_FUNCTION_NO_DEPRECATED
604 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
605 typename InAllocator>
606 struct maybe_decode_function_args<false, InR, InT1, InT2, InT3, InT4,
607 InT5, InT6, InT7, InT8, InT9, InT10,
608 #ifndef BOOST_FUNCTION_NO_DEPRECATED
610 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
613 // Not a function, so just map the types directly
625 #ifndef BOOST_FUNCTION_NO_DEPRECATED
626 typedef InPolicy Policy;
627 typedef InMixin Mixin;
628 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
629 typedef InAllocator Allocator;
632 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
634 #endif // ndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION
648 typename InPolicy = empty_function_policy,
649 typename InMixin = empty_function_mixin,
650 typename InAllocator = std::allocator<function_base>
652 struct get_function_impl
654 #ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION
655 typedef maybe_decode_function_args<(is_function<InR>::value),
656 InR, InT1, InT2, InT3, InT4, InT5,
657 InT6, InT7, InT8, InT9, InT10,
658 #ifndef BOOST_FUNCTION_NO_DEPRECATED
660 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
661 InAllocator> decoder;
662 typedef typename decoder::R R;
663 typedef typename decoder::T1 T1;
664 typedef typename decoder::T2 T2;
665 typedef typename decoder::T3 T3;
666 typedef typename decoder::T4 T4;
667 typedef typename decoder::T5 T5;
668 typedef typename decoder::T6 T6;
669 typedef typename decoder::T7 T7;
670 typedef typename decoder::T8 T8;
671 typedef typename decoder::T9 T9;
672 typedef typename decoder::T10 T10;
673 #ifndef BOOST_FUNCTION_NO_DEPRECATED
674 typedef typename decoder::Policy Policy;
675 typedef typename decoder::Mixin Mixin;
676 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
677 typedef typename decoder::Allocator Allocator;
690 typedef InPolicy Policy;
691 typedef InMixin Mixin;
692 typedef InAllocator Allocator;
693 #endif // def BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION
695 typedef typename real_get_function_impl<
696 (count_used_args<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>::value)
697 >::template params<R, T1, T2, T3, T4, T5, T6, T7, T8, T9, T10,
698 #ifndef BOOST_FUNCTION_NO_DEPRECATED
700 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
705 #ifndef BOOST_FUNCTION_NO_DEPRECATED
718 typename InMyPolicy = empty_function_policy,
719 typename InMyMixin = empty_function_mixin,
720 typename InMyAllocator = std::allocator<function_base>
722 class function_traits_builder
724 typedef get_function_impl<InR, InT1, InT2, InT3, InT4, InT5, InT6, InT7,
725 InT8, InT9, InT10, InMyPolicy, InMyMixin,
729 typedef typename impl::R MyR;
730 typedef typename impl::T1 MyT1;
731 typedef typename impl::T2 MyT2;
732 typedef typename impl::T3 MyT3;
733 typedef typename impl::T4 MyT4;
734 typedef typename impl::T5 MyT5;
735 typedef typename impl::T6 MyT6;
736 typedef typename impl::T7 MyT7;
737 typedef typename impl::T8 MyT8;
738 typedef typename impl::T9 MyT9;
739 typedef typename impl::T10 MyT10;
740 typedef typename impl::Policy MyPolicy;
741 typedef typename impl::Mixin MyMixin;
742 typedef typename impl::Allocator MyAllocator;
745 typedef typename impl::type type;
746 typedef MyPolicy policy_type;
747 typedef MyMixin mixin_type;
748 typedef MyAllocator allocator_type;
750 #ifndef BOOST_NO_DEPENDENT_NESTED_DERIVATIONS
751 template<typename Policy>
753 public function_traits_builder<MyR, MyT1, MyT2, MyT3, MyT4, MyT5, MyT6,
754 MyT7, MyT8, MyT9, MyT10, Policy,
755 mixin_type, allocator_type> {};
757 template<typename Mixin>
759 public function_traits_builder<MyR, MyT1, MyT2, MyT3, MyT4, MyT5, MyT6,
760 MyT7, MyT8, MyT9, MyT10, policy_type,
761 Mixin, allocator_type> {};
763 template<typename Allocator>
765 public function_traits_builder<MyR, MyT1, MyT2, MyT3, MyT4, MyT5, MyT6,
766 MyT7, MyT8, MyT9, MyT10, policy_type,
767 mixin_type, Allocator> {};
769 template<typename Policy>
772 typedef typename function_traits_builder<MyR, MyT1, MyT2, MyT3, MyT4,
773 MyT5, MyT6, MyT7, MyT8, MyT9,
774 MyT10, Policy, mixin_type,
775 allocator_type>::type
779 template<typename Mixin>
782 typedef typename function_traits_builder<MyR, MyT1, MyT2, MyT3, MyT4,
783 MyT5, MyT6, MyT7, MyT8, MyT9,
784 MyT10, policy_type, Mixin,
785 allocator_type>::type
789 template<typename Allocator>
792 typedef typename function_traits_builder<MyR, MyT1, MyT2, MyT3, MyT4,
793 MyT5, MyT6, MyT7, MyT8, MyT9,
794 MyT10, policy_type, mixin_type,
798 #endif // ndef NO_DEPENDENT_NESTED_DERIVATIONS
800 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
801 } // end namespace function
802 } // end namespace detail
806 typename T1 = detail::function::unusable,
807 typename T2 = detail::function::unusable,
808 typename T3 = detail::function::unusable,
809 typename T4 = detail::function::unusable,
810 typename T5 = detail::function::unusable,
811 typename T6 = detail::function::unusable,
812 typename T7 = detail::function::unusable,
813 typename T8 = detail::function::unusable,
814 typename T9 = detail::function::unusable,
815 typename T10 = detail::function::unusable
818 public detail::function::get_function_impl<R, T1, T2, T3, T4, T5, T6, T7,
820 #ifndef BOOST_FUNCTION_NO_DEPRECATED
821 , public detail::function::function_traits_builder<R, T1, T2, T3, T4, T5,
823 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
825 typedef typename detail::function::get_function_impl<R, T1, T2, T3, T4, T5,
831 #ifndef BOOST_FUNCTION_NO_DEPRECATED
832 typedef typename base_type::policy_type policy_type;
833 typedef typename base_type::mixin_type mixin_type;
834 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
835 typedef typename base_type::allocator_type allocator_type;
836 typedef function self_type;
838 function() : base_type() {}
840 template<typename Functor>
841 function(Functor BOOST_FUNCTION_TARGET_FIX(const &) f) : base_type(f) {}
843 function(const self_type& f) : base_type(static_cast<const base_type&>(f)){}
845 template<typename Functor>
846 self_type& operator=(Functor BOOST_FUNCTION_TARGET_FIX(const &) f)
848 self_type(f).swap(*this);
852 self_type& operator=(const base_type& f)
854 self_type(f).swap(*this);
858 self_type& operator=(const self_type& f)
860 self_type(f).swap(*this);
864 #ifndef BOOST_FUNCTION_NO_DEPRECATED
865 template<typename Functor>
866 BOOST_FUNCTION_DEPRECATED_PRE
867 void set(Functor BOOST_FUNCTION_TARGET_FIX(const &) f)
869 BOOST_FUNCTION_DEPRECATED_INNER
870 self_type(f).swap(*this);
873 BOOST_FUNCTION_DEPRECATED_PRE
874 void set(const base_type& f)
876 BOOST_FUNCTION_DEPRECATED_INNER
877 self_type(f).swap(*this);
880 BOOST_FUNCTION_DEPRECATED_PRE
881 void set(const self_type& f)
883 BOOST_FUNCTION_DEPRECATED_INNER
884 self_type(f).swap(*this);
886 #endif // ndef BOOST_FUNCTION_NO_DEPRECATED
900 inline void swap(function<R, T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>& f1,
901 function<R, T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>& f2)
905 } // end namespace boost
907 #endif // !no deprecated || !no partial specialization