xref: /freebsd-12.1/contrib/libc++/include/stack (revision 4ba319b5)
17a984708SDavid Chisnall// -*- C++ -*-
27a984708SDavid Chisnall//===---------------------------- stack -----------------------------------===//
37a984708SDavid Chisnall//
47a984708SDavid Chisnall//                     The LLVM Compiler Infrastructure
57a984708SDavid Chisnall//
67a984708SDavid Chisnall// This file is dual licensed under the MIT and the University of Illinois Open
77a984708SDavid Chisnall// Source Licenses. See LICENSE.TXT for details.
87a984708SDavid Chisnall//
97a984708SDavid Chisnall//===----------------------------------------------------------------------===//
107a984708SDavid Chisnall
117a984708SDavid Chisnall#ifndef _LIBCPP_STACK
127a984708SDavid Chisnall#define _LIBCPP_STACK
137a984708SDavid Chisnall
147a984708SDavid Chisnall/*
157a984708SDavid Chisnall    stack synopsis
167a984708SDavid Chisnall
177a984708SDavid Chisnallnamespace std
187a984708SDavid Chisnall{
197a984708SDavid Chisnall
207a984708SDavid Chisnalltemplate <class T, class Container = deque<T>>
217a984708SDavid Chisnallclass stack
227a984708SDavid Chisnall{
237a984708SDavid Chisnallpublic:
247a984708SDavid Chisnall    typedef Container                                container_type;
257a984708SDavid Chisnall    typedef typename container_type::value_type      value_type;
267a984708SDavid Chisnall    typedef typename container_type::reference       reference;
277a984708SDavid Chisnall    typedef typename container_type::const_reference const_reference;
287a984708SDavid Chisnall    typedef typename container_type::size_type       size_type;
297a984708SDavid Chisnall
307a984708SDavid Chisnallprotected:
317a984708SDavid Chisnall    container_type c;
327a984708SDavid Chisnall
337a984708SDavid Chisnallpublic:
347a984708SDavid Chisnall    stack() = default;
357a984708SDavid Chisnall    ~stack() = default;
367a984708SDavid Chisnall
377a984708SDavid Chisnall    stack(const stack& q) = default;
387a984708SDavid Chisnall    stack(stack&& q) = default;
397a984708SDavid Chisnall
407a984708SDavid Chisnall    stack& operator=(const stack& q) = default;
417a984708SDavid Chisnall    stack& operator=(stack&& q) = default;
427a984708SDavid Chisnall
437a984708SDavid Chisnall    explicit stack(const container_type& c);
447a984708SDavid Chisnall    explicit stack(container_type&& c);
457a984708SDavid Chisnall    template <class Alloc> explicit stack(const Alloc& a);
467a984708SDavid Chisnall    template <class Alloc> stack(const container_type& c, const Alloc& a);
477a984708SDavid Chisnall    template <class Alloc> stack(container_type&& c, const Alloc& a);
487a984708SDavid Chisnall    template <class Alloc> stack(const stack& c, const Alloc& a);
497a984708SDavid Chisnall    template <class Alloc> stack(stack&& c, const Alloc& a);
507a984708SDavid Chisnall
517a984708SDavid Chisnall    bool empty() const;
527a984708SDavid Chisnall    size_type size() const;
537a984708SDavid Chisnall    reference top();
547a984708SDavid Chisnall    const_reference top() const;
557a984708SDavid Chisnall
567a984708SDavid Chisnall    void push(const value_type& x);
577a984708SDavid Chisnall    void push(value_type&& x);
5898221d2eSDimitry Andric    template <class... Args> reference emplace(Args&&... args); // reference in C++17
597a984708SDavid Chisnall    void pop();
607a984708SDavid Chisnall
617c82a1ecSDimitry Andric    void swap(stack& c) noexcept(is_nothrow_swappable_v<Container>)
627a984708SDavid Chisnall};
637a984708SDavid Chisnall
64*4ba319b5SDimitry Andrictemplate<class Container>
65*4ba319b5SDimitry Andric  stack(Container) -> stack<typename Container::value_type, Container>;  // C++17
66*4ba319b5SDimitry Andric
67*4ba319b5SDimitry Andrictemplate<class Container, class Allocator>
68*4ba319b5SDimitry Andric  stack(Container, Allocator) -> stack<typename Container::value_type, Container>; // C++17
69*4ba319b5SDimitry Andric
707a984708SDavid Chisnalltemplate <class T, class Container>
717a984708SDavid Chisnall  bool operator==(const stack<T, Container>& x, const stack<T, Container>& y);
727a984708SDavid Chisnalltemplate <class T, class Container>
737a984708SDavid Chisnall  bool operator< (const stack<T, Container>& x, const stack<T, Container>& y);
747a984708SDavid Chisnalltemplate <class T, class Container>
757a984708SDavid Chisnall  bool operator!=(const stack<T, Container>& x, const stack<T, Container>& y);
767a984708SDavid Chisnalltemplate <class T, class Container>
777a984708SDavid Chisnall  bool operator> (const stack<T, Container>& x, const stack<T, Container>& y);
787a984708SDavid Chisnalltemplate <class T, class Container>
797a984708SDavid Chisnall  bool operator>=(const stack<T, Container>& x, const stack<T, Container>& y);
807a984708SDavid Chisnalltemplate <class T, class Container>
817a984708SDavid Chisnall  bool operator<=(const stack<T, Container>& x, const stack<T, Container>& y);
827a984708SDavid Chisnall
837a984708SDavid Chisnalltemplate <class T, class Container>
847a984708SDavid Chisnall  void swap(stack<T, Container>& x, stack<T, Container>& y)
857a984708SDavid Chisnall  noexcept(noexcept(x.swap(y)));
867a984708SDavid Chisnall
877a984708SDavid Chisnall}  // std
887a984708SDavid Chisnall
897a984708SDavid Chisnall*/
907a984708SDavid Chisnall
917a984708SDavid Chisnall#include <__config>
927a984708SDavid Chisnall#include <deque>
937a984708SDavid Chisnall
947a984708SDavid Chisnall#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
957a984708SDavid Chisnall#pragma GCC system_header
967a984708SDavid Chisnall#endif
977a984708SDavid Chisnall
987a984708SDavid Chisnall_LIBCPP_BEGIN_NAMESPACE_STD
997a984708SDavid Chisnall
100aed8d94eSDimitry Andrictemplate <class _Tp, class _Container = deque<_Tp> > class _LIBCPP_TEMPLATE_VIS stack;
1017a984708SDavid Chisnall
1027a984708SDavid Chisnalltemplate <class _Tp, class _Container>
103936e9439SDimitry Andric_LIBCPP_INLINE_VISIBILITY
1047a984708SDavid Chisnallbool
1057a984708SDavid Chisnalloperator==(const stack<_Tp, _Container>& __x, const stack<_Tp, _Container>& __y);
1067a984708SDavid Chisnall
1077a984708SDavid Chisnalltemplate <class _Tp, class _Container>
108936e9439SDimitry Andric_LIBCPP_INLINE_VISIBILITY
1097a984708SDavid Chisnallbool
1107a984708SDavid Chisnalloperator< (const stack<_Tp, _Container>& __x, const stack<_Tp, _Container>& __y);
1117a984708SDavid Chisnall
112854fa44bSDimitry Andrictemplate <class _Tp, class _Container /*= deque<_Tp>*/>
113aed8d94eSDimitry Andricclass _LIBCPP_TEMPLATE_VIS stack
1147a984708SDavid Chisnall{
1157a984708SDavid Chisnallpublic:
1167a984708SDavid Chisnall    typedef _Container                               container_type;
1177a984708SDavid Chisnall    typedef typename container_type::value_type      value_type;
1187a984708SDavid Chisnall    typedef typename container_type::reference       reference;
1197a984708SDavid Chisnall    typedef typename container_type::const_reference const_reference;
1207a984708SDavid Chisnall    typedef typename container_type::size_type       size_type;
1217c82a1ecSDimitry Andric    static_assert((is_same<_Tp, value_type>::value), "" );
1227a984708SDavid Chisnall
1237a984708SDavid Chisnallprotected:
1247a984708SDavid Chisnall    container_type c;
1257a984708SDavid Chisnall
1267a984708SDavid Chisnallpublic:
1277a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
1287a984708SDavid Chisnall    stack()
1297a984708SDavid Chisnall        _NOEXCEPT_(is_nothrow_default_constructible<container_type>::value)
1307a984708SDavid Chisnall        : c() {}
1317a984708SDavid Chisnall
1327a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
1337a984708SDavid Chisnall    stack(const stack& __q) : c(__q.c) {}
1347a984708SDavid Chisnall
135540d2a8bSDimitry Andric    _LIBCPP_INLINE_VISIBILITY
136540d2a8bSDimitry Andric    stack& operator=(const stack& __q) {c = __q.c; return *this;}
137540d2a8bSDimitry Andric
138540d2a8bSDimitry Andric
139540d2a8bSDimitry Andric#ifndef _LIBCPP_CXX03_LANG
1407a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
1417a984708SDavid Chisnall    stack(stack&& __q)
1427a984708SDavid Chisnall        _NOEXCEPT_(is_nothrow_move_constructible<container_type>::value)
1437a984708SDavid Chisnall        : c(_VSTD::move(__q.c)) {}
1447a984708SDavid Chisnall
1457a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
1467a984708SDavid Chisnall    stack& operator=(stack&& __q)
1477a984708SDavid Chisnall        _NOEXCEPT_(is_nothrow_move_assignable<container_type>::value)
1487a984708SDavid Chisnall        {c = _VSTD::move(__q.c); return *this;}
149540d2a8bSDimitry Andric
150540d2a8bSDimitry Andric    _LIBCPP_INLINE_VISIBILITY
151540d2a8bSDimitry Andric    explicit stack(container_type&& __c) : c(_VSTD::move(__c)) {}
152540d2a8bSDimitry Andric#endif  // _LIBCPP_CXX03_LANG
1537a984708SDavid Chisnall
1547a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
1557a984708SDavid Chisnall    explicit stack(const container_type& __c) : c(__c) {}
156540d2a8bSDimitry Andric
1577a984708SDavid Chisnall    template <class _Alloc>
1587a984708SDavid Chisnall        _LIBCPP_INLINE_VISIBILITY
1597a984708SDavid Chisnall        explicit stack(const _Alloc& __a,
1607a984708SDavid Chisnall                       typename enable_if<uses_allocator<container_type,
1617a984708SDavid Chisnall                                                         _Alloc>::value>::type* = 0)
1627a984708SDavid Chisnall            : c(__a) {}
1637a984708SDavid Chisnall    template <class _Alloc>
1647a984708SDavid Chisnall        _LIBCPP_INLINE_VISIBILITY
1657a984708SDavid Chisnall        stack(const container_type& __c, const _Alloc& __a,
1667a984708SDavid Chisnall              typename enable_if<uses_allocator<container_type,
1677a984708SDavid Chisnall                                                _Alloc>::value>::type* = 0)
1687a984708SDavid Chisnall            : c(__c, __a) {}
1697a984708SDavid Chisnall    template <class _Alloc>
1707a984708SDavid Chisnall        _LIBCPP_INLINE_VISIBILITY
1717a984708SDavid Chisnall        stack(const stack& __s, const _Alloc& __a,
1727a984708SDavid Chisnall              typename enable_if<uses_allocator<container_type,
1737a984708SDavid Chisnall                                                _Alloc>::value>::type* = 0)
1747a984708SDavid Chisnall            : c(__s.c, __a) {}
175540d2a8bSDimitry Andric#ifndef _LIBCPP_CXX03_LANG
1767a984708SDavid Chisnall    template <class _Alloc>
1777a984708SDavid Chisnall        _LIBCPP_INLINE_VISIBILITY
1787a984708SDavid Chisnall        stack(container_type&& __c, const _Alloc& __a,
1797a984708SDavid Chisnall              typename enable_if<uses_allocator<container_type,
1807a984708SDavid Chisnall                                                _Alloc>::value>::type* = 0)
1817a984708SDavid Chisnall            : c(_VSTD::move(__c), __a) {}
1827a984708SDavid Chisnall    template <class _Alloc>
1837a984708SDavid Chisnall        _LIBCPP_INLINE_VISIBILITY
1847a984708SDavid Chisnall        stack(stack&& __s, const _Alloc& __a,
1857a984708SDavid Chisnall              typename enable_if<uses_allocator<container_type,
1867a984708SDavid Chisnall                                                _Alloc>::value>::type* = 0)
1877a984708SDavid Chisnall            : c(_VSTD::move(__s.c), __a) {}
188540d2a8bSDimitry Andric#endif  // _LIBCPP_CXX03_LANG
1897a984708SDavid Chisnall
190b2c7081bSDimitry Andric    _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY
1917a984708SDavid Chisnall    bool empty()     const      {return c.empty();}
1927a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
1937a984708SDavid Chisnall    size_type size() const      {return c.size();}
1947a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
1957a984708SDavid Chisnall    reference top()             {return c.back();}
1967a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
1977a984708SDavid Chisnall    const_reference top() const {return c.back();}
1987a984708SDavid Chisnall
1997a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
2007a984708SDavid Chisnall    void push(const value_type& __v) {c.push_back(__v);}
201540d2a8bSDimitry Andric#ifndef _LIBCPP_CXX03_LANG
2027a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
2037a984708SDavid Chisnall    void push(value_type&& __v) {c.push_back(_VSTD::move(__v));}
204540d2a8bSDimitry Andric
2057a984708SDavid Chisnall    template <class... _Args>
2067a984708SDavid Chisnall        _LIBCPP_INLINE_VISIBILITY
20798221d2eSDimitry Andric#if _LIBCPP_STD_VER > 14
208*4ba319b5SDimitry Andric        decltype(auto) emplace(_Args&&... __args)
209aed8d94eSDimitry Andric        { return c.emplace_back(_VSTD::forward<_Args>(__args)...);}
21098221d2eSDimitry Andric#else
21198221d2eSDimitry Andric        void      emplace(_Args&&... __args)
21298221d2eSDimitry Andric        {        c.emplace_back(_VSTD::forward<_Args>(__args)...);}
21398221d2eSDimitry Andric#endif
214540d2a8bSDimitry Andric#endif  // _LIBCPP_CXX03_LANG
215540d2a8bSDimitry Andric
2167a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
2177a984708SDavid Chisnall    void pop() {c.pop_back();}
2187a984708SDavid Chisnall
2197a984708SDavid Chisnall    _LIBCPP_INLINE_VISIBILITY
2207a984708SDavid Chisnall    void swap(stack& __s)
2217a984708SDavid Chisnall        _NOEXCEPT_(__is_nothrow_swappable<container_type>::value)
2227a984708SDavid Chisnall    {
2237a984708SDavid Chisnall        using _VSTD::swap;
2247a984708SDavid Chisnall        swap(c, __s.c);
2257a984708SDavid Chisnall    }
2267a984708SDavid Chisnall
2277a984708SDavid Chisnall    template <class T1, class _C1>
2287a984708SDavid Chisnall    friend
2297a984708SDavid Chisnall    bool
2307a984708SDavid Chisnall    operator==(const stack<T1, _C1>& __x, const stack<T1, _C1>& __y);
2317a984708SDavid Chisnall
2327a984708SDavid Chisnall    template <class T1, class _C1>
2337a984708SDavid Chisnall    friend
2347a984708SDavid Chisnall    bool
2357a984708SDavid Chisnall    operator< (const stack<T1, _C1>& __x, const stack<T1, _C1>& __y);
2367a984708SDavid Chisnall};
2377a984708SDavid Chisnall
238*4ba319b5SDimitry Andric#ifndef _LIBCPP_HAS_NO_DEDUCTION_GUIDES
239*4ba319b5SDimitry Andrictemplate<class _Container,
240*4ba319b5SDimitry Andric         class = typename enable_if<!__is_allocator<_Container>::value, nullptr_t>::type
241*4ba319b5SDimitry Andric>
242*4ba319b5SDimitry Andricstack(_Container)
243*4ba319b5SDimitry Andric    -> stack<typename _Container::value_type, _Container>;
244*4ba319b5SDimitry Andric
245*4ba319b5SDimitry Andrictemplate<class _Container,
246*4ba319b5SDimitry Andric         class _Alloc,
247*4ba319b5SDimitry Andric         class = typename enable_if<!__is_allocator<_Container>::value, nullptr_t>::type,
248*4ba319b5SDimitry Andric         class = typename enable_if< __is_allocator<_Alloc>::value, nullptr_t>::type
249*4ba319b5SDimitry Andric         >
250*4ba319b5SDimitry Andricstack(_Container, _Alloc)
251*4ba319b5SDimitry Andric    -> stack<typename _Container::value_type, _Container>;
252*4ba319b5SDimitry Andric#endif
253*4ba319b5SDimitry Andric
2547a984708SDavid Chisnalltemplate <class _Tp, class _Container>
2557a984708SDavid Chisnallinline _LIBCPP_INLINE_VISIBILITY
2567a984708SDavid Chisnallbool
2577a984708SDavid Chisnalloperator==(const stack<_Tp, _Container>& __x, const stack<_Tp, _Container>& __y)
2587a984708SDavid Chisnall{
2597a984708SDavid Chisnall    return __x.c == __y.c;
2607a984708SDavid Chisnall}
2617a984708SDavid Chisnall
2627a984708SDavid Chisnalltemplate <class _Tp, class _Container>
2637a984708SDavid Chisnallinline _LIBCPP_INLINE_VISIBILITY
2647a984708SDavid Chisnallbool
2657a984708SDavid Chisnalloperator< (const stack<_Tp, _Container>& __x, const stack<_Tp, _Container>& __y)
2667a984708SDavid Chisnall{
2677a984708SDavid Chisnall    return __x.c < __y.c;
2687a984708SDavid Chisnall}
2697a984708SDavid Chisnall
2707a984708SDavid Chisnalltemplate <class _Tp, class _Container>
2717a984708SDavid Chisnallinline _LIBCPP_INLINE_VISIBILITY
2727a984708SDavid Chisnallbool
2737a984708SDavid Chisnalloperator!=(const stack<_Tp, _Container>& __x, const stack<_Tp, _Container>& __y)
2747a984708SDavid Chisnall{
2757a984708SDavid Chisnall    return !(__x == __y);
2767a984708SDavid Chisnall}
2777a984708SDavid Chisnall
2787a984708SDavid Chisnalltemplate <class _Tp, class _Container>
2797a984708SDavid Chisnallinline _LIBCPP_INLINE_VISIBILITY
2807a984708SDavid Chisnallbool
2817a984708SDavid Chisnalloperator> (const stack<_Tp, _Container>& __x, const stack<_Tp, _Container>& __y)
2827a984708SDavid Chisnall{
2837a984708SDavid Chisnall    return __y < __x;
2847a984708SDavid Chisnall}
2857a984708SDavid Chisnall
2867a984708SDavid Chisnalltemplate <class _Tp, class _Container>
2877a984708SDavid Chisnallinline _LIBCPP_INLINE_VISIBILITY
2887a984708SDavid Chisnallbool
2897a984708SDavid Chisnalloperator>=(const stack<_Tp, _Container>& __x, const stack<_Tp, _Container>& __y)
2907a984708SDavid Chisnall{
2917a984708SDavid Chisnall    return !(__x < __y);
2927a984708SDavid Chisnall}
2937a984708SDavid Chisnall
2947a984708SDavid Chisnalltemplate <class _Tp, class _Container>
2957a984708SDavid Chisnallinline _LIBCPP_INLINE_VISIBILITY
2967a984708SDavid Chisnallbool
2977a984708SDavid Chisnalloperator<=(const stack<_Tp, _Container>& __x, const stack<_Tp, _Container>& __y)
2987a984708SDavid Chisnall{
2997a984708SDavid Chisnall    return !(__y < __x);
3007a984708SDavid Chisnall}
3017a984708SDavid Chisnall
3027a984708SDavid Chisnalltemplate <class _Tp, class _Container>
3037a984708SDavid Chisnallinline _LIBCPP_INLINE_VISIBILITY
3047c82a1ecSDimitry Andrictypename enable_if<
3057c82a1ecSDimitry Andric    __is_swappable<_Container>::value,
3067a984708SDavid Chisnall    void
3077c82a1ecSDimitry Andric>::type
3087a984708SDavid Chisnallswap(stack<_Tp, _Container>& __x, stack<_Tp, _Container>& __y)
3097a984708SDavid Chisnall    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
3107a984708SDavid Chisnall{
3117a984708SDavid Chisnall    __x.swap(__y);
3127a984708SDavid Chisnall}
3137a984708SDavid Chisnall
3147a984708SDavid Chisnalltemplate <class _Tp, class _Container, class _Alloc>
315aed8d94eSDimitry Andricstruct _LIBCPP_TEMPLATE_VIS uses_allocator<stack<_Tp, _Container>, _Alloc>
3167a984708SDavid Chisnall    : public uses_allocator<_Container, _Alloc>
3177a984708SDavid Chisnall{
3187a984708SDavid Chisnall};
3197a984708SDavid Chisnall
3207a984708SDavid Chisnall_LIBCPP_END_NAMESPACE_STD
3217a984708SDavid Chisnall
3227a984708SDavid Chisnall#endif  // _LIBCPP_STACK
323