zoukankan      html  css  js  c++  java
  • class CBoDrvEmbeddedList

    节点内嵌prev/next指针的双向链表,减少link节点的内存分配。

    BoDrvEmbeddedList.h

      1 #ifndef BoDrvEmbeddedList_H
      2 #define BoDrvEmbeddedList_H
      3 
      4 #include <stdlib.h>
      5 #include <assert.h>
      6 
      7 #define NAMESPACE_BO_BEGIN namespace BO {
      8 #define NAMESPACE_BO_END }
      9 
     10 NAMESPACE_BO_BEGIN
     11 
     12 //////////////////////////////////////////////////////////////////////////
     13 // CBoDrvEmbeddedList
     14 
     15 class CBoDrvEmbeddedList
     16 {
     17 public:
     18     class CNode
     19     {
     20         friend CBoDrvEmbeddedList;
     21         template<class TYPE>
     22         friend class CBoDrvTypedEmbeddedList;
     23 
     24         CNode* pPrev;
     25         CNode* pNext;
     26 
     27     public:
     28         CNode()
     29             : pPrev(NULL)
     30             , pNext(NULL)
     31         {}
     32     };
     33 
     34 protected:
     35     CNode* CBoDrvEmbeddedList::node_ptr(void* p) const;
     36     void* CBoDrvEmbeddedList::void_ptr(CNode* pNode) const;
     37 
     38 public:
     39     CBoDrvEmbeddedList(size_t offset = 0);
     40     ~CBoDrvEmbeddedList(void);
     41 
     42     bool empty() const;
     43     size_t size() const;
     44 
     45     void push_front(void* p);
     46     void push_back(void* p);
     47 
     48     void* front() const;
     49     void* back() const;
     50 
     51     void pop_front();
     52     void pop_back();
     53 
     54     void clear();
     55     void clear(size_t offset);
     56 
     57 public:
     58     class iterator
     59     {
     60         friend class CBoDrvEmbeddedList;
     61         template<class TYPE>
     62         friend class CBoDrvTypedEmbeddedList;
     63 
     64         CNode* m_pNode;
     65         CBoDrvEmbeddedList* m_pList;
     66 
     67         iterator(CNode* pNode, CBoDrvEmbeddedList* pList);
     68 
     69     public:
     70         iterator(const iterator& other);
     71 
     72         iterator& operator=(const iterator& other);
     73 
     74         bool operator!=(const iterator& other) const;
     75         bool operator==(const iterator& other) const;
     76 
     77         iterator& operator++();
     78         iterator operator++(int);
     79 
     80         void* operator*() const;
     81     };
     82 
     83     iterator begin();
     84     iterator end();
     85     iterator erase(iterator i);
     86     iterator erase(iterator a, iterator b);
     87 
     88 private:
     89     CNode m_head;
     90     size_t m_size;
     91     size_t m_offset;
     92 };
     93 
     94 //////////////////////////////////////////////////////////////////////////
     95 // CBoDrvEmbeddedList inline functions
     96 
     97 inline CBoDrvEmbeddedList::CNode* CBoDrvEmbeddedList::node_ptr(void* p) const
     98 { return (CNode*)((char*)p + m_offset); }
     99 
    100 inline void* CBoDrvEmbeddedList::void_ptr(CBoDrvEmbeddedList::CNode* pNode) const
    101 { return (char*)pNode - m_offset; }
    102 
    103 inline bool CBoDrvEmbeddedList::empty() const
    104 { return m_head.pNext == &m_head; }
    105 
    106 inline size_t CBoDrvEmbeddedList::size() const
    107 { return m_size; }
    108 
    109 inline void* CBoDrvEmbeddedList::front() const
    110 {
    111     assert(!empty());
    112     return void_ptr(m_head.pNext);
    113 }
    114 
    115 inline void* CBoDrvEmbeddedList::back() const
    116 {
    117     assert(!empty());
    118     return void_ptr(m_head.pPrev);
    119 }
    120 
    121 inline void CBoDrvEmbeddedList::clear()
    122 {
    123 #ifndef NDEBUG
    124     (void)erase(begin(), end());
    125 #endif
    126     m_head.pPrev = &m_head;
    127     m_head.pNext = &m_head;
    128     m_size = 0;
    129 }
    130 
    131 inline void CBoDrvEmbeddedList::clear(size_t offset)
    132 {
    133     clear();
    134     m_offset = offset;
    135 }
    136 
    137 inline CBoDrvEmbeddedList::iterator CBoDrvEmbeddedList::begin()
    138 { return iterator(m_head.pNext, this); }
    139 
    140 inline CBoDrvEmbeddedList::iterator CBoDrvEmbeddedList::end()
    141 { return iterator(&m_head, this); }
    142 
    143 //////////////////////////////////////////////////////////////////////////
    144 // CBoDrvEmbeddedList::CIterator<TYPE> inline functions
    145 
    146 inline CBoDrvEmbeddedList::iterator::iterator(CNode* pNode, CBoDrvEmbeddedList* pList)
    147     : m_pNode(pNode)
    148     , m_pList(pList)
    149 {}
    150 
    151 inline CBoDrvEmbeddedList::iterator::iterator(const iterator& other)
    152     : m_pNode(other.m_pNode)
    153     , m_pList(other.m_pList)
    154 {}
    155 
    156 inline CBoDrvEmbeddedList::iterator& CBoDrvEmbeddedList::iterator::operator=(const iterator& other)
    157 {
    158     m_pNode = other.m_pNode;
    159     m_pList = other.m_pList;
    160     return *this;
    161 }
    162 
    163 inline bool CBoDrvEmbeddedList::iterator::operator!=(const iterator& other) const
    164 {
    165     assert(m_pList == other.m_pList);
    166     return m_pNode != other.m_pNode;
    167 }
    168 
    169 inline bool CBoDrvEmbeddedList::iterator::operator==(const iterator& other) const
    170 { return !(*this != other); }
    171 
    172 inline CBoDrvEmbeddedList::iterator& CBoDrvEmbeddedList::iterator::operator++()
    173 {
    174     assert(*this != m_pList->end());
    175     m_pNode = m_pNode->pNext;
    176     return *this;
    177 }
    178 
    179 inline CBoDrvEmbeddedList::iterator CBoDrvEmbeddedList::iterator::operator++(int)
    180 {
    181     iterator i(m_pNode, m_pList);
    182     assert(*this != m_pList->end());
    183     ++*this;
    184     return i;
    185 }
    186 
    187 inline void* CBoDrvEmbeddedList::iterator::operator*() const
    188 {
    189     assert(*this != m_pList->end());
    190     return m_pList->void_ptr(m_pNode);
    191 }
    192 
    193 //////////////////////////////////////////////////////////////////////////
    194 // CBoDrvTypedEmbeddedList<TYPE>
    195 
    196 template<class TYPE>
    197 class CBoDrvTypedEmbeddedList : public CBoDrvEmbeddedList
    198 {
    199     typedef CBoDrvEmbeddedList MyBase;
    200 
    201 public:
    202     CBoDrvTypedEmbeddedList(size_t offset = 0);
    203     ~CBoDrvTypedEmbeddedList();
    204 
    205     void push_front(TYPE* p);
    206     void push_back(TYPE* p);
    207 
    208     void* front() const;
    209     void* back() const;
    210 
    211 public:
    212     class iterator : public CBoDrvEmbeddedList::iterator
    213     {
    214         typedef CBoDrvEmbeddedList::iterator MyBase;
    215 
    216     public:
    217         iterator(const MyBase& other);
    218 
    219         iterator& operator=(const MyBase& other);
    220 
    221         TYPE* operator*() const;
    222         TYPE* operator->() const;
    223     };
    224 };
    225 
    226 //////////////////////////////////////////////////////////////////////////
    227 // CBoDrvTypedEmbeddedList<TYPE> inline functions
    228 
    229 template<class TYPE>
    230 inline CBoDrvTypedEmbeddedList<TYPE>::CBoDrvTypedEmbeddedList(size_t offset /* = 0 */)
    231     : MyBase(offset) {}
    232 
    233 template<class TYPE>
    234 inline CBoDrvTypedEmbeddedList<TYPE>::~CBoDrvTypedEmbeddedList()
    235 {}
    236 
    237 template<class TYPE>
    238 inline void CBoDrvTypedEmbeddedList<TYPE>::push_front(TYPE* p)
    239 { MyBase::push_front(p); }
    240 
    241 template<class TYPE>
    242 inline void CBoDrvTypedEmbeddedList<TYPE>::push_back(TYPE* p)
    243 { MyBase::push_back(p); }
    244 
    245 template<class TYPE>
    246 inline void* CBoDrvTypedEmbeddedList<TYPE>::front() const
    247 { return (TYPE*)MyBase::front(); }
    248 
    249 template<class TYPE>
    250 inline void* CBoDrvTypedEmbeddedList<TYPE>::back() const
    251 { return (TYPE*)MyBase::back(); }
    252 
    253 //////////////////////////////////////////////////////////////////////////
    254 // CBoDrvTypedEmbeddedList<TYPE>::iterator inline functions
    255 
    256 template<class TYPE>
    257 inline CBoDrvTypedEmbeddedList<TYPE>::iterator::iterator(const MyBase& other)
    258     : MyBase(other) {}
    259 
    260 template<class TYPE>
    261 inline typename CBoDrvTypedEmbeddedList<TYPE>::iterator& CBoDrvTypedEmbeddedList<TYPE>::iterator::operator=(const MyBase& other)
    262 {
    263     (MyBase&)*this = other;
    264     return *this;
    265 }
    266 
    267 template<class TYPE>
    268 inline TYPE* CBoDrvTypedEmbeddedList<TYPE>::iterator::operator*() const
    269 {  return (TYPE*)**(const MyBase*)this; }
    270 
    271 template<class TYPE>
    272 inline TYPE* CBoDrvTypedEmbeddedList<TYPE>::iterator::operator->() const
    273 { return (TYPE*)**this; }
    274 
    275 NAMESPACE_BO_END
    276 
    277 #endif // !BoDrvEmbeddedList_H

    BoDrvEmbeddedList.cpp

      1 #include "BoDrvEmbeddedList.h"
      2 
      3 NAMESPACE_BO_BEGIN
      4 
      5 //////////////////////////////////////////////////////////////////////////
      6 // CBoDrvEmbeddedList out-of-line functions
      7 
      8 CBoDrvEmbeddedList::CBoDrvEmbeddedList(size_t offset /* = 0 */)
      9     : m_size(0)
     10     , m_offset(offset)
     11 {
     12     m_head.pPrev = &m_head;
     13     m_head.pNext = &m_head;
     14 }
     15 
     16 
     17 CBoDrvEmbeddedList::~CBoDrvEmbeddedList(void)
     18 {
     19 #ifndef NDEBUG
     20     (void)erase(begin(), end());
     21 #endif
     22 }
     23 
     24 
     25 void CBoDrvEmbeddedList::push_front(void* p)
     26 {
     27     CNode* pNode = node_ptr(p);
     28     assert(NULL == pNode->pPrev && NULL == pNode->pNext);
     29 
     30     pNode->pNext = m_head.pNext;
     31     pNode->pPrev = &m_head;
     32     m_head.pNext->pPrev = pNode;
     33     m_head.pNext = pNode;
     34 
     35     ++m_size;
     36 }
     37 
     38 
     39 void CBoDrvEmbeddedList::push_back(void* p)
     40 {
     41     CNode* pNode = node_ptr(p);
     42     assert(NULL == pNode->pPrev && NULL == pNode->pNext);
     43 
     44     pNode->pPrev = m_head.pPrev;
     45     pNode->pNext = &m_head;
     46     m_head.pPrev->pNext = pNode;
     47     m_head.pPrev = pNode;
     48 
     49     ++m_size;
     50 }
     51 
     52 
     53 void CBoDrvEmbeddedList::pop_front()
     54 {
     55     assert(!empty());
     56 
     57     CNode* pNode = m_head.pNext;
     58     m_head.pNext = pNode->pNext;
     59     pNode->pNext->pPrev = &m_head;
     60 #ifndef NDEBUG
     61     pNode->pPrev = NULL;
     62     pNode->pNext = NULL;
     63 #endif
     64     --m_size;
     65 }
     66 
     67 
     68 void CBoDrvEmbeddedList::pop_back()
     69 {
     70     assert(!empty());
     71 
     72     CNode* pNode = m_head.pPrev;
     73 
     74     m_head.pPrev = pNode->pPrev;
     75     pNode->pPrev->pNext = &m_head;
     76 #ifndef NDEBUG
     77     pNode->pNext = NULL;
     78     pNode->pPrev = NULL;
     79 #endif
     80     --m_size;
     81 }
     82 
     83 
     84 CBoDrvEmbeddedList::iterator CBoDrvEmbeddedList::erase(iterator i)
     85 {
     86     assert(i != end());
     87 
     88     CNode* pNode = i.m_pNode;
     89     i.m_pNode = pNode->pNext;
     90 
     91     pNode->pPrev->pNext = pNode->pNext;
     92     pNode->pNext->pPrev = pNode->pPrev;
     93 #ifndef NDEBUG
     94     pNode->pPrev = NULL;
     95     pNode->pNext = NULL;
     96 #endif
     97     --m_size;
     98     return i;
     99 }
    100 
    101 
    102 CBoDrvEmbeddedList::iterator CBoDrvEmbeddedList::erase(iterator a, iterator b)
    103 {
    104     CNode* pBegin = a.m_pNode;
    105     CNode* pEnd = b.m_pNode;
    106 
    107     pBegin->pPrev->pNext = pEnd;
    108     pEnd->pPrev = pBegin->pPrev;
    109 
    110     for (; pBegin != pEnd; )
    111     {
    112         CNode* pNode = pBegin;
    113         pBegin = pBegin->pNext;
    114 #ifndef NDEBUG
    115         pNode->pPrev = NULL;
    116         pNode->pNext = NULL;
    117 #endif
    118         --m_size;
    119     }
    120 
    121     return b;
    122 }
    123 
    124 NAMESPACE_BO_END
  • 相关阅读:
    mysql复制那点事
    全排列问题
    56. Merge Interval
    2. Add Two Numbers
    20. Valid Parentheses
    121. Best Time to Buy and Sell Stock
    120. Triangle
    96. Unique Binary Search Trees
    91. Decode Ways
    72. Edit Distance
  • 原文地址:https://www.cnblogs.com/luning/p/7538436.html
Copyright © 2011-2022 走看看