value_at_key.hpp 2.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586
  1. /*=============================================================================
  2. Copyright (c) 2001-2011 Joel de Guzman
  3. Copyright (c) 2006 Dan Marsden
  4. Distributed under the Boost Software License, Version 1.0. (See accompanying
  5. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  6. ==============================================================================*/
  7. #if !defined(FUSION_VALUE_AT_KEY_05052005_0229)
  8. #define FUSION_VALUE_AT_KEY_05052005_0229
  9. #include <boost/fusion/support/config.hpp>
  10. #include <boost/mpl/int.hpp>
  11. #include <boost/mpl/empty_base.hpp>
  12. #include <boost/mpl/if.hpp>
  13. #include <boost/mpl/or.hpp>
  14. #include <boost/fusion/sequence/intrinsic_fwd.hpp>
  15. #include <boost/fusion/sequence/intrinsic/has_key.hpp>
  16. #include <boost/fusion/iterator/value_of_data.hpp>
  17. #include <boost/fusion/algorithm/query/find.hpp>
  18. #include <boost/fusion/support/tag_of.hpp>
  19. #include <boost/fusion/support/category_of.hpp>
  20. namespace boost { namespace fusion
  21. {
  22. // Special tags:
  23. struct sequence_facade_tag;
  24. struct boost_array_tag; // boost::array tag
  25. struct mpl_sequence_tag; // mpl sequence tag
  26. struct std_pair_tag; // std::pair tag
  27. namespace extension
  28. {
  29. template <typename Tag>
  30. struct value_at_key_impl
  31. {
  32. template <typename Seq, typename Key>
  33. struct apply
  34. : result_of::value_of_data<
  35. typename result_of::find<Seq, Key>::type
  36. >
  37. {};
  38. };
  39. template <>
  40. struct value_at_key_impl<sequence_facade_tag>
  41. {
  42. template <typename Sequence, typename Key>
  43. struct apply : Sequence::template value_at_key<Sequence, Key> {};
  44. };
  45. template <>
  46. struct value_at_key_impl<boost_array_tag>;
  47. template <>
  48. struct value_at_key_impl<mpl_sequence_tag>;
  49. template <>
  50. struct value_at_key_impl<std_pair_tag>;
  51. }
  52. namespace detail
  53. {
  54. template <typename Sequence, typename N, typename Tag>
  55. struct value_at_key_impl
  56. : mpl::if_<
  57. mpl::or_<
  58. typename extension::has_key_impl<Tag>::template apply<Sequence, N>
  59. , traits::is_unbounded<Sequence>
  60. >
  61. , typename extension::value_at_key_impl<Tag>::template apply<Sequence, N>
  62. , mpl::empty_base
  63. >::type
  64. {};
  65. }
  66. namespace result_of
  67. {
  68. template <typename Sequence, typename N>
  69. struct value_at_key
  70. : detail::value_at_key_impl<Sequence, N, typename detail::tag_of<Sequence>::type>
  71. {};
  72. }
  73. }}
  74. #endif