You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1621 lines
56 KiB

  1. #pragma once
  2. #include <set>
  3. #include <map>
  4. #include <list>
  5. #include <vector>
  6. #include "Nullable.h"
  7. #include "Exception.h"
  8. #include "MetaProgramming.h"
  9. // #define LINQ_DEBUG
  10. #ifdef LINQ_DEBUG
  11. #include "Misc.h"
  12. #define LINQ_TYPE_NAME() utl::TypeHelper<decltype(*this)>::name()
  13. #define LINQ_CTOR() do { std::cout << "CTOR(this=" << this << ")" << LINQ_TYPE_NAME() << std::endl; } while(0)
  14. #define LINQ_COPY_CTOR() do { std::cout << "COPY(this=" << this << ")" << LINQ_TYPE_NAME() << std::endl; } while(0)
  15. #define LINQ_MOVE_CTOR() do { std::cout << "MOVE(this=" << this << ")" << LINQ_TYPE_NAME() << std::endl; } while(0)
  16. #define LINQ_DTOR() do { std::cout << "DTOR(this=" << this << ")" << LINQ_TYPE_NAME() << std::endl; } while(0)
  17. #else
  18. #define LINQ_TYPE_NAME() while(0)
  19. #define LINQ_CTOR() while(0)
  20. #define LINQ_COPY_CTOR() while(0)
  21. #define LINQ_MOVE_CTOR() while(0)
  22. #define LINQ_DTOR() while(0)
  23. #endif
  24. namespace linq
  25. {
  26. namespace __impl
  27. {
  28. struct tag_range { };
  29. struct tag_builder { };
  30. /* meta programming **********************************************************************/
  31. template<class TArray>
  32. struct mp_array_properties;
  33. template<class T, size_t N>
  34. struct mp_array_properties<T[N]>
  35. {
  36. using size = std::integral_constant<size_t, N>;
  37. using value_type = T;
  38. using iterator_type = T*;
  39. };
  40. template<class T>
  41. using mp_range_value_type = typename utl::mp_remove_ref<T>::value_type;
  42. /* helper types **************************************************************************/
  43. template<class T>
  44. struct wrapper
  45. {
  46. using value_type = T;
  47. value_type value;
  48. inline value_type operator*() const
  49. { return value; }
  50. inline wrapper& operator=(const wrapper& other)
  51. {
  52. value = other.value;
  53. return *this;
  54. }
  55. inline wrapper& operator=(wrapper&& other)
  56. {
  57. value = std::move(other).value;
  58. return *this;
  59. }
  60. template<class X>
  61. inline wrapper(X&& v) :
  62. value(std::forward<X>(v))
  63. { }
  64. inline wrapper(const value_type& v) :
  65. value(v)
  66. { }
  67. inline wrapper(const wrapper& other) :
  68. value(other.value)
  69. { }
  70. inline wrapper(wrapper&& other) :
  71. value(std::move(other.value))
  72. { }
  73. };
  74. template<class T>
  75. struct wrapper<T&>
  76. {
  77. using value_type = T&;
  78. using storage_type = T*;
  79. storage_type value;
  80. inline value_type operator*() const
  81. { return *value; }
  82. inline wrapper& operator=(const wrapper& other)
  83. {
  84. value = other.value;
  85. return *this;
  86. }
  87. inline wrapper& operator=(wrapper&& other)
  88. {
  89. value = std::move(other.value);
  90. return *this;
  91. }
  92. inline wrapper(value_type v) :
  93. value(&v)
  94. { }
  95. inline wrapper(const wrapper& other) :
  96. value(other.value)
  97. { }
  98. inline wrapper(wrapper&& other) :
  99. value(std::move(other.value))
  100. { }
  101. };
  102. template<class T, class TPredicate>
  103. struct op_wrapper_less
  104. {
  105. using predicate_type = TPredicate;
  106. using value_type = wrapper<T>;
  107. predicate_type predicate;
  108. inline bool operator()(const value_type& l, const value_type& r)
  109. { return predicate(*l, *r); }
  110. inline op_wrapper_less(const predicate_type& lp) :
  111. predicate(lp)
  112. { }
  113. inline op_wrapper_less(const op_wrapper_less& other) :
  114. predicate(other.predicate)
  115. { }
  116. inline op_wrapper_less(op_wrapper_less&& other) :
  117. predicate(std::move(other.predicate))
  118. { }
  119. };
  120. template<class TRange>
  121. struct range_wrapper
  122. {
  123. using range_type = TRange;
  124. using this_type = range_wrapper<range_type>;
  125. using value_type = mp_range_value_type<range_type>;
  126. range_type range;
  127. inline value_type& front()
  128. { return range.front(); }
  129. inline bool next()
  130. { return range.next(); }
  131. template<class TBuilder>
  132. inline auto operator >> (TBuilder&& builder) &
  133. { return builder.build(range); }
  134. template<class TBuilder>
  135. inline auto operator >> (TBuilder&& builder) &&
  136. { return builder.build(std::move(range)); }
  137. template<class... Args>
  138. range_wrapper(Args&&... args) :
  139. range(std::forward<Args>(args)...)
  140. { }
  141. range_wrapper(const this_type& other) :
  142. range(other.range)
  143. { }
  144. range_wrapper(this_type&& other) :
  145. range(std::move(other.range))
  146. { }
  147. };
  148. template<class TKey, class TValue>
  149. struct lookup
  150. {
  151. public:
  152. using key_type = TKey;
  153. using clean_key_type = utl::mp_remove_ref<key_type>;
  154. using value_type = TValue;
  155. using this_type = lookup<key_type, value_type>;
  156. using wrapped_key_type = wrapper<key_type>;
  157. using wrapped_value_type = wrapper<value_type>;
  158. using keys_value_type = std::pair<wrapped_key_type, size_t>;
  159. using keys_type = std::vector<keys_value_type>;
  160. using values_type = std::vector<wrapped_value_type>;
  161. using range_indices_type = std::pair<size_t, size_t>;
  162. private:
  163. struct lookup_range;
  164. struct lookup_key_value_range;
  165. using lookup_range_wrapper = range_wrapper<lookup_range>;
  166. using lookup_key_value_range_wrapper = range_wrapper<lookup_key_value_range>;
  167. public:
  168. using range_type = lookup_key_value_range_wrapper;
  169. private:
  170. struct lookup_range : public tag_range
  171. {
  172. using value_type = lookup::value_type;
  173. enum class State
  174. {
  175. Initialize,
  176. Iterating,
  177. Finished,
  178. };
  179. const values_type& values;
  180. size_t current;
  181. size_t end;
  182. State state;
  183. inline value_type& front()
  184. {
  185. assert(state == State::Iterating);
  186. assert(current < end);
  187. return *values[current];
  188. }
  189. inline bool next()
  190. {
  191. switch (state)
  192. {
  193. case State::Iterating:
  194. {
  195. ++current;
  196. }
  197. case State::Initialize:
  198. {
  199. auto hasElements = (current < end);
  200. state = (hasElements ? State::Iterating : State::Finished);
  201. return hasElements;
  202. }
  203. default:
  204. {
  205. return false;
  206. }
  207. }
  208. }
  209. inline lookup_range(const values_type& v, size_t c, size_t e) :
  210. values (v),
  211. current (c),
  212. end (e),
  213. state (State::Initialize)
  214. { LINQ_CTOR(); }
  215. inline lookup_range(const lookup_range& other) :
  216. values (other.values),
  217. current (other.current),
  218. end (other.end),
  219. state (other.state)
  220. { LINQ_COPY_CTOR(); }
  221. inline lookup_range(lookup_range&& other) :
  222. values (std::move(other.values)),
  223. current (std::move(other.current)),
  224. end (std::move(other.end)),
  225. state (std::move(other.state))
  226. { LINQ_MOVE_CTOR(); }
  227. inline ~lookup_range()
  228. { LINQ_DTOR(); }
  229. };
  230. struct lookup_key_value_range : public tag_range
  231. {
  232. using value_type = std::pair<key_type, lookup_range_wrapper>;
  233. using iterator_type = typename keys_type::const_iterator;
  234. lookup container;
  235. bool initialized;
  236. range_indices_type range_indices;
  237. iterator_type current;
  238. iterator_type end;
  239. inline value_type front()
  240. {
  241. assert(initialized);
  242. assert(current != end);
  243. return value_type(
  244. *current->first,
  245. std::move(container.createRange(range_indices)));
  246. }
  247. inline bool next()
  248. {
  249. if (!initialized)
  250. {
  251. initialized = true;
  252. current = container._keys.begin();
  253. end = container._keys.end();
  254. if (current == end)
  255. return false;
  256. }
  257. else
  258. {
  259. if (current == end)
  260. return false;
  261. ++current;
  262. if (current == end)
  263. return false;
  264. }
  265. range_indices = container.findKey(*current->first);
  266. return true;
  267. }
  268. template<class C>
  269. lookup_key_value_range(C&& c) :
  270. container (std::forward<C>(c)),
  271. initialized (false)
  272. { LINQ_CTOR(); }
  273. lookup_key_value_range(const lookup_key_value_range& other) :
  274. container (other.container),
  275. initialized (other.initialized),
  276. range_indices (other.range_indices),
  277. current (other.current),
  278. end (other.end)
  279. { LINQ_COPY_CTOR(); }
  280. lookup_key_value_range(lookup_key_value_range&& other) :
  281. container (std::move(other).container),
  282. initialized (std::move(other).initialized),
  283. range_indices (std::move(other).range_indices),
  284. current (std::move(other).current),
  285. end (std::move(other).end)
  286. { LINQ_MOVE_CTOR(); }
  287. ~lookup_key_value_range()
  288. { LINQ_DTOR(); }
  289. };
  290. struct op_compare_keys
  291. {
  292. bool operator()(
  293. const keys_value_type& l,
  294. const keys_value_type& r)
  295. { return *l.first < *r.first; }
  296. };
  297. private:
  298. keys_type _keys;
  299. values_type _values;
  300. inline range_indices_type findKey(const clean_key_type& key)
  301. {
  302. if (_values.empty())
  303. return std::make_pair<size_t, size_t>(0, 0);
  304. auto it = std::lower_bound(
  305. _keys.begin(),
  306. _keys.end(),
  307. typename keys_type::value_type (const_cast<clean_key_type&>(key), 0),
  308. op_compare_keys());
  309. if ( it == _keys.end()
  310. || *it->first != const_cast<clean_key_type&>(key))
  311. return std::make_pair<size_t, size_t>(0, 0);
  312. auto next = it + 1;
  313. range_indices_type ret;
  314. ret.first = it->second;
  315. ret.second = next == _keys.end()
  316. ? _values.size()
  317. : next->second;
  318. return ret;
  319. }
  320. inline lookup_range_wrapper createRange(const range_indices_type& indices)
  321. { return lookup_range_wrapper(_values, indices.first, indices.second); }
  322. public:
  323. inline lookup_range_wrapper operator[](const clean_key_type& key)
  324. { return createRange(findKey(key)); }
  325. template<class TBuilder>
  326. inline auto operator >> (TBuilder&& builder) &
  327. { return builder.build(std::move(lookup_key_value_range(*this))); }
  328. template<class TBuilder>
  329. inline auto operator >> (TBuilder&& builder) &&
  330. { return builder.build(std::move(lookup_key_value_range(std::move(*this)))); }
  331. private:
  332. inline lookup(keys_type&& k, values_type&& v) :
  333. _keys (k),
  334. _values (v)
  335. { LINQ_CTOR(); }
  336. public:
  337. inline lookup()
  338. { LINQ_CTOR(); }
  339. inline lookup(const lookup& other) :
  340. _keys (other._keys),
  341. _values (other._values)
  342. { LINQ_COPY_CTOR(); }
  343. inline lookup(lookup&& other) :
  344. _keys (std::move(other)._keys),
  345. _values (std::move(other)._values)
  346. { LINQ_MOVE_CTOR(); }
  347. inline ~lookup()
  348. { LINQ_DTOR(); }
  349. public:
  350. template<class TRange, class TKeyPredicate, class TValuePredicate>
  351. static inline auto build(TRange& range, TKeyPredicate& kp, TValuePredicate& vp)
  352. {
  353. keys_type k;
  354. values_type v;
  355. size_t index = 0;
  356. while (range.next())
  357. {
  358. k.emplace_back(kp(range.front()), index);
  359. v.emplace_back(vp(range.front()));
  360. ++index;
  361. }
  362. if (v.empty())
  363. return lookup();
  364. std::sort(k.begin(), k.end(), op_compare_keys());
  365. keys_type keys;
  366. values_type values;
  367. keys.reserve (k.size());
  368. values.reserve(k.size());
  369. auto it = k.begin();
  370. auto end = k.end();
  371. index = 0;
  372. if (it != end)
  373. {
  374. keys.emplace_back(it->first, index);
  375. values.push_back(v.at(it->second));
  376. }
  377. auto prev = it;
  378. ++it;
  379. ++index;
  380. while (it != end)
  381. {
  382. values.push_back(v.at(it->second));
  383. if (*prev->first < *it->first)
  384. keys.push_back(std::make_pair(it->first, index));
  385. prev = it;
  386. ++it;
  387. ++index;
  388. }
  389. return lookup(std::move(keys), std::move(values));
  390. }
  391. };
  392. /* ranges ********************************************************************************/
  393. template<class TIterator>
  394. struct iterator_range : public tag_range
  395. {
  396. using iterator_type = TIterator;
  397. using this_type = iterator_range<iterator_type>;
  398. using value_type = decltype(*std::declval<iterator_type>());
  399. bool initialized;
  400. iterator_type current;
  401. iterator_type end;
  402. inline value_type& front()
  403. {
  404. assert(initialized);
  405. assert(current != end);
  406. return *current;
  407. }
  408. inline bool next()
  409. {
  410. if (!initialized)
  411. initialized = true;
  412. else if (current != end)
  413. ++current;
  414. return (current != end);
  415. }
  416. inline iterator_range(iterator_type beg, iterator_type end) :
  417. initialized (false),
  418. current (beg),
  419. end (end)
  420. { LINQ_CTOR(); }
  421. inline iterator_range(const this_type& other) :
  422. initialized (other.initialized),
  423. current (other.current),
  424. end (other.end)
  425. { LINQ_COPY_CTOR(); }
  426. inline iterator_range(this_type&& other) :
  427. initialized (std::move(other).initialized),
  428. current (std::move(other).current),
  429. end (std::move(other).end)
  430. { LINQ_MOVE_CTOR(); }
  431. inline ~iterator_range()
  432. { LINQ_DTOR(); }
  433. };
  434. template<class TIterator>
  435. using iterator_range_wrapper = range_wrapper<iterator_range<TIterator>>;
  436. template<class TContainer>
  437. struct container_range : public tag_range
  438. {
  439. using container_type = TContainer;
  440. using this_type = container_range<container_type>;
  441. using iterator_type = decltype(std::begin(std::declval<container_type>()));
  442. using value_type = decltype(*std::declval<iterator_type>());
  443. TContainer container;
  444. bool initialized;
  445. iterator_type current;
  446. inline value_type& front()
  447. {
  448. assert(initialized);
  449. assert(current != std::end(container));
  450. return *current;
  451. }
  452. inline bool next()
  453. {
  454. if (!initialized)
  455. {
  456. initialized = true;
  457. current = std::begin(container);
  458. }
  459. else if (current != std::end(container))
  460. {
  461. ++current;
  462. }
  463. return (current != std::end(container));
  464. }
  465. inline container_range(container_type& c) noexcept :
  466. container (c),
  467. initialized (false)
  468. { LINQ_CTOR(); }
  469. inline container_range(const this_type& other) noexcept :
  470. container (other.container),
  471. initialized (other.initialized),
  472. current (other.current)
  473. { LINQ_COPY_CTOR(); }
  474. inline container_range(this_type&& other) noexcept :
  475. container (std::move(other).container),
  476. initialized (std::move(other).initialized),
  477. current (std::move(other).current)
  478. { LINQ_MOVE_CTOR(); }
  479. inline ~container_range()
  480. { LINQ_DTOR(); }
  481. };
  482. template<class TContainer>
  483. using container_range_wrapper = range_wrapper<container_range<TContainer>>;
  484. template<class TPredicate>
  485. struct generator_range : public tag_range
  486. {
  487. using predicate_type = TPredicate;
  488. using this_type = generator_range<predicate_type>;
  489. using predicate_value_type = decltype(std::declval<predicate_type>()());
  490. using value_type = decltype(*std::declval<predicate_value_type>());
  491. predicate_type predicate;
  492. predicate_value_type value;
  493. inline value_type& front()
  494. {
  495. assert(static_cast<bool>(value));
  496. return *value;
  497. }
  498. inline bool next()
  499. {
  500. value = predicate();
  501. return static_cast<bool>(value);
  502. }
  503. inline generator_range(predicate_type p) :
  504. predicate (p)
  505. { LINQ_CTOR(); }
  506. inline generator_range(const this_type& other) :
  507. predicate (other.predicate),
  508. value (other.value)
  509. { LINQ_COPY_CTOR(); }
  510. inline generator_range(this_type&& other) :
  511. predicate (std::move(other).predicate),
  512. value (std::move(other).value)
  513. { LINQ_MOVE_CTOR(); }
  514. inline ~generator_range()
  515. { LINQ_DTOR(); }
  516. };
  517. template<class TPredicate>
  518. using generator_range_wrapper = range_wrapper<generator_range<TPredicate>>;
  519. template<class TRange, class TPredicate>
  520. struct where_range : public tag_range
  521. {
  522. using range_type = TRange;
  523. using predicate_type = TPredicate;
  524. using this_type = where_range<range_type, predicate_type>;
  525. using value_type = mp_range_value_type<range_type>;
  526. range_type range;
  527. predicate_type predicate;
  528. inline value_type& front()
  529. { return range.front(); }
  530. inline bool next()
  531. {
  532. while (range.next())
  533. {
  534. if (predicate(range.front()))
  535. return true;
  536. }
  537. return false;
  538. }
  539. template<class R, class P>
  540. inline where_range(R&& r, P&& p) :
  541. range (std::forward<R>(r)),
  542. predicate (std::forward<P>(p))
  543. { LINQ_CTOR(); }
  544. inline where_range(const this_type& other) :
  545. range (other.range),
  546. predicate (other.predicate)
  547. { LINQ_COPY_CTOR(); }
  548. inline where_range(this_type&& other) :
  549. range (std::move(other).range),
  550. predicate (std::move(other).predicate)
  551. { LINQ_MOVE_CTOR(); }
  552. inline ~where_range()
  553. { LINQ_DTOR(); }
  554. };
  555. template<class TRange, class TPredicate>
  556. using where_range_wrapper = range_wrapper<where_range<TRange, TPredicate>>;
  557. template<class TRange, class TPredicate>
  558. struct select_range : public tag_range
  559. {
  560. using range_type = TRange;
  561. using predicate_type = TPredicate;
  562. using this_type = select_range<range_type, predicate_type>;
  563. using range_value_type = mp_range_value_type<range_type>;
  564. using value_type = decltype(std::declval<predicate_type>()(std::declval<range_value_type>()));
  565. using cache_type = utl::Nullable<value_type>;
  566. predicate_type predicate;
  567. range_type range;
  568. cache_type cache;
  569. inline value_type& front()
  570. {
  571. assert(static_cast<bool>(cache));
  572. return *cache;
  573. }
  574. inline bool next()
  575. {
  576. if (range.next())
  577. {
  578. cache = predicate(range.front());
  579. return true;
  580. }
  581. cache.reset();
  582. return false;
  583. }
  584. template<class R, class P>
  585. inline select_range(R&& r, P&& p) :
  586. range (std::forward<R>(r)),
  587. predicate (std::forward<P>(p))
  588. { LINQ_CTOR(); }
  589. inline select_range(const this_type& other) :
  590. range (other.range),
  591. predicate (other.predicate)
  592. { LINQ_COPY_CTOR(); }
  593. inline select_range(this_type&& other) :
  594. range (std::move(other).range),
  595. predicate (std::move(other).predicate)
  596. { LINQ_MOVE_CTOR(); }
  597. inline ~select_range()
  598. { LINQ_DTOR(); }
  599. };
  600. template<class TRange, class TPredicate>
  601. using select_range_wrapper = range_wrapper<select_range<TRange, TPredicate>>;
  602. template<class TRange, class TPredicate>
  603. struct select_many_range : public tag_range
  604. {
  605. template<class T>
  606. struct __impl_make_inner_range
  607. {
  608. using iterator_type = decltype(std::begin(std::declval<T>()));
  609. using type = iterator_range<iterator_type>;
  610. };
  611. template<class T>
  612. using mp_make_inner_range = typename __impl_make_inner_range<T>::type;
  613. using range_type = TRange;
  614. using predicate_type = TPredicate;
  615. using this_type = where_range<range_type, predicate_type>;
  616. using range_value_type = mp_range_value_type<range_type>;
  617. using predicate_return_type = decltype(std::declval<predicate_type>()(std::declval<range_value_type>()));
  618. using inner_range_type = utl::mp_eval_if<
  619. std::is_base_of<tag_range, predicate_return_type>,
  620. predicate_return_type,
  621. mp_make_inner_range, predicate_return_type>;
  622. using value_type = mp_range_value_type<inner_range_type>;
  623. using inner_range_cache_type = utl::Nullable<inner_range_type>;
  624. predicate_type predicate;
  625. range_type range;
  626. inner_range_cache_type inner_range;
  627. template<class T>
  628. inline typename std::enable_if<std::is_base_of<tag_range, T>::value>::type
  629. build_inner_range(T value)
  630. { inner_range = value; }
  631. template<class T>
  632. inline typename std::enable_if<!std::is_base_of<tag_range, T>::value>::type
  633. build_inner_range(T value)
  634. { inner_range = inner_range_type(std::begin(value), std::end(value)); }
  635. inline value_type& front()
  636. {
  637. assert(inner_range);
  638. return inner_range->front();
  639. }
  640. inline bool next()
  641. {
  642. if (inner_range && inner_range->next())
  643. return true;
  644. while (range.next())
  645. {
  646. inner_range.reset();
  647. build_inner_range<predicate_return_type>(predicate(range.front()));
  648. if (inner_range && inner_range->next())
  649. return true;
  650. }
  651. inner_range.reset();
  652. return false;
  653. }
  654. template<class R, class P>
  655. inline select_many_range(R&& r, P&& p) :
  656. range (std::forward<R>(r)),
  657. predicate (std::forward<P>(p))
  658. { LINQ_CTOR(); }
  659. inline select_many_range(const this_type& other) :
  660. range (other.range),
  661. predicate (other.predicate),
  662. inner_range (other.inner_range)
  663. { LINQ_COPY_CTOR(); }
  664. inline select_many_range(this_type&& other) :
  665. range (std::move(other).range),
  666. predicate (std::move(other).predicate),
  667. inner_range (std::move(other).inner_range)
  668. { LINQ_MOVE_CTOR(); }
  669. inline ~select_many_range()
  670. { LINQ_DTOR(); }
  671. };
  672. template<class TRange, class TPredicate>
  673. using select_many_range_wrapper = range_wrapper<select_many_range<TRange, TPredicate>>;
  674. template<class TRange, class TSelectPredicate, class TLessPredicate>
  675. struct order_by_range : public tag_range
  676. {
  677. using range_type = TRange;
  678. using select_predicate_type = TSelectPredicate;
  679. using less_predicate_type = TLessPredicate;
  680. using this_type = order_by_range<range_type, select_predicate_type, less_predicate_type>;
  681. using value_type = mp_range_value_type<range_type>;
  682. using vector_value_type = utl::mp_if<
  683. std::is_reference<value_type>,
  684. utl::mp_remove_ref<value_type>*,
  685. value_type>;
  686. using vector_type = std::vector<vector_value_type>;
  687. range_type range;
  688. select_predicate_type select_predicate;
  689. less_predicate_type less_predicate;
  690. ssize_t current;
  691. vector_type values;
  692. template<class X>
  693. inline utl::mp_enable_if_c<std::is_reference<X>::value, X>
  694. front_impl()
  695. {
  696. assert(current >= 0);
  697. assert(current < static_cast<ssize_t>(values.size()));
  698. return *values.at(current);
  699. }
  700. template<class X>
  701. inline utl::mp_enable_if_c<!std::is_reference<X>::value, X>
  702. front_impl()
  703. {
  704. assert(current >= 0);
  705. assert(current < static_cast<ssize_t>(values.size()));
  706. return values.at(current);
  707. }
  708. template<class X>
  709. inline utl::mp_enable_if_c<std::is_reference<X>::value>
  710. storeValue(X x)
  711. { values.emplace_back(&x); }
  712. template<class X>
  713. inline utl::mp_enable_if_c<!std::is_reference<X>::value>
  714. storeValue(X x)
  715. { values.emplace_back(x); }
  716. template<class X>
  717. inline utl::mp_enable_if_c<std::is_reference<X>::value>
  718. sortValues()
  719. {
  720. std::sort(
  721. values.begin(),
  722. values.end(),
  723. [this](vector_value_type& l, vector_value_type& r) {
  724. return this->less_predicate(
  725. this->select_predicate(*l),
  726. this->select_predicate(*r));
  727. });
  728. }
  729. template<class X>
  730. inline utl::mp_enable_if_c<!std::is_reference<X>::value>
  731. sortValues()
  732. {
  733. std::sort(
  734. values.begin(),
  735. values.end(),
  736. [this](vector_value_type& l, vector_value_type& r) {
  737. return this->less_predicate(
  738. this->select_predicate(l),
  739. this->select_predicate(r));
  740. });
  741. }
  742. inline value_type& front()
  743. { return front_impl<value_type>(); }
  744. inline bool next()
  745. {
  746. if (current < 0)
  747. {
  748. values.clear();
  749. while (range.next())
  750. storeValue<value_type>(range.front());
  751. if (values.empty())
  752. return false;
  753. sortValues<value_type>();
  754. current = 0;
  755. return true;
  756. }
  757. if (current < static_cast<ssize_t>(values.size()))
  758. ++current;
  759. return (current < static_cast<ssize_t>(values.size()));
  760. }
  761. template<class R, class SP, class LP>
  762. inline order_by_range(R&& r, SP&& sp, LP&& lp) :
  763. range (std::forward<R>(r)),
  764. select_predicate(std::forward<SP>(sp)),
  765. less_predicate (std::forward<LP>(lp)),
  766. current (-1)
  767. { LINQ_CTOR(); }
  768. inline order_by_range(const this_type& other) :
  769. range (other.range),
  770. select_predicate(other.select_predicate),
  771. less_predicate (other.less_predicate),
  772. current (other.current)
  773. { LINQ_COPY_CTOR(); }
  774. inline order_by_range(this_type&& other) :
  775. range (std::move(other).range),
  776. select_predicate(std::move(other).select_predicate),
  777. less_predicate (std::move(other).less_predicate),
  778. current (std::move(other).current)
  779. { LINQ_MOVE_CTOR(); }
  780. inline ~order_by_range()
  781. { LINQ_DTOR(); }
  782. };
  783. template<class TRange, class TSelectPredicate, class TLessPredicate>
  784. using order_by_range_wrapper = range_wrapper<order_by_range<TRange, TSelectPredicate, TLessPredicate>>;
  785. template<class TRange, class TLessPredicate>
  786. struct distinct_range : public tag_range
  787. {
  788. using range_type = TRange;
  789. using less_predicate_type = TLessPredicate;
  790. using this_type = distinct_range<range_type, less_predicate_type>;
  791. using value_type = mp_range_value_type<range_type>;
  792. using set_value_type = wrapper<value_type>;
  793. using set_less_type = op_wrapper_less<value_type, less_predicate_type>;
  794. using set_type = std::set<set_value_type, set_less_type>;
  795. range_type range;
  796. set_type set;
  797. inline value_type& front()
  798. { return range.front(); }
  799. inline bool next()
  800. {
  801. while(range.next())
  802. {
  803. if (set.emplace(range.front()).second)
  804. return true;
  805. }
  806. return false;
  807. }
  808. template<class R, class LP>
  809. inline distinct_range(R&& r, LP&& lp) :
  810. range (std::forward<R>(r)),
  811. set (std::forward<LP>(lp))
  812. { LINQ_CTOR(); }
  813. inline distinct_range(const this_type& other) :
  814. range (other.range),
  815. set (other.set)
  816. { LINQ_COPY_CTOR(); }
  817. inline distinct_range(this_type&& other) :
  818. range (std::move(other).range),
  819. set (std::move(other).set)
  820. { LINQ_MOVE_CTOR(); }
  821. inline ~distinct_range()
  822. { LINQ_DTOR(); }
  823. };
  824. template<class TRange, class TLessPredicate>
  825. using distinct_range_wrapper = range_wrapper<distinct_range<TRange, TLessPredicate>>;
  826. /* builder *******************************************************************************/
  827. template<template<class> class TOuterRange>
  828. struct builder : public tag_builder
  829. {
  830. template<class R>
  831. using outer_range_type = TOuterRange<R>;
  832. using this_type = builder<outer_range_type>;
  833. template<class TRange>
  834. inline auto build(TRange&& range)
  835. {
  836. // CAUTION: we want no reference to a range here, because the passed range may be destroyed before used in outer_range_type
  837. using range_type = utl::mp_remove_ref<TRange>;
  838. return outer_range_type<range_type>(std::forward<TRange>(range));
  839. }
  840. inline builder()
  841. { LINQ_CTOR(); }
  842. inline builder(this_type&& other)
  843. { LINQ_MOVE_CTOR(); }
  844. inline builder(const this_type&) = delete;
  845. inline ~builder()
  846. { LINQ_DTOR(); }
  847. };
  848. template<class TPredicate, template<class, class> class TOuterRange>
  849. struct predicate_builder : public tag_builder
  850. {
  851. template<class R, class P>
  852. using outer_range_type = TOuterRange<R, P>;
  853. using predicate_type = TPredicate;
  854. using this_type = predicate_builder<predicate_type, outer_range_type>;
  855. predicate_type predicate;
  856. template<class TRange>
  857. inline auto build(TRange&& range)
  858. {
  859. // CAUTION: we want no reference to a range here, because the passed range may be destroyed before used in outer_range_type
  860. using range_type = utl::mp_remove_ref<TRange>;
  861. return outer_range_type<range_type, predicate_type>(std::forward<TRange>(range), std::move(predicate));
  862. }
  863. inline predicate_builder(const predicate_type& p) :
  864. predicate(p)
  865. { LINQ_CTOR(); }
  866. inline predicate_builder(this_type&& other) :
  867. predicate(std::move(other).predicate)
  868. { LINQ_MOVE_CTOR(); }
  869. inline predicate_builder(const this_type&) = delete;
  870. inline ~predicate_builder()
  871. { LINQ_DTOR(); }
  872. };
  873. template<class TPredicate0, class TPredicate1, template<class, class, class> class TOuterRange>
  874. struct dual_predicate_builder : public tag_builder
  875. {
  876. template<class R, class P0, class P1>
  877. using outer_range_type = TOuterRange<R, P0, P1>;
  878. using predicate_0_type = TPredicate0;
  879. using predicate_1_type = TPredicate1;
  880. using this_type = dual_predicate_builder<predicate_0_type, predicate_1_type, outer_range_type>;
  881. predicate_0_type predicate0;
  882. predicate_1_type predicate1;
  883. template<class TRange>
  884. inline auto build(TRange&& range)
  885. {
  886. // CAUTION: we want no reference to a range here, because the passed range may be destroyed before used in outer_range_type
  887. using range_type = utl::mp_remove_ref<TRange>;
  888. return outer_range_type<range_type, predicate_0_type, predicate_1_type>(std::forward<range_type>(range), std::move(predicate0), std::move(predicate1));
  889. }
  890. inline dual_predicate_builder(const predicate_0_type& p0, const predicate_1_type& p1) :
  891. predicate0(p0),
  892. predicate1(p1)
  893. { LINQ_CTOR(); }
  894. inline dual_predicate_builder(this_type&& other) :
  895. predicate0(std::move(other).predicate0),
  896. predicate1(std::move(other).predicate1)
  897. { LINQ_MOVE_CTOR(); }
  898. inline dual_predicate_builder(const this_type&) = delete;
  899. inline ~dual_predicate_builder()
  900. { LINQ_DTOR(); }
  901. };
  902. struct count_builder : public tag_builder
  903. {
  904. template<class TRange>
  905. inline auto build(TRange&& range)
  906. {
  907. size_t ret = 0;
  908. while (range.next())
  909. ++ret;
  910. return ret;
  911. }
  912. };
  913. struct sum_builder : public tag_builder
  914. {
  915. template<class TRange>
  916. inline auto build(TRange&& range)
  917. {
  918. using value_type = mp_range_value_type<TRange>;
  919. using return_type = utl::mp_clean_type<value_type>;
  920. return_type sum = return_type();
  921. while (range.next())
  922. sum += range.front();
  923. return sum;
  924. }
  925. };
  926. struct min_builder : public tag_builder
  927. {
  928. template<class TRange>
  929. inline auto build(TRange&& range)
  930. {
  931. using value_type = mp_range_value_type<TRange>;
  932. using return_type = utl::mp_clean_type<value_type>;
  933. return_type ret = std::numeric_limits<return_type>::max();
  934. while (range.next())
  935. {
  936. if (ret > range.front())
  937. ret = range.front();
  938. }
  939. return ret;
  940. }
  941. };
  942. struct max_builder : public tag_builder
  943. {
  944. template<class TRange>
  945. inline auto build(TRange&& range)
  946. {
  947. using value_type = mp_range_value_type<TRange>;
  948. using return_type = utl::mp_clean_type<value_type>;
  949. return_type ret = std::numeric_limits<return_type>::min();
  950. while (range.next())
  951. {
  952. if (ret < range.front())
  953. ret = range.front();
  954. }
  955. return ret;
  956. }
  957. };
  958. struct any_builder : public tag_builder
  959. {
  960. template<class TRange>
  961. inline auto build(TRange&& range)
  962. { return range.next(); }
  963. };
  964. template <class T, class TPredicate>
  965. struct contains_builder : public tag_builder
  966. {
  967. using comperator_type = T;
  968. using predicate_type = TPredicate;
  969. using this_type = contains_builder<comperator_type, predicate_type>;
  970. comperator_type comperator;
  971. predicate_type predicate;
  972. template<class TRange>
  973. inline auto build(TRange&& range)
  974. {
  975. while(range.next())
  976. {
  977. if (predicate(comperator, range.front()))
  978. return true;
  979. }
  980. return false;
  981. }
  982. inline contains_builder(comperator_type&& c, predicate_type&& p) :
  983. comperator(c),
  984. predicate (p)
  985. { }
  986. };
  987. struct single_builder : public tag_builder
  988. {
  989. template<class TRange>
  990. inline auto build(TRange&& range)
  991. {
  992. if (!range.next())
  993. throw utl::Exception("range is empty");
  994. auto ret = std::move(range.front());
  995. if (range.next())
  996. throw utl::Exception("range contains more than one value");
  997. return ret;
  998. }
  999. };
  1000. struct single_or_default_builder : public tag_builder
  1001. {
  1002. template<class TRange>
  1003. inline auto build(TRange&& range)
  1004. {
  1005. using range_value_type = mp_range_value_type<TRange>;
  1006. using value_type = utl::mp_remove_ref<range_value_type>;
  1007. if (!range.next())
  1008. return value_type();
  1009. auto ret = std::move(range.front());
  1010. if (range.next())
  1011. return value_type();
  1012. return ret;
  1013. }
  1014. };
  1015. struct first_builder : public tag_builder
  1016. {
  1017. template<class TRange>
  1018. inline auto build(TRange&& range)
  1019. {
  1020. if (!range.next())
  1021. throw utl::Exception("range is empty");
  1022. return std::move(range.front());
  1023. }
  1024. };
  1025. struct first_or_default_builder : public tag_builder
  1026. {
  1027. template<class TRange>
  1028. inline auto build(TRange&& range)
  1029. {
  1030. using range_value_type = mp_range_value_type<TRange>;
  1031. using value_type = utl::mp_remove_ref<range_value_type>;
  1032. if (!range.next())
  1033. return value_type();
  1034. return std::move(range.front());
  1035. }
  1036. };
  1037. struct last_builder_base
  1038. {
  1039. template<class T>
  1040. struct cache
  1041. {
  1042. std::unique_ptr<T> value;
  1043. inline cache& operator=(T& t)
  1044. { value.reset(new T(std::move(t))); return *this; }
  1045. inline T& operator*()
  1046. { return *value; }
  1047. inline operator bool()
  1048. { return static_cast<bool>(value); }
  1049. inline cache()
  1050. { }
  1051. };
  1052. template<class T>
  1053. struct cache<T&>
  1054. {
  1055. T* value;
  1056. inline cache& operator=(T& t)
  1057. { value = &t; return *this; }
  1058. inline T& operator*()
  1059. { return *value; }
  1060. inline operator bool()
  1061. { return static_cast<bool>(value); }
  1062. inline cache() :
  1063. value(nullptr)
  1064. { }
  1065. };
  1066. };
  1067. struct last_builder : public tag_builder, public last_builder_base
  1068. {
  1069. template<class TRange>
  1070. inline auto build(TRange&& range)
  1071. {
  1072. using value_type = mp_range_value_type<TRange>;
  1073. using cache_type = cache<value_type>;
  1074. cache_type cache;
  1075. while(range.next())
  1076. cache = range.front();
  1077. if (!static_cast<bool>(cache))
  1078. throw utl::Exception("range is empty");
  1079. return std::move(*cache);
  1080. }
  1081. };
  1082. struct last_or_default_builder : public tag_builder, public last_builder_base
  1083. {
  1084. template<class TRange>
  1085. inline auto build(TRange&& range)
  1086. {
  1087. using range_value_type = mp_range_value_type<TRange>;
  1088. using value_type = utl::mp_remove_ref<range_value_type>;
  1089. using cache_type = cache<value_type>;
  1090. cache_type cache;
  1091. while(range.next())
  1092. cache = range.front();
  1093. if (!static_cast<bool>(cache))
  1094. return value_type();
  1095. return std::move(*cache);
  1096. }
  1097. };
  1098. struct to_vector_builder : public tag_builder
  1099. {
  1100. size_t capacity;
  1101. template<class TRange>
  1102. inline auto build(TRange&& range)
  1103. {
  1104. using range_value_type = mp_range_value_type<TRange>;
  1105. using value_type = utl::mp_remove_ref<range_value_type>;
  1106. using vector_type = std::vector<value_type>;
  1107. vector_type ret;
  1108. ret.reserve(capacity);
  1109. while (range.next())
  1110. ret.emplace_back(std::move(range.front()));
  1111. return ret;
  1112. }
  1113. inline to_vector_builder(size_t cap = 16) :
  1114. capacity(cap)
  1115. { }
  1116. };
  1117. struct to_list_builder : public tag_builder
  1118. {
  1119. template<class TRange>
  1120. inline auto build(TRange&& range)
  1121. {
  1122. using range_value_type = mp_range_value_type<TRange>;
  1123. using value_type = utl::mp_remove_ref<range_value_type>;
  1124. using list_type = std::list<value_type>;
  1125. list_type ret;
  1126. while (range.next())
  1127. ret.emplace_back(std::move(range.front()));
  1128. return ret;
  1129. }
  1130. };
  1131. template<class TKeyPredicate, class TValuePredicate>
  1132. struct to_map_builder : public tag_builder
  1133. {
  1134. using key_predicate_type = TKeyPredicate;
  1135. using value_predicate_type = TValuePredicate;
  1136. using this_type = to_map_builder<key_predicate_type, value_predicate_type>;
  1137. key_predicate_type key_predicate;
  1138. value_predicate_type value_predicate;
  1139. template<class TRange>
  1140. inline auto build(TRange&& range)
  1141. {
  1142. using range_type = TRange;
  1143. using range_value_type = mp_range_value_type<range_type>;
  1144. using key_type = decltype(std::declval<key_predicate_type>()(std::declval<range_value_type&>()));
  1145. using value_type = decltype(std::declval<value_predicate_type>()(std::declval<range_value_type&>()));
  1146. using map_type = std::map<utl::mp_remove_ref<key_type>, value_type>;
  1147. map_type map;
  1148. while (range.next())
  1149. {
  1150. auto ret = map.emplace(
  1151. key_predicate(range.front()),
  1152. value_predicate(range.front()));
  1153. if (!ret.second)
  1154. throw utl::Exception("duplicate key in range");
  1155. }
  1156. return map;
  1157. }
  1158. inline to_map_builder(const key_predicate_type& kp, const value_predicate_type& vp) :
  1159. key_predicate (kp),
  1160. value_predicate (vp)
  1161. { LINQ_CTOR(); }
  1162. };
  1163. template<class TPredicate>
  1164. struct for_each_builder : public tag_builder
  1165. {
  1166. using predicate_type = TPredicate;
  1167. using this_type = for_each_builder<predicate_type>;
  1168. predicate_type predicate;
  1169. template<class TRange>
  1170. inline auto build(TRange&& range)
  1171. {
  1172. while(range.next())
  1173. predicate(range.front());
  1174. }
  1175. inline for_each_builder(const predicate_type& p) :
  1176. predicate(p)
  1177. { }
  1178. };
  1179. template<class TKeyPredicate, class TValuePredicate>
  1180. struct to_lookup_builder : public tag_builder
  1181. {
  1182. using key_predicate_type = TKeyPredicate;
  1183. using value_predicate_type = TValuePredicate;
  1184. using this_type = to_lookup_builder<key_predicate_type, value_predicate_type>;
  1185. key_predicate_type key_predicate;
  1186. value_predicate_type value_predicate;
  1187. template<class TRange>
  1188. inline auto build(TRange&& range)
  1189. {
  1190. using range_type = TRange;
  1191. using range_value_type = mp_range_value_type<range_type>;
  1192. using key_type = decltype(std::declval<key_predicate_type>()(std::declval<range_value_type>()));
  1193. using value_type = decltype(std::declval<value_predicate_type>()(std::declval<range_value_type>()));
  1194. using lookup_type = lookup<key_type, value_type>;
  1195. return lookup_type::build(range, key_predicate, value_predicate);
  1196. }
  1197. inline to_lookup_builder(const key_predicate_type& kp, const value_predicate_type& vp) :
  1198. key_predicate (kp),
  1199. value_predicate (vp)
  1200. { LINQ_CTOR(); }
  1201. };
  1202. }
  1203. /* default operations ********************************************************************/
  1204. struct op_select_default
  1205. {
  1206. template<class T>
  1207. inline T operator()(T t)
  1208. { return t; }
  1209. };
  1210. struct op_less_default
  1211. {
  1212. template<class L, class R>
  1213. inline bool operator()(L&& l, R&& r) const
  1214. { return (l < r); }
  1215. };
  1216. struct op_compare_default
  1217. {
  1218. template<class L, class R>
  1219. inline bool operator()(L&& l, R&& r) const
  1220. { return (l == r); }
  1221. };
  1222. struct op_select_key_default
  1223. {
  1224. template<class TKey, class TValue>
  1225. inline auto operator()(std::pair<TKey, TValue>& p)
  1226. { return p.first; }
  1227. template<class TKey, class TValue>
  1228. inline auto operator()(std::tuple<TKey, TValue>& t)
  1229. { return std::get<0>(t); }
  1230. template<class T>
  1231. inline auto operator()(T& t)
  1232. { return t; }
  1233. };
  1234. struct op_select_value_default
  1235. {
  1236. template<class TKey, class TValue>
  1237. inline auto operator()(std::pair<TKey, TValue>& p)
  1238. { return p.second; }
  1239. template<class TKey, class TValue>
  1240. inline auto operator()(std::tuple<TKey, TValue>& t)
  1241. { return std::get<1>(t); }
  1242. template<class T>
  1243. inline auto operator()(T&& t)
  1244. { return std::forward<T>(t); }
  1245. };
  1246. /* constructors ******************************************************************************/
  1247. template<class TIterator>
  1248. inline auto from_iterator(TIterator&& beg, TIterator&& end)
  1249. { return __impl::iterator_range_wrapper<TIterator>(std::forward<TIterator>(beg), std::forward<TIterator>(end)); }
  1250. template<class TContainer>
  1251. inline auto from_container(TContainer&& container)
  1252. { return __impl::container_range_wrapper<TContainer>(std::forward<TContainer>(container)); }
  1253. template<class TPredicate>
  1254. inline auto from_generator(TPredicate&& predicate)
  1255. { return __impl::generator_range_wrapper<TPredicate>(std::forward<TPredicate>(predicate)); }
  1256. template<class TArray>
  1257. inline auto from_array(TArray&& array)
  1258. {
  1259. using array_type = typename std::remove_reference<TArray>::type;
  1260. using array_size = typename __impl::mp_array_properties<array_type>::size;
  1261. return from_iterator(&array[0], &array[array_size::value]);
  1262. }
  1263. /* filter ************************************************************************************/
  1264. template<class TPredicate>
  1265. inline auto where(TPredicate&& predicate)
  1266. { return __impl::predicate_builder<TPredicate, __impl::where_range_wrapper>(std::forward<TPredicate>(predicate)); }
  1267. template<class TPredicate>
  1268. inline auto select(TPredicate&& predicate)
  1269. { return __impl::predicate_builder<TPredicate, __impl::select_range_wrapper>(std::forward<TPredicate>(predicate)); }
  1270. template<class TPredicate>
  1271. inline auto select_many(TPredicate&& predicate)
  1272. { return __impl::predicate_builder<TPredicate, __impl::select_many_range_wrapper>(std::forward<TPredicate>(predicate)); }
  1273. template<class TSelectPredicate, class TLessPredicate>
  1274. inline auto order_by(TSelectPredicate&& sp, TLessPredicate&& lp)
  1275. { return __impl::dual_predicate_builder<TSelectPredicate, TLessPredicate, __impl::order_by_range_wrapper>(std::forward<TSelectPredicate>(sp), std::forward<TLessPredicate>(lp)); }
  1276. template<class TSelectPredicate>
  1277. inline auto order_by(TSelectPredicate&& sp)
  1278. { return order_by(std::forward(sp), op_less_default()); }
  1279. inline auto order_by()
  1280. { return order_by(op_select_default(), op_less_default()); }
  1281. template<class TLessPredicate>
  1282. inline auto distinct(TLessPredicate&& lp)
  1283. { return __impl::predicate_builder<TLessPredicate, __impl::distinct_range_wrapper>(std::forward<TLessPredicate>(lp)); }
  1284. inline auto distinct()
  1285. { return distinct(op_less_default()); }
  1286. /* result generators */
  1287. inline auto count()
  1288. { return __impl::count_builder(); }
  1289. inline auto sum()
  1290. { return __impl::sum_builder(); }
  1291. inline auto min()
  1292. { return __impl::min_builder(); }
  1293. inline auto max()
  1294. { return __impl::max_builder(); }
  1295. inline auto any()
  1296. { return __impl::any_builder(); }
  1297. template<class T, class TPredicate>
  1298. inline auto contains(T&& t, TPredicate&& p)
  1299. { return __impl::contains_builder<T, TPredicate>(std::forward<T>(t), std::forward<TPredicate>(p)); }
  1300. template<class T>
  1301. inline auto contains(T&& t)
  1302. { return contains(std::forward<T>(t), op_compare_default()); }
  1303. inline auto single()
  1304. { return __impl::single_builder(); }
  1305. inline auto single_or_default()
  1306. { return __impl::single_or_default_builder(); }
  1307. inline auto first()
  1308. { return __impl::first_builder(); }
  1309. inline auto first_or_default()
  1310. { return __impl::first_or_default_builder(); }
  1311. inline auto last()
  1312. { return __impl::last_builder(); }
  1313. inline auto last_or_default()
  1314. { return __impl::last_or_default_builder(); }
  1315. inline auto to_vector(size_t capacity = 16)
  1316. { return __impl::to_vector_builder(capacity); }
  1317. inline auto to_list()
  1318. { return __impl::to_list_builder(); }
  1319. template<class TKeyPredicate, class TValuePredicate>
  1320. inline auto to_map(TKeyPredicate&& kp, TValuePredicate&& vp)
  1321. { return __impl::to_map_builder<TKeyPredicate, TValuePredicate>(std::forward<TKeyPredicate>(kp), std::forward<TValuePredicate>(vp)); }
  1322. template<class TKeyPredicate>
  1323. inline auto to_map(TKeyPredicate&& kp)
  1324. { return to_map(std::forward<TKeyPredicate>(kp), std::move(op_select_value_default())); }
  1325. inline auto to_map()
  1326. { return to_map(std::move(op_select_key_default()), std::move(op_select_value_default())); }
  1327. template<class TPredicate>
  1328. inline auto for_each(TPredicate&& p)
  1329. { return __impl::for_each_builder<TPredicate>(std::forward<TPredicate>(p)); }
  1330. template<class TKeyPredicate, class TValuePredicate>
  1331. inline auto to_lookup(TKeyPredicate&& kp, TValuePredicate&& vp)
  1332. { return __impl::to_lookup_builder<TKeyPredicate, TValuePredicate>(std::forward<TKeyPredicate>(kp), std::forward<TValuePredicate>(vp)); }
  1333. template<class TKeyPredicate>
  1334. inline auto to_lookup(TKeyPredicate&& kp)
  1335. { return to_lookup(std::forward<TKeyPredicate>(kp), std::move(op_select_value_default())); }
  1336. inline auto to_lookup()
  1337. { return to_lookup(std::move(op_select_key_default()), std::move(op_select_value_default())); }
  1338. }