92ef9df04d0e92acf49c074d53caf14e087c4fed
[libcds.git] / tests / unit / pqueue / skiplist_pqueue.h
1 //$$CDS-header$$
2
3 #ifndef __CDSUNIT_SKIPLIST_PQUEUE_H
4 #define __CDSUNIT_SKIPLIST_PQUEUE_H
5
6 #include <cds/container/skip_list_set_hp.h>
7 #include <cds/container/skip_list_set_dhp.h>
8 #include <cds/urcu/general_instant.h>
9 #include <cds/urcu/general_buffered.h>
10 #include <cds/urcu/general_threaded.h>
11 #include <cds/urcu/signal_buffered.h>
12 #include <cds/urcu/signal_threaded.h>
13 #include <cds/container/skip_list_set_rcu.h>
14
15 namespace pqueue {
16
17     template <typename GC>
18     struct SkipListPQueue_pop_max
19     {
20         template <typename T, typename Set>
21         bool operator()( T& dest, Set& container ) const
22         {
23             typename Set::guarded_ptr gp;
24             bool bRet = container.extract_max( gp );
25             if ( bRet )
26                 dest = *gp;
27             return bRet;
28         }
29     };
30
31     template <typename RCU>
32     struct SkipListPQueue_pop_max< cds::urcu::gc<RCU> >
33     {
34         template <typename T, typename Set>
35         bool operator()( T& dest, Set& container ) const
36         {
37             typename Set::exempt_ptr ep( container.extract_max());
38             if ( ep )
39                 dest = *ep;
40             return !ep.empty();
41         }
42     };
43
44     template <typename GC>
45     struct SkipListPQueue_pop_min
46     {
47         template <typename T, typename Set>
48         bool operator()( T& dest, Set& container ) const
49         {
50             typename Set::guarded_ptr gp;
51             bool bRet = container.extract_min( gp );
52             if ( bRet )
53                 dest = *gp;
54             return bRet;
55         }
56     };
57
58     template <typename RCU>
59     struct SkipListPQueue_pop_min< cds::urcu::gc<RCU> >
60     {
61         template <typename T, typename Set>
62         bool operator()( T& dest, Set& container ) const
63         {
64             typename Set::exempt_ptr ep( container.extract_min());
65             if ( ep )
66                 dest = *ep;
67             return !ep.empty();
68         }
69     };
70
71     template <typename GC, typename T, typename Traits, bool Max=true>
72     class SkipListPQueue: protected cds::container::SkipListSet< GC, T, Traits >
73     {
74         typedef cds::container::SkipListSet< GC, T, Traits > base_class;
75         typedef T value_type;
76         template <typename GC2> friend struct SkipListPQueue_pop_max;
77         template <typename GC2> friend struct SkipListPQueue_pop_min;
78
79     public:
80         bool push( value_type const& val )
81         {
82             return base_class::insert( val );
83         }
84
85         bool pop( value_type& dest )
86         {
87             return Max ? SkipListPQueue_pop_max< typename base_class::gc >()( dest, *this )
88                        : SkipListPQueue_pop_min< typename base_class::gc >()( dest, *this );
89         }
90
91         void clear()
92         {
93             base_class::clear();
94         }
95
96         bool empty() const
97         {
98             return base_class::empty();
99         }
100
101         size_t size() const
102         {
103             return base_class::size();
104         }
105
106         typename base_class::stat const& statistics() const
107         {
108             return base_class::statistics();
109         }
110     };
111
112 } // namespace pqueue
113
114 #endif // #ifndef __CDSUNIT_SKIPLIST_PQUEUE_H