#ifndef _RC_HPP_ #define _RC_HPP_ #include #include #include #include #include #include #include #include #include #include #include "rs_iter.hpp" namespace rs { template class linear_container : public P { public: using P::P; template rs::iterator into_iter() const { if constexpr (!REV) { return rs::iterator{[this, iter = this->begin()] () mutable { if(iter == this->end()) return std::optional(); return std::optional(*iter++); }}; } else { return rs::iterator{[this, riter = this->rbegin()] () mutable { if(riter == this->rend()) return std::optional(); return std::optional(*riter++); }}; } } template rs::iterator into_iter_ptr() const { if constexpr (!REV) { return rs::iterator{[this, iter = this->cbegin()] () mutable { if(iter == this->cend()) return std::optional(); return std::optional(&*iter++); }}; } else { return rs::iterator{[this, riter = this->crbegin()] () mutable { if(riter == this->crend()) return std::optional(); return std::optional(&*riter++); }}; } } template rs::iterator into_iter_mptr() { if constexpr (!REV) { return rs::iterator{[this, iter = this->begin()] () mutable { if(iter == this->end()) return std::optional(); return std::optional(&*iter++); }}; } else { return rs::iterator{[this, riter = this->rbegin()] () mutable { if(riter == this->rend()) return std::optional(); return std::optional(&*riter++); }}; } } void collect_item(const TP& v) { this->push_back(v); } }; template > using vector = linear_container, TP>; template > using list = linear_container, TP>; template > using forward_list = linear_container, TP>; template > using deque = linear_container, TP>; template using array = linear_container, TP>; template class set_container : public S { public: using S::S; template rs::iterator into_iter() const { if constexpr (!REV || !CanRev) { return rs::iterator{[this, iter = this->begin()] () mutable { if(iter == this->end()) return std::optional(); return std::optional(*iter++); }}; } else { return rs::iterator{[this, riter = this->rbegin()] () mutable { if(riter == this->rend()) return std::optional(); return std::optional(*riter++); }}; } } template rs::iterator into_iter_ptr() const { if constexpr (!REV || !CanRev) { return rs::iterator{[this, iter = this->cbegin()] () mutable { if(iter == this->cend()) return std::optional(); return std::optional(&*iter++); }}; } else { return rs::iterator{[this, riter = this->crbegin()] () mutable { if(riter == this->crend()) return std::optional(); return std::optional(&*riter++); }}; } } void collect_item(const KEY& value) { this->insert(value); } }; template, typename ALLOC = std::allocator> using set = set_container, KEY, true>; template, typename ALLOC = std::allocator> using multiset = set_container, KEY, true>; template, typename PRED = std::equal_to, typename ALLOC = std::allocator> using unordered_set = set_container, KEY, false>; template, typename PRED = std::equal_to, typename ALLOC = std::allocator> using unordered_multiset = set_container, KEY, false>; template class map_container : public M { public: using M::M; template rs::iterator> into_iter() const { if constexpr (!REV || !CanRev) { return rs::iterator>{[this, iter = this->begin()] () mutable { if(iter == this->end()) return std::optional>(); return std::optional>(*iter++); }}; } else { return rs::iterator>{[this, riter = this->rbegin()] () mutable { if(riter == this->rend()) return std::optional>(); return std::optional>(*riter++); }}; } } template rs::iterator> into_iter_ptr() const { if constexpr (!REV || !CanRev) { return rs::iterator>{[this, iter = this->cbegin()] (bool rev) mutable { if(iter == this->cend()) return std::optional>(); auto ptr = &*iter++; return std::optional>(std::make_pair(&ptr->first, &ptr->second)); }}; } else { return rs::iterator>{[this, riter = this->crbegin()] (bool rev) mutable { if(riter == this->crend()) return std::optional>(); auto ptr = &*riter++; return std::optional>(std::make_pair(&ptr->first, &ptr->second)); }}; } } template rs::iterator> into_iter_mptr() { if constexpr (!REV || !CanRev) { return rs::iterator>{[this, iter = this->begin()] (bool rev) mutable { if(iter == this->end()) return std::optional>(); auto ptr = &*iter++; return std::optional>(std::make_pair(&ptr->first, &ptr->second)); }}; } else { return rs::iterator>{[this, riter = this->rbegin()] (bool rev) mutable { if(riter == this->rend()) return std::optional>(); auto ptr = &*riter++; return std::optional>(std::make_pair(&ptr->first, &ptr->second)); }}; } } rs::iterator keys() const { return into_iter().unzip().first; } rs::iterator keys_ptr() const { return into_iter_ptr().unzip().first; } rs::iterator values() const { return into_iter().unzip().second; } rs::iterator values_ptr() const { return into_iter_ptr().unzip().second; } void collect_item(const std::pair& value) { this->insert(value); } }; template, typename ALLOC = std::allocator>> using map = map_container, KEY, TP, true>; template, typename ALLOC = std::allocator>> using multimap = map_container, KEY, TP, true>; template, typename PRED = std::equal_to, typename ALLOC = std::allocator>> using unordered_map = map_container, KEY, TP, false>; template, typename PRED = std::equal_to, typename ALLOC = std::allocator>> using unordered_multimap = map_container, KEY, TP, false>; } #endif