1169691Skan// TR1 functional -*- C++ -*- 2169691Skan 3169691Skan// Copyright (C) 2005, 2006 Free Software Foundation, Inc. 4169691Skan// Written by Douglas Gregor <doug.gregor -at- gmail.com> 5169691Skan// 6169691Skan// This file is part of the GNU ISO C++ Library. This library is free 7169691Skan// software; you can redistribute it and/or modify it under the 8169691Skan// terms of the GNU General Public License as published by the 9169691Skan// Free Software Foundation; either version 2, or (at your option) 10169691Skan// any later version. 11169691Skan 12169691Skan// This library is distributed in the hope that it will be useful, 13169691Skan// but WITHOUT ANY WARRANTY; without even the implied warranty of 14169691Skan// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15169691Skan// GNU General Public License for more details. 16169691Skan 17169691Skan// You should have received a copy of the GNU General Public License along 18169691Skan// with this library; see the file COPYING. If not, write to the Free 19169691Skan// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, 20169691Skan// USA. 21169691Skan 22169691Skan// As a special exception, you may use this file as part of a free software 23169691Skan// library without restriction. Specifically, if other files instantiate 24169691Skan// templates or use macros or inline functions from this file, or you compile 25169691Skan// this file and link it with other files to produce an executable, this 26169691Skan// file does not by itself cause the resulting executable to be covered by 27169691Skan// the GNU General Public License. This exception does not however 28169691Skan// invalidate any other reasons why the executable file might be covered by 29169691Skan// the GNU General Public License. 30169691Skan 31169691Skan/** @file tr1/functional_iterate.h 32169691Skan * This is an internal header file, included by other library headers. 33169691Skan * You should not attempt to use it directly. 34169691Skan */ 35169691Skan 36169691Skannamespace std 37169691Skan{ 38169691Skan_GLIBCXX_BEGIN_NAMESPACE(tr1) 39169691Skan 40169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 41169691Skan struct _Weak_result_type_impl<_Res(_GLIBCXX_TEMPLATE_ARGS)> 42169691Skan { 43169691Skan typedef _Res result_type; 44169691Skan }; 45169691Skan 46169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 47169691Skan struct _Weak_result_type_impl<_Res (&)(_GLIBCXX_TEMPLATE_ARGS)> 48169691Skan { 49169691Skan typedef _Res result_type; 50169691Skan }; 51169691Skan 52169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 53169691Skan struct _Weak_result_type_impl<_Res (*)(_GLIBCXX_TEMPLATE_ARGS)> 54169691Skan { 55169691Skan typedef _Res result_type; 56169691Skan }; 57169691Skan 58169691Skan#if _GLIBCXX_NUM_ARGS > 0 59169691Skantemplate<typename _Res, typename _Class _GLIBCXX_COMMA_SHIFTED 60169691Skan _GLIBCXX_TEMPLATE_PARAMS_SHIFTED> 61169691Skan struct _Weak_result_type_impl< 62169691Skan _Res (_Class::*)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED)> 63169691Skan { 64169691Skan typedef _Res result_type; 65169691Skan }; 66169691Skan 67169691Skantemplate<typename _Res, typename _Class _GLIBCXX_COMMA_SHIFTED 68169691Skan _GLIBCXX_TEMPLATE_PARAMS_SHIFTED> 69169691Skan struct _Weak_result_type_impl< 70169691Skan _Res (_Class::*)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED) const> 71169691Skan { 72169691Skan typedef _Res result_type; 73169691Skan }; 74169691Skan 75169691Skantemplate<typename _Res, typename _Class _GLIBCXX_COMMA_SHIFTED 76169691Skan _GLIBCXX_TEMPLATE_PARAMS_SHIFTED> 77169691Skan struct _Weak_result_type_impl< 78169691Skan _Res (_Class::*)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED) volatile> 79169691Skan { 80169691Skan typedef _Res result_type; 81169691Skan }; 82169691Skan 83169691Skantemplate<typename _Res, typename _Class _GLIBCXX_COMMA_SHIFTED 84169691Skan _GLIBCXX_TEMPLATE_PARAMS_SHIFTED> 85169691Skan struct _Weak_result_type_impl< 86169691Skan _Res (_Class::*)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED) const volatile> 87169691Skan { 88169691Skan typedef _Res result_type; 89169691Skan }; 90169691Skan#endif 91169691Skan 92169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 93169691Skan class result_of<_Functor(_GLIBCXX_TEMPLATE_ARGS)> 94169691Skan : public _Result_of_impl< 95169691Skan _Has_result_type<_Weak_result_type<_Functor> >::value, 96169691Skan _Functor(_GLIBCXX_TEMPLATE_ARGS)> 97169691Skan { }; 98169691Skan 99169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 100169691Skan struct _Result_of_impl<true, _Functor(_GLIBCXX_TEMPLATE_ARGS)> 101169691Skan { 102169691Skan typedef typename _Weak_result_type<_Functor>::result_type type; 103169691Skan }; 104169691Skan 105169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 106169691Skan struct _Result_of_impl<false, _Functor(_GLIBCXX_TEMPLATE_ARGS)> 107169691Skan { 108169691Skan#if _GLIBCXX_NUM_ARGS > 0 109169691Skan typedef typename _Functor 110169691Skan ::template result<_Functor(_GLIBCXX_TEMPLATE_ARGS)>::type type; 111169691Skan#else 112169691Skan typedef void type; 113169691Skan#endif 114169691Skan }; 115169691Skan 116169691Skan/** 117169691Skan * @if maint 118169691Skan * Invoke a function object, which may be either a member pointer or a 119169691Skan * function object. The first parameter will tell which. 120169691Skan * @endif 121169691Skan */ 122169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 123169691Skan inline 124169691Skan typename __gnu_cxx::__enable_if<(!is_member_pointer<_Functor>::value 125169691Skan && !is_function<_Functor>::value 126169691Skan && !is_function<typename remove_pointer<_Functor>::type>::value), 127169691Skan typename result_of<_Functor(_GLIBCXX_TEMPLATE_ARGS)>::type>::__type 128169691Skan __invoke(_Functor& __f _GLIBCXX_COMMA _GLIBCXX_REF_PARAMS) 129169691Skan { 130169691Skan return __f(_GLIBCXX_ARGS); 131169691Skan } 132169691Skan 133169691Skan#if _GLIBCXX_NUM_ARGS > 0 134169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 135169691Skan inline 136169691Skan typename __gnu_cxx::__enable_if<(is_member_pointer<_Functor>::value 137169691Skan && !is_function<_Functor>::value 138169691Skan && !is_function<typename remove_pointer<_Functor>::type>::value), 139169691Skan typename result_of<_Functor(_GLIBCXX_TEMPLATE_ARGS)>::type 140169691Skan >::__type 141169691Skan __invoke(_Functor& __f _GLIBCXX_COMMA _GLIBCXX_REF_PARAMS) 142169691Skan { 143169691Skan return mem_fn(__f)(_GLIBCXX_ARGS); 144169691Skan } 145169691Skan#endif 146169691Skan 147169691Skan// To pick up function references (that will become function pointers) 148169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 149169691Skan inline 150169691Skan typename __gnu_cxx::__enable_if<(is_pointer<_Functor>::value 151169691Skan && is_function<typename remove_pointer<_Functor>::type>::value), 152169691Skan typename result_of<_Functor(_GLIBCXX_TEMPLATE_ARGS)>::type 153169691Skan >::__type 154169691Skan __invoke(_Functor __f _GLIBCXX_COMMA _GLIBCXX_REF_PARAMS) 155169691Skan { 156169691Skan return __f(_GLIBCXX_ARGS); 157169691Skan } 158169691Skan 159169691Skan/** 160169691Skan * @if maint 161169691Skan * Implementation of reference_wrapper::operator() 162169691Skan * @endif 163169691Skan*/ 164169691Skan#if _GLIBCXX_NUM_ARGS > 0 165169691Skantemplate<typename _Tp> 166169691Skantemplate<_GLIBCXX_TEMPLATE_PARAMS> 167169691Skan typename result_of< 168169691Skan typename reference_wrapper<_Tp>::_M_func_type(_GLIBCXX_TEMPLATE_ARGS)>::type 169169691Skan reference_wrapper<_Tp>::operator()(_GLIBCXX_REF_PARAMS) const 170169691Skan { 171169691Skan return __invoke(get(), _GLIBCXX_ARGS); 172169691Skan } 173169691Skan#endif 174169691Skan 175169691Skan#if _GLIBCXX_NUM_ARGS > 0 176169691Skantemplate<typename _Res, typename _Class _GLIBCXX_COMMA_SHIFTED 177169691Skan _GLIBCXX_TEMPLATE_PARAMS_SHIFTED> 178169691Skan class _Mem_fn<_Res (_Class::*)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED)> 179169691Skan#if _GLIBCXX_NUM_ARGS == 1 180169691Skan : public unary_function<_Class*, _Res> 181169691Skan#elif _GLIBCXX_NUM_ARGS == 2 182169691Skan : public binary_function<_Class*, _T1, _Res> 183169691Skan#endif 184169691Skan { 185169691Skan typedef _Res (_Class::*_Functor)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED); 186169691Skan 187169691Skan template<typename _Tp> 188169691Skan _Res 189169691Skan _M_call(_Tp& __object, const volatile _Class * _GLIBCXX_COMMA_SHIFTED 190169691Skan _GLIBCXX_PARAMS_SHIFTED) const 191169691Skan { return (__object.*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 192169691Skan 193169691Skan template<typename _Tp> 194169691Skan _Res 195169691Skan _M_call(_Tp& __ptr, const volatile void * _GLIBCXX_COMMA_SHIFTED 196169691Skan _GLIBCXX_PARAMS_SHIFTED) const 197169691Skan { return ((*__ptr).*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 198169691Skan 199169691Skan public: 200169691Skan typedef _Res result_type; 201169691Skan 202169691Skan explicit _Mem_fn(_Functor __pf) : __pmf(__pf) { } 203169691Skan 204169691Skan // Handle objects 205169691Skan _Res 206169691Skan operator()(_Class& __object _GLIBCXX_COMMA_SHIFTED 207169691Skan _GLIBCXX_PARAMS_SHIFTED) const 208169691Skan { return (__object.*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 209169691Skan 210169691Skan // Handle pointers 211169691Skan _Res 212169691Skan operator()(_Class* __object _GLIBCXX_COMMA_SHIFTED 213169691Skan _GLIBCXX_PARAMS_SHIFTED) const 214169691Skan { return (__object->*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 215169691Skan 216169691Skan // Handle smart pointers, references and pointers to derived 217169691Skan template<typename _Tp> 218169691Skan _Res 219169691Skan operator()(_Tp& __object _GLIBCXX_COMMA_SHIFTED 220169691Skan _GLIBCXX_PARAMS_SHIFTED) const 221169691Skan { 222169691Skan return _M_call(__object, &__object _GLIBCXX_COMMA_SHIFTED 223169691Skan _GLIBCXX_ARGS_SHIFTED); 224169691Skan } 225169691Skan 226169691Skan private: 227169691Skan _Functor __pmf; 228169691Skan }; 229169691Skan 230169691Skantemplate<typename _Res, typename _Class _GLIBCXX_COMMA_SHIFTED 231169691Skan _GLIBCXX_TEMPLATE_PARAMS_SHIFTED> 232169691Skan class _Mem_fn<_Res (_Class::*)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED) const> 233169691Skan#if _GLIBCXX_NUM_ARGS == 1 234169691Skan : public unary_function<const _Class*, _Res> 235169691Skan#elif _GLIBCXX_NUM_ARGS == 2 236169691Skan : public binary_function<const _Class*, _T1, _Res> 237169691Skan#endif 238169691Skan { 239169691Skan typedef _Res (_Class::*_Functor)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED) const; 240169691Skan 241169691Skan template<typename _Tp> 242169691Skan _Res 243169691Skan _M_call(_Tp& __object, const volatile _Class * _GLIBCXX_COMMA_SHIFTED 244169691Skan _GLIBCXX_PARAMS_SHIFTED) const 245169691Skan { return (__object.*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 246169691Skan 247169691Skan template<typename _Tp> 248169691Skan _Res 249169691Skan _M_call(_Tp& __ptr, const volatile void * _GLIBCXX_COMMA_SHIFTED 250169691Skan _GLIBCXX_PARAMS_SHIFTED) const 251169691Skan { return ((*__ptr).*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 252169691Skan 253169691Skan public: 254169691Skan typedef _Res result_type; 255169691Skan 256169691Skan explicit _Mem_fn(_Functor __pf) : __pmf(__pf) { } 257169691Skan 258169691Skan // Handle objects 259169691Skan _Res 260169691Skan operator()(const _Class& __object _GLIBCXX_COMMA_SHIFTED 261169691Skan _GLIBCXX_PARAMS_SHIFTED) const 262169691Skan { return (__object.*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 263169691Skan 264169691Skan // Handle pointers 265169691Skan _Res 266169691Skan operator()(const _Class* __object _GLIBCXX_COMMA_SHIFTED 267169691Skan _GLIBCXX_PARAMS_SHIFTED) const 268169691Skan { return (__object->*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 269169691Skan 270169691Skan // Handle smart pointers, references and pointers to derived 271169691Skan template<typename _Tp> 272169691Skan _Res 273169691Skan operator()(_Tp& __object _GLIBCXX_COMMA_SHIFTED 274169691Skan _GLIBCXX_PARAMS_SHIFTED) const 275169691Skan { 276169691Skan return _M_call(__object, &__object _GLIBCXX_COMMA_SHIFTED 277169691Skan _GLIBCXX_ARGS_SHIFTED); 278169691Skan } 279169691Skan 280169691Skan private: 281169691Skan _Functor __pmf; 282169691Skan }; 283169691Skan 284169691Skantemplate<typename _Res, typename _Class _GLIBCXX_COMMA_SHIFTED 285169691Skan _GLIBCXX_TEMPLATE_PARAMS_SHIFTED> 286169691Skan class _Mem_fn<_Res (_Class::*)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED) volatile> 287169691Skan#if _GLIBCXX_NUM_ARGS == 1 288169691Skan : public unary_function<volatile _Class*, _Res> 289169691Skan#elif _GLIBCXX_NUM_ARGS == 2 290169691Skan : public binary_function<volatile _Class*, _T1, _Res> 291169691Skan#endif 292169691Skan { 293169691Skan typedef _Res (_Class::*_Functor)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED) volatile; 294169691Skan 295169691Skan template<typename _Tp> 296169691Skan _Res 297169691Skan _M_call(_Tp& __object, const volatile _Class * _GLIBCXX_COMMA_SHIFTED 298169691Skan _GLIBCXX_PARAMS_SHIFTED) const 299169691Skan { return (__object.*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 300169691Skan 301169691Skan template<typename _Tp> 302169691Skan _Res 303169691Skan _M_call(_Tp& __ptr, const volatile void * _GLIBCXX_COMMA_SHIFTED 304169691Skan _GLIBCXX_PARAMS_SHIFTED) const 305169691Skan { return ((*__ptr).*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 306169691Skan 307169691Skan public: 308169691Skan typedef _Res result_type; 309169691Skan 310169691Skan explicit _Mem_fn(_Functor __pf) : __pmf(__pf) { } 311169691Skan 312169691Skan // Handle objects 313169691Skan _Res 314169691Skan operator()(volatile _Class& __object _GLIBCXX_COMMA_SHIFTED 315169691Skan _GLIBCXX_PARAMS_SHIFTED) const 316169691Skan { return (__object.*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 317169691Skan 318169691Skan // Handle pointers 319169691Skan _Res 320169691Skan operator()(volatile _Class* __object _GLIBCXX_COMMA_SHIFTED 321169691Skan _GLIBCXX_PARAMS_SHIFTED) const 322169691Skan { return (__object->*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 323169691Skan 324169691Skan // Handle smart pointers, references and pointers to derived 325169691Skan template<typename _Tp> 326169691Skan _Res 327169691Skan operator()(_Tp& __object _GLIBCXX_COMMA_SHIFTED 328169691Skan _GLIBCXX_PARAMS_SHIFTED) const 329169691Skan { 330169691Skan return _M_call(__object, &__object _GLIBCXX_COMMA_SHIFTED 331169691Skan _GLIBCXX_ARGS_SHIFTED); 332169691Skan } 333169691Skan private: 334169691Skan _Functor __pmf; 335169691Skan }; 336169691Skan 337169691Skantemplate<typename _Res, typename _Class _GLIBCXX_COMMA_SHIFTED 338169691Skan _GLIBCXX_TEMPLATE_PARAMS_SHIFTED> 339169691Skan class _Mem_fn<_Res(_Class::*)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED) const volatile> 340169691Skan#if _GLIBCXX_NUM_ARGS == 1 341169691Skan : public unary_function<const volatile _Class*, _Res> 342169691Skan#elif _GLIBCXX_NUM_ARGS == 2 343169691Skan : public binary_function<const volatile _Class*, _T1, _Res> 344169691Skan#endif 345169691Skan { 346169691Skan typedef _Res (_Class::*_Functor)(_GLIBCXX_TEMPLATE_ARGS_SHIFTED) 347169691Skan const volatile; 348169691Skan 349169691Skan template<typename _Tp> 350169691Skan _Res 351169691Skan _M_call(_Tp& __object, const volatile _Class * _GLIBCXX_COMMA_SHIFTED 352169691Skan _GLIBCXX_PARAMS_SHIFTED) const 353169691Skan { return (__object.*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 354169691Skan 355169691Skan template<typename _Tp> 356169691Skan _Res 357169691Skan _M_call(_Tp& __ptr, const volatile void * _GLIBCXX_COMMA_SHIFTED 358169691Skan _GLIBCXX_PARAMS_SHIFTED) const 359169691Skan { return ((*__ptr).*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 360169691Skan 361169691Skan public: 362169691Skan typedef _Res result_type; 363169691Skan 364169691Skan explicit _Mem_fn(_Functor __pf) : __pmf(__pf) { } 365169691Skan 366169691Skan // Handle objects 367169691Skan _Res 368169691Skan operator()(const volatile _Class& __object _GLIBCXX_COMMA_SHIFTED 369169691Skan _GLIBCXX_PARAMS_SHIFTED) const 370169691Skan { return (__object.*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 371169691Skan 372169691Skan // Handle pointers 373169691Skan _Res 374169691Skan operator()(const volatile _Class* __object _GLIBCXX_COMMA_SHIFTED 375169691Skan _GLIBCXX_PARAMS_SHIFTED) const 376169691Skan { return (__object->*__pmf)(_GLIBCXX_ARGS_SHIFTED); } 377169691Skan 378169691Skan // Handle smart pointers, references and pointers to derived 379169691Skan template<typename _Tp> 380169691Skan _Res 381169691Skan operator()(_Tp& __object _GLIBCXX_COMMA_SHIFTED 382169691Skan _GLIBCXX_PARAMS_SHIFTED) const 383169691Skan { 384169691Skan return _M_call(__object, &__object _GLIBCXX_COMMA_SHIFTED 385169691Skan _GLIBCXX_ARGS_SHIFTED); 386169691Skan } 387169691Skan 388169691Skan private: 389169691Skan _Functor __pmf; 390169691Skan }; 391169691Skan#endif 392169691Skan 393169691Skan#if _GLIBCXX_NUM_ARGS > 0 394169691Skannamespace placeholders 395169691Skan{ 396169691Skannamespace 397169691Skan{ 398169691Skan _Placeholder<_GLIBCXX_NUM_ARGS> _GLIBCXX_JOIN(_,_GLIBCXX_NUM_ARGS); 399169691Skan} // anonymous namespace 400169691Skan} 401169691Skan#endif 402169691Skan 403169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 404169691Skanclass _Bind<_Functor(_GLIBCXX_TEMPLATE_ARGS)> 405169691Skan : public _Weak_result_type<_Functor> 406169691Skan{ 407169691Skan typedef _Bind __self_type; 408169691Skan 409169691Skan _Functor _M_f; 410169691Skan _GLIBCXX_BIND_MEMBERS 411169691Skan 412169691Skan public: 413169691Skan#if _GLIBCXX_NUM_ARGS == 0 414169691Skan explicit 415169691Skan#endif 416169691Skan _Bind(_Functor __f _GLIBCXX_COMMA _GLIBCXX_PARAMS) 417169691Skan : _M_f(__f) _GLIBCXX_COMMA _GLIBCXX_BIND_MEMBERS_INIT { } 418169691Skan 419169691Skan#define _GLIBCXX_BIND_REPEAT_HEADER <tr1/bind_iterate.h> 420169691Skan#include <tr1/bind_repeat.h> 421169691Skan#undef _GLIBCXX_BIND_REPEAT_HEADER 422169691Skan}; 423169691Skan 424169691Skantemplate<typename _Result, typename _Functor 425169691Skan _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 426169691Skanclass _Bind_result<_Result, _Functor(_GLIBCXX_TEMPLATE_ARGS)> 427169691Skan{ 428169691Skan _Functor _M_f; 429169691Skan _GLIBCXX_BIND_MEMBERS 430169691Skan 431169691Skan public: 432169691Skan typedef _Result result_type; 433169691Skan 434169691Skan#if _GLIBCXX_NUM_ARGS == 0 435169691Skan explicit 436169691Skan#endif 437169691Skan _Bind_result(_Functor __f _GLIBCXX_COMMA _GLIBCXX_PARAMS) 438169691Skan : _M_f(__f) _GLIBCXX_COMMA _GLIBCXX_BIND_MEMBERS_INIT { } 439169691Skan 440169691Skan#define _GLIBCXX_BIND_REPEAT_HEADER <tr1/bind_iterate.h> 441169691Skan#define _GLIBCXX_BIND_HAS_RESULT_TYPE 442169691Skan#include <tr1/bind_repeat.h> 443169691Skan#undef _GLIBCXX_BIND_HAS_RESULT_TYPE 444169691Skan#undef _GLIBCXX_BIND_REPEAT_HEADER 445169691Skan}; 446169691Skan 447169691Skan// Handle arbitrary function objects 448169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 449169691Skaninline 450169691Skan_Bind<typename _Maybe_wrap_member_pointer<_Functor>::type 451169691Skan (_GLIBCXX_TEMPLATE_ARGS)> 452169691Skanbind(_Functor __f _GLIBCXX_COMMA _GLIBCXX_PARAMS) 453169691Skan{ 454169691Skan typedef _Maybe_wrap_member_pointer<_Functor> __maybe_type; 455169691Skan typedef typename __maybe_type::type __functor_type; 456169691Skan typedef _Bind<__functor_type(_GLIBCXX_TEMPLATE_ARGS)> __result_type; 457169691Skan return __result_type(__maybe_type::__do_wrap(__f) 458169691Skan _GLIBCXX_COMMA _GLIBCXX_ARGS); 459169691Skan} 460169691Skan 461169691Skantemplate<typename _Result, typename _Functor 462169691Skan _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 463169691Skaninline 464169691Skan_Bind_result<_Result, 465169691Skan typename _Maybe_wrap_member_pointer<_Functor>::type 466169691Skan (_GLIBCXX_TEMPLATE_ARGS)> 467169691Skanbind(_Functor __f _GLIBCXX_COMMA _GLIBCXX_PARAMS) 468169691Skan{ 469169691Skan typedef _Maybe_wrap_member_pointer<_Functor> __maybe_type; 470169691Skan typedef typename __maybe_type::type __functor_type; 471169691Skan typedef _Bind_result<_Result, __functor_type(_GLIBCXX_TEMPLATE_ARGS)> 472169691Skan __result_type; 473169691Skan return __result_type(__maybe_type::__do_wrap(__f) 474169691Skan _GLIBCXX_COMMA _GLIBCXX_ARGS); 475169691Skan} 476169691Skan 477169691Skantemplate<typename _Res, typename _Functor _GLIBCXX_COMMA 478169691Skan _GLIBCXX_TEMPLATE_PARAMS> 479169691Skanclass _Function_handler<_Res(_GLIBCXX_TEMPLATE_ARGS), _Functor> 480169691Skan : public _Function_base::_Base_manager<_Functor> 481169691Skan{ 482169691Skan typedef _Function_base::_Base_manager<_Functor> _Base; 483169691Skan 484169691Skan public: 485169691Skan static _Res 486169691Skan _M_invoke(const _Any_data& __functor _GLIBCXX_COMMA _GLIBCXX_PARAMS) 487169691Skan { 488169691Skan return (*_Base::_M_get_pointer(__functor))(_GLIBCXX_ARGS); 489169691Skan } 490169691Skan}; 491169691Skan 492169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 493169691Skanclass _Function_handler<void(_GLIBCXX_TEMPLATE_ARGS), _Functor> 494169691Skan : public _Function_base::_Base_manager<_Functor> 495169691Skan{ 496169691Skan typedef _Function_base::_Base_manager<_Functor> _Base; 497169691Skan 498169691Skan public: 499169691Skan static void 500169691Skan _M_invoke(const _Any_data& __functor _GLIBCXX_COMMA _GLIBCXX_PARAMS) 501169691Skan { 502169691Skan (*_Base::_M_get_pointer(__functor))(_GLIBCXX_ARGS); 503169691Skan } 504169691Skan}; 505169691Skan 506169691Skantemplate<typename _Res, typename _Functor _GLIBCXX_COMMA 507169691Skan _GLIBCXX_TEMPLATE_PARAMS> 508169691Skanclass _Function_handler<_Res(_GLIBCXX_TEMPLATE_ARGS), 509169691Skan reference_wrapper<_Functor> > 510169691Skan : public _Function_base::_Ref_manager<_Functor> 511169691Skan{ 512169691Skan typedef _Function_base::_Ref_manager<_Functor> _Base; 513169691Skan 514169691Skan public: 515169691Skan static _Res 516169691Skan _M_invoke(const _Any_data& __functor _GLIBCXX_COMMA _GLIBCXX_PARAMS) 517169691Skan { 518169691Skan return __callable_functor(**_Base::_M_get_pointer(__functor)) 519169691Skan (_GLIBCXX_ARGS); 520169691Skan } 521169691Skan}; 522169691Skan 523169691Skantemplate<typename _Functor _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 524169691Skanclass _Function_handler<void(_GLIBCXX_TEMPLATE_ARGS), 525169691Skan reference_wrapper<_Functor> > 526169691Skan : public _Function_base::_Ref_manager<_Functor> 527169691Skan{ 528169691Skan typedef _Function_base::_Ref_manager<_Functor> _Base; 529169691Skan 530169691Skan public: 531169691Skan static void 532169691Skan _M_invoke(const _Any_data& __functor _GLIBCXX_COMMA _GLIBCXX_PARAMS) 533169691Skan { 534169691Skan __callable_functor(**_Base::_M_get_pointer(__functor))(_GLIBCXX_ARGS); 535169691Skan } 536169691Skan}; 537169691Skan 538169691Skantemplate<typename _Class, typename _Member, typename _Res 539169691Skan _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 540169691Skanclass _Function_handler<_Res(_GLIBCXX_TEMPLATE_ARGS), _Member _Class::*> 541169691Skan : public _Function_handler<void(_GLIBCXX_TEMPLATE_ARGS), _Member _Class::*> 542169691Skan{ 543169691Skan typedef _Function_handler<void(_GLIBCXX_TEMPLATE_ARGS), _Member _Class::*> 544169691Skan _Base; 545169691Skan 546169691Skan public: 547169691Skan static _Res 548169691Skan _M_invoke(const _Any_data& __functor _GLIBCXX_COMMA _GLIBCXX_PARAMS) 549169691Skan { 550169691Skan return std::tr1::mem_fn(_Base::_M_get_pointer(__functor)->__value) 551169691Skan (_GLIBCXX_ARGS); 552169691Skan } 553169691Skan}; 554169691Skan 555169691Skantemplate<typename _Class, typename _Member 556169691Skan _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 557169691Skanclass _Function_handler<void(_GLIBCXX_TEMPLATE_ARGS), _Member _Class::*> 558169691Skan : public _Function_base::_Base_manager< 559169691Skan _Simple_type_wrapper< _Member _Class::* > > 560169691Skan{ 561169691Skan typedef _Member _Class::* _Functor; 562169691Skan typedef _Simple_type_wrapper< _Functor > _Wrapper; 563169691Skan typedef _Function_base::_Base_manager<_Wrapper> _Base; 564169691Skan 565169691Skan public: 566169691Skan static bool 567169691Skan _M_manager(_Any_data& __dest, const _Any_data& __source, 568169691Skan _Manager_operation __op) 569169691Skan { 570169691Skan switch (__op) { 571169691Skan case __get_type_info: 572169691Skan __dest._M_access<const type_info*>() = &typeid(_Functor); 573169691Skan break; 574169691Skan 575169691Skan case __get_functor_ptr: 576169691Skan __dest._M_access<_Functor*>() = 577169691Skan &_Base::_M_get_pointer(__source)->__value; 578169691Skan break; 579169691Skan 580169691Skan default: 581169691Skan _Base::_M_manager(__dest, __source, __op); 582169691Skan } 583169691Skan return false; 584169691Skan } 585169691Skan 586169691Skan static void 587169691Skan _M_invoke(const _Any_data& __functor _GLIBCXX_COMMA _GLIBCXX_PARAMS) 588169691Skan { 589169691Skan std::tr1::mem_fn(_Base::_M_get_pointer(__functor)->__value) 590169691Skan (_GLIBCXX_ARGS); 591169691Skan } 592169691Skan}; 593169691Skan 594169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 595169691Skanclass function<_Res(_GLIBCXX_TEMPLATE_ARGS)> 596169691Skan#if _GLIBCXX_NUM_ARGS == 1 597169691Skan : public unary_function<_T1, _Res>, private _Function_base 598169691Skan#elif _GLIBCXX_NUM_ARGS == 2 599169691Skan : public binary_function<_T1, _T2, _Res>, private _Function_base 600169691Skan#else 601169691Skan : private _Function_base 602169691Skan#endif 603169691Skan{ 604169691Skan /** 605169691Skan * @if maint 606169691Skan * This class is used to implement the safe_bool idiom. 607169691Skan * @endif 608169691Skan */ 609169691Skan struct _Hidden_type 610169691Skan { 611169691Skan _Hidden_type* _M_bool; 612169691Skan }; 613169691Skan 614169691Skan /** 615169691Skan * @if maint 616169691Skan * This typedef is used to implement the safe_bool idiom. 617169691Skan * @endif 618169691Skan */ 619169691Skan typedef _Hidden_type* _Hidden_type::* _Safe_bool; 620169691Skan 621169691Skan typedef _Res _Signature_type(_GLIBCXX_TEMPLATE_ARGS); 622169691Skan 623169691Skan struct _Useless {}; 624169691Skan 625169691Skan public: 626169691Skan typedef _Res result_type; 627169691Skan 628169691Skan // [3.7.2.1] construct/copy/destroy 629169691Skan 630169691Skan /** 631169691Skan * @brief Default construct creates an empty function call wrapper. 632169691Skan * @post @c !(bool)*this 633169691Skan */ 634169691Skan function() : _Function_base() { } 635169691Skan 636169691Skan /** 637169691Skan * @brief Default construct creates an empty function call wrapper. 638169691Skan * @post @c !(bool)*this 639169691Skan */ 640169691Skan function(_M_clear_type*) : _Function_base() { } 641169691Skan 642169691Skan /** 643169691Skan * @brief %Function copy constructor. 644169691Skan * @param x A %function object with identical call signature. 645169691Skan * @pre @c (bool)*this == (bool)x 646169691Skan * 647169691Skan * The newly-created %function contains a copy of the target of @a 648169691Skan * x (if it has one). 649169691Skan */ 650169691Skan function(const function& __x); 651169691Skan 652169691Skan /** 653169691Skan * @brief Builds a %function that targets a copy of the incoming 654169691Skan * function object. 655169691Skan * @param f A %function object that is callable with parameters of 656169691Skan * type @c T1, @c T2, ..., @c TN and returns a value convertible 657169691Skan * to @c Res. 658169691Skan * 659169691Skan * The newly-created %function object will target a copy of @a 660169691Skan * f. If @a f is @c reference_wrapper<F>, then this function 661169691Skan * object will contain a reference to the function object @c 662169691Skan * f.get(). If @a f is a NULL function pointer or NULL 663169691Skan * pointer-to-member, the newly-created object will be empty. 664169691Skan * 665169691Skan * If @a f is a non-NULL function pointer or an object of type @c 666169691Skan * reference_wrapper<F>, this function will not throw. 667169691Skan */ 668169691Skan template<typename _Functor> 669169691Skan function(_Functor __f, 670169691Skan typename __gnu_cxx::__enable_if<!is_integral<_Functor>::value, _Useless>::__type = _Useless()); 671169691Skan 672169691Skan /** 673169691Skan * @brief %Function assignment operator. 674169691Skan * @param x A %function with identical call signature. 675169691Skan * @post @c (bool)*this == (bool)x 676169691Skan * @returns @c *this 677169691Skan * 678169691Skan * The target of @a x is copied to @c *this. If @a x has no 679169691Skan * target, then @c *this will be empty. 680169691Skan * 681169691Skan * If @a x targets a function pointer or a reference to a function 682169691Skan * object, then this operation will not throw an exception. 683169691Skan */ 684169691Skan function& operator=(const function& __x) 685169691Skan { 686169691Skan function(__x).swap(*this); 687169691Skan return *this; 688169691Skan } 689169691Skan 690169691Skan /** 691169691Skan * @brief %Function assignment to zero. 692169691Skan * @post @c !(bool)*this 693169691Skan * @returns @c *this 694169691Skan * 695169691Skan * The target of @a *this is deallocated, leaving it empty. 696169691Skan */ 697169691Skan function& operator=(_M_clear_type*) 698169691Skan { 699169691Skan if (_M_manager) { 700169691Skan _M_manager(_M_functor, _M_functor, __destroy_functor); 701169691Skan _M_manager = 0; 702169691Skan _M_invoker = 0; 703169691Skan } 704169691Skan return *this; 705169691Skan } 706169691Skan 707169691Skan /** 708169691Skan * @brief %Function assignment to a new target. 709169691Skan * @param f A %function object that is callable with parameters of 710169691Skan * type @c T1, @c T2, ..., @c TN and returns a value convertible 711169691Skan * to @c Res. 712169691Skan * @return @c *this 713169691Skan * 714169691Skan * This %function object wrapper will target a copy of @a 715169691Skan * f. If @a f is @c reference_wrapper<F>, then this function 716169691Skan * object will contain a reference to the function object @c 717169691Skan * f.get(). If @a f is a NULL function pointer or NULL 718169691Skan * pointer-to-member, @c this object will be empty. 719169691Skan * 720169691Skan * If @a f is a non-NULL function pointer or an object of type @c 721169691Skan * reference_wrapper<F>, this function will not throw. 722169691Skan */ 723169691Skan template<typename _Functor> 724169691Skan typename __gnu_cxx::__enable_if<!is_integral<_Functor>::value, function&>::__type 725169691Skan operator=(_Functor __f) 726169691Skan { 727169691Skan function(__f).swap(*this); 728169691Skan return *this; 729169691Skan } 730169691Skan 731169691Skan // [3.7.2.2] function modifiers 732169691Skan 733169691Skan /** 734169691Skan * @brief Swap the targets of two %function objects. 735169691Skan * @param f A %function with identical call signature. 736169691Skan * 737169691Skan * Swap the targets of @c this function object and @a f. This 738169691Skan * function will not throw an exception. 739169691Skan */ 740169691Skan void swap(function& __x) 741169691Skan { 742169691Skan _Any_data __old_functor = _M_functor; 743169691Skan _M_functor = __x._M_functor; 744169691Skan __x._M_functor = __old_functor; 745169691Skan _Manager_type __old_manager = _M_manager; 746169691Skan _M_manager = __x._M_manager; 747169691Skan __x._M_manager = __old_manager; 748169691Skan _Invoker_type __old_invoker = _M_invoker; 749169691Skan _M_invoker = __x._M_invoker; 750169691Skan __x._M_invoker = __old_invoker; 751169691Skan } 752169691Skan 753169691Skan // [3.7.2.3] function capacity 754169691Skan 755169691Skan /** 756169691Skan * @brief Determine if the %function wrapper has a target. 757169691Skan * 758169691Skan * @return @c true when this %function object contains a target, 759169691Skan * or @c false when it is empty. 760169691Skan * 761169691Skan * This function will not throw an exception. 762169691Skan */ 763169691Skan operator _Safe_bool() const 764169691Skan { 765169691Skan if (_M_empty()) 766169691Skan { 767169691Skan return 0; 768169691Skan } 769169691Skan else 770169691Skan { 771169691Skan return &_Hidden_type::_M_bool; 772169691Skan } 773169691Skan } 774169691Skan 775169691Skan // [3.7.2.4] function invocation 776169691Skan 777169691Skan /** 778169691Skan * @brief Invokes the function targeted by @c *this. 779169691Skan * @returns the result of the target. 780169691Skan * @throws bad_function_call when @c !(bool)*this 781169691Skan * 782169691Skan * The function call operator invokes the target function object 783169691Skan * stored by @c this. 784169691Skan */ 785169691Skan _Res operator()(_GLIBCXX_PARAMS) const; 786169691Skan 787169691Skan // [3.7.2.5] function target access 788169691Skan /** 789169691Skan * @brief Determine the type of the target of this function object 790169691Skan * wrapper. 791169691Skan * 792169691Skan * @returns the type identifier of the target function object, or 793169691Skan * @c typeid(void) if @c !(bool)*this. 794169691Skan * 795169691Skan * This function will not throw an exception. 796169691Skan */ 797169691Skan const type_info& target_type() const; 798169691Skan 799169691Skan /** 800169691Skan * @brief Access the stored target function object. 801169691Skan * 802169691Skan * @return Returns a pointer to the stored target function object, 803169691Skan * if @c typeid(Functor).equals(target_type()); otherwise, a NULL 804169691Skan * pointer. 805169691Skan * 806169691Skan * This function will not throw an exception. 807169691Skan */ 808169691Skan template<typename _Functor> _Functor* target(); 809169691Skan 810169691Skan /** 811169691Skan * @overload 812169691Skan */ 813169691Skan template<typename _Functor> const _Functor* target() const; 814169691Skan 815169691Skan private: 816169691Skan // [3.7.2.6] undefined operators 817169691Skan template<typename _Function> 818169691Skan void operator==(const function<_Function>&) const; 819169691Skan template<typename _Function> 820169691Skan void operator!=(const function<_Function>&) const; 821169691Skan 822169691Skan typedef _Res (*_Invoker_type)(const _Any_data& _GLIBCXX_COMMA 823169691Skan _GLIBCXX_PARAMS); 824169691Skan _Invoker_type _M_invoker; 825169691Skan}; 826169691Skan 827169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 828169691Skan function<_Res(_GLIBCXX_TEMPLATE_ARGS)>::function(const function& __x) 829169691Skan : _Function_base() 830169691Skan { 831169691Skan if (__x) { 832169691Skan _M_invoker = __x._M_invoker; 833169691Skan _M_manager = __x._M_manager; 834169691Skan __x._M_manager(_M_functor, __x._M_functor, __clone_functor); 835169691Skan } 836169691Skan } 837169691Skan 838169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 839169691Skantemplate<typename _Functor> 840169691Skan function<_Res(_GLIBCXX_TEMPLATE_ARGS)> 841169691Skan ::function(_Functor __f, 842169691Skan typename __gnu_cxx::__enable_if<!is_integral<_Functor>::value, _Useless>::__type) 843169691Skan : _Function_base() 844169691Skan{ 845169691Skan typedef _Function_handler<_Signature_type, _Functor> _My_handler; 846169691Skan if (_My_handler::_M_not_empty_function(__f)) { 847169691Skan _M_invoker = &_My_handler::_M_invoke; 848169691Skan _M_manager = &_My_handler::_M_manager; 849169691Skan _My_handler::_M_init_functor(_M_functor, __f); 850169691Skan } 851169691Skan} 852169691Skan 853169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 854169691Skan _Res 855169691Skan function<_Res(_GLIBCXX_TEMPLATE_ARGS)>::operator()(_GLIBCXX_PARAMS) const 856169691Skan { 857169691Skan if (_M_empty()) 858169691Skan { 859169691Skan#if __EXCEPTIONS 860169691Skan throw bad_function_call(); 861169691Skan#else 862169691Skan std::abort(); 863169691Skan#endif 864169691Skan } 865169691Skan return _M_invoker(_M_functor _GLIBCXX_COMMA _GLIBCXX_ARGS); 866169691Skan } 867169691Skan 868169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 869169691Skan const type_info& 870169691Skan function<_Res(_GLIBCXX_TEMPLATE_ARGS)>::target_type() const 871169691Skan { 872169691Skan if (_M_manager) 873169691Skan { 874169691Skan _Any_data __typeinfo_result; 875169691Skan _M_manager(__typeinfo_result, _M_functor, __get_type_info); 876169691Skan return *__typeinfo_result._M_access<const type_info*>(); 877169691Skan } 878169691Skan else 879169691Skan { 880169691Skan return typeid(void); 881169691Skan } 882169691Skan } 883169691Skan 884169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 885169691Skantemplate<typename _Functor> 886169691Skan _Functor* 887169691Skan function<_Res(_GLIBCXX_TEMPLATE_ARGS)>::target() 888169691Skan { 889169691Skan if (typeid(_Functor) == target_type() && _M_manager) 890169691Skan { 891169691Skan _Any_data __ptr; 892169691Skan if (_M_manager(__ptr, _M_functor, __get_functor_ptr) 893169691Skan && !is_const<_Functor>::value) 894169691Skan return 0; 895169691Skan else 896169691Skan return __ptr._M_access<_Functor*>(); 897169691Skan } 898169691Skan else 899169691Skan { 900169691Skan return 0; 901169691Skan } 902169691Skan } 903169691Skan 904169691Skantemplate<typename _Res _GLIBCXX_COMMA _GLIBCXX_TEMPLATE_PARAMS> 905169691Skantemplate<typename _Functor> 906169691Skan const _Functor* 907169691Skan function<_Res(_GLIBCXX_TEMPLATE_ARGS)>::target() const 908169691Skan { 909169691Skan if (typeid(_Functor) == target_type() && _M_manager) 910169691Skan { 911169691Skan _Any_data __ptr; 912169691Skan _M_manager(__ptr, _M_functor, __get_functor_ptr); 913169691Skan return __ptr._M_access<const _Functor*>(); 914169691Skan } 915169691Skan else 916169691Skan { 917169691Skan return 0; 918169691Skan } 919169691Skan } 920169691Skan 921169691Skan_GLIBCXX_END_NAMESPACE 922169691Skan} 923