voidptr_key_test.cpp 2.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394
  1. /////////////////////////////////////////////////////////////////////////////
  2. //
  3. // (C) Copyright Andrey Semashev 2018.
  4. //
  5. // Distributed under the Boost Software License, Version 1.0.
  6. // (See accompanying file LICENSE_1_0.txt or copy at
  7. // http://www.boost.org/LICENSE_1_0.txt)
  8. //
  9. // See http://www.boost.org/libs/intrusive for documentation.
  10. //
  11. /////////////////////////////////////////////////////////////////////////////
  12. #include <boost/intrusive/options.hpp>
  13. #include <boost/intrusive/set.hpp>
  14. #include <boost/intrusive/set_hook.hpp>
  15. #include <boost/config.hpp>
  16. #include <boost/core/lightweight_test.hpp>
  17. #include <functional> // std::less
  18. // The test verifies that the set implementation does not use void* as auxiliary arguments for SFINAE
  19. // in internal functions, which would make overload resolution ambiguous if user's key type is also void*.
  20. typedef boost::intrusive::set_base_hook<
  21. boost::intrusive::link_mode< boost::intrusive::safe_link >,
  22. boost::intrusive::tag< struct for_set_element_lookup_by_key >,
  23. boost::intrusive::optimize_size< true >
  24. > set_element_hook_t;
  25. struct set_element :
  26. public set_element_hook_t
  27. {
  28. struct order_by_key
  29. {
  30. typedef bool result_type;
  31. result_type operator() (set_element const& left, set_element const& right) const
  32. {
  33. return std::less< void* >()(left.m_key, right.m_key);
  34. }
  35. result_type operator() (void* left, set_element const& right) const
  36. {
  37. return std::less< void* >()(left, right.m_key);
  38. }
  39. result_type operator() (set_element const& left, void* right) const
  40. {
  41. return std::less< void* >()(left.m_key, right);
  42. }
  43. };
  44. void* m_key;
  45. explicit set_element(void* key) : m_key(key) {}
  46. BOOST_DELETED_FUNCTION(set_element(set_element const&))
  47. BOOST_DELETED_FUNCTION(set_element& operator=(set_element const&))
  48. };
  49. typedef boost::intrusive::set<
  50. set_element,
  51. boost::intrusive::base_hook< set_element_hook_t >,
  52. boost::intrusive::compare< set_element::order_by_key >,
  53. boost::intrusive::constant_time_size< true >
  54. > set_t;
  55. void test_set()
  56. {
  57. int v1 = 0, v2 = 1, v3 = 2;
  58. set_element e1(&v1), e2(&v2), e3(&v3);
  59. set_t s;
  60. s.insert(e1);
  61. s.insert(e2);
  62. set_t::iterator it = s.find(e1);
  63. BOOST_TEST(it != s.end() && &*it == &e1);
  64. it = s.find((void*)&v2, set_element::order_by_key());
  65. BOOST_TEST(it != s.end() && &*it == &e2);
  66. it = s.find(e3);
  67. BOOST_TEST(it == s.end());
  68. it = s.find((void*)&v3, set_element::order_by_key());
  69. BOOST_TEST(it == s.end());
  70. s.clear();
  71. }
  72. int main()
  73. {
  74. test_set();
  75. return boost::report_errors();
  76. }