Guest User

Untitled

a guest
Oct 17th, 2018
116
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 6.32 KB | None | 0 0
  1. class FooV1
  2. {
  3. public:
  4. FooV1();
  5. const std::vector<int>& getBars() const;
  6. private:
  7. std::vector<int> _bars;
  8. };
  9.  
  10.  
  11. class FooV2
  12. {
  13. public:
  14. FooV2();
  15. std::vector<int>::const_iterator beginBars() const;
  16. std::vector<int>::const_iterator endBars() const;
  17. private:
  18. std::vector<int> _bars;
  19. };
  20.  
  21. template<typename T>
  22. class InputIteratorDelegate final : public std::iterator<std::input_iterator_tag, T>
  23. {
  24. public:
  25. typedef void* DelegateType;
  26. typedef std::function<DelegateType(DelegateType)> CopyFuncType;
  27. typedef std::function<void(DelegateType&)> DestructorFuncType;
  28. typedef std::function<bool(DelegateType, DelegateType)> ComparerFuncType;
  29. typedef std::function<void(DelegateType)> PrefixIncrementFuncType;
  30. typedef std::function<const T&(DelegateType)> DereferenceFuncType;
  31.  
  32. InputIteratorDelegate(DelegateType delegateTo, CopyFuncType copy, DestructorFuncType destructor,
  33. ComparerFuncType comparer, PrefixIncrementFuncType prefixIncrement, DereferenceFuncType dereference) :
  34. _delegateTo(delegateTo), _copy(copy), _destructor(destructor), _comparer(comparer),
  35. _prefixIncrement(prefixIncrement), _dereference(dereference)
  36. {
  37. }
  38.  
  39. InputIteratorDelegate(const InputIteratorDelegate& other) :
  40. _delegateTo(other._copy(other._delegateTo)), _copy(other._copy), _destructor(other._destructor),
  41. _comparer(other._comparer), _prefixIncrement(other._prefixIncrement), _dereference(other._dereference)
  42. {
  43. }
  44.  
  45. InputIteratorDelegate(InputIteratorDelegate&& other) :
  46. _delegateTo(other._delegateTo), _copy(std::move(other._copy)), _destructor(std::move(other._destructor)),
  47. _comparer(std::move(other._comparer)), _prefixIncrement(std::move(other._prefixIncrement)),
  48. _dereference(std::move(other._dereference))
  49. {
  50. other._delegateTo = nullptr;
  51. }
  52.  
  53. ~InputIteratorDelegate()
  54. {
  55. if (_destructor && _delegateTo)
  56. {
  57. _destructor(_delegateTo);
  58. }
  59. }
  60.  
  61. InputIteratorDelegate& operator=(const InputIteratorDelegate& other)
  62. {
  63. InputIteratorDelegate temp(other);
  64. *this = std::move(temp);
  65. return *this;
  66. }
  67.  
  68. InputIteratorDelegate& operator=(InputIteratorDelegate&& other)
  69. {
  70. _delegateTo = other._delegateTo;
  71. other._delegateTo = nullptr;
  72. _copy = std::move(other._copy);
  73. _destructor = std::move(other._destructor);
  74. _comparer = std::move(other._comparer);
  75. _prefixIncrement = std::move(other._prefixIncrement);
  76. _dereference = std::move(other._dereference);
  77. return *this;
  78. }
  79.  
  80. bool operator==(const InputIteratorDelegate& other) const
  81. {
  82. return _comparer(_delegateTo, other._delegateTo);
  83. }
  84.  
  85. bool operator!=(const InputIteratorDelegate& other) const
  86. {
  87. return !(*this == other);
  88. }
  89.  
  90. InputIteratorDelegate<T>& operator++()
  91. {
  92. _prefixIncrement(_delegateTo);
  93. return *this;
  94. }
  95.  
  96. InputIteratorDelegate<T> operator++(int)
  97. {
  98. auto current = *this;
  99. ++*this;
  100. return current;
  101. }
  102.  
  103. const T& operator*() const
  104. {
  105. return _dereference(_delegateTo);
  106. }
  107.  
  108. private:
  109. DelegateType _delegateTo;
  110. CopyFuncType _copy;
  111. DestructorFuncType _destructor;
  112. ComparerFuncType _comparer;
  113. PrefixIncrementFuncType _prefixIncrement;
  114. DereferenceFuncType _dereference;
  115. };
  116.  
  117. template<typename T>
  118. class InputIteratorWrapper final
  119. {
  120. public:
  121. InputIteratorWrapper(InputIteratorDelegate<T> begin, InputIteratorDelegate<T> end) :
  122. _begin(std::move(begin)), _end(std::move(end))
  123. {
  124. }
  125.  
  126. InputIteratorWrapper(const InputIteratorWrapper& other) :
  127. _begin(other._begin), _end(other._end)
  128. {
  129. }
  130.  
  131. InputIteratorWrapper(InputIteratorWrapper&& other) :
  132. _begin(std::move(other._begin)), _end(std::move(other._end))
  133. {
  134. }
  135.  
  136. InputIteratorDelegate<T> begin() const
  137. {
  138. return _begin;
  139. }
  140.  
  141. InputIteratorDelegate<T> end() const
  142. {
  143. return _end;
  144. }
  145.  
  146. private:
  147. InputIteratorDelegate<T> _begin;
  148. InputIteratorDelegate<T> _end;
  149. };
  150.  
  151. template<typename T, typename TIterator>
  152. InputIteratorDelegate<T> make_input_iterator_delegate(const TIterator& iterator)
  153. {
  154. auto iteratorCopy = new TIterator(iterator);
  155.  
  156. auto copy = [](typename InputIteratorDelegate<T>::DelegateType pointer) ->
  157. typename InputIteratorDelegate<T>::DelegateType
  158. {
  159. if ( ! pointer)
  160. {
  161. return nullptr;
  162. }
  163. auto it = reinterpret_cast<TIterator*>(pointer);
  164. return new TIterator(*it);
  165. };
  166.  
  167. auto destructor = [](typename InputIteratorDelegate<T>::DelegateType& pointer)
  168. {
  169. auto it = reinterpret_cast<TIterator*>(pointer);
  170. delete it;
  171. pointer = nullptr;
  172. };
  173.  
  174. auto comparer = [](typename InputIteratorDelegate<T>::DelegateType first,
  175. typename InputIteratorDelegate<T>::DelegateType second)
  176. {
  177. auto itFirst = reinterpret_cast<TIterator*>(first);
  178. auto itSecond = reinterpret_cast<TIterator*>(second);
  179.  
  180. return *itFirst == *itSecond;
  181. };
  182.  
  183. auto prefixIncrement = [](typename InputIteratorDelegate<T>::DelegateType pointer)
  184. {
  185. auto it = reinterpret_cast<TIterator*>(pointer);
  186. ++(*it);
  187. };
  188.  
  189. auto dereference = [](typename InputIteratorDelegate<T>::DelegateType pointer) -> const T&
  190. {
  191. auto it = reinterpret_cast<TIterator*>(pointer);
  192. return **it;
  193. };
  194.  
  195. return InputIteratorDelegate<T>(iteratorCopy, copy, destructor, comparer, prefixIncrement, dereference);
  196. }
  197.  
  198. class FooV3
  199. {
  200. public:
  201. FooV3();
  202. virtual ~FooV3();
  203. InputIteratorWrapper<int> getBars() const;
  204. private:
  205. struct Private;
  206. Private* _private;
  207. };
  208.  
  209. struct FooV3::Private
  210. {
  211. std::vector<int> bars;
  212. };
  213.  
  214. FooV3::FooV3() : _private(new Private())
  215. {
  216. _private->bars = { 1, 2, 3 };
  217. }
  218.  
  219. FooV3::~FooV3()
  220. {
  221. delete _private;
  222. }
  223.  
  224. InputIteratorWrapper<int> FooV3::getBars() const
  225. {
  226. return InputIteratorWrapper<int>(make_input_iterator_delegate<int>(_private->bars.cbegin()),
  227. make_input_iterator_delegate<int>(_private->bars.cend()));
  228. }
  229.  
  230. FooV3 v3;
  231. for (auto& item : v3.getBars())
  232. {
  233. std::cout << item << ' ';
  234. }
  235. std::cout << 'n';
  236.  
  237. using iterator_category = std::input_iterator_tag;
  238. using value_type = T;
  239. using difference_type = std::ptrdiff_t;
  240. using pointer = T*;
  241. using reference = T&;
Add Comment
Please, Sign In to add comment