further routing into wxApp
[wxWidgets.git] / include / wx / dlist.h
1 ///////////////////////////////////////////////////////////////////////////////
2 // Name: wx/dlist.h
3 // Purpose: wxDList<T> which is a template version of wxList
4 // Author: Robert Roebling
5 // Created: 18.09.2008
6 // Copyright: (c) 2008 wxWidgets team
7 // Licence: wxWindows licence
8 ///////////////////////////////////////////////////////////////////////////////
9
10 #ifndef _WX_DLIST_H_
11 #define _WX_DLIST_H_
12
13 #include "wx/defs.h"
14 #include "wx/utils.h"
15
16 #if wxUSE_STD_CONTAINERS
17
18 #include "wx/beforestd.h"
19 #include <algorithm>
20 #include <iterator>
21 #include <list>
22 #include "wx/afterstd.h"
23
24 template<typename T>
25 class wxDList: public std::list<T*>
26 {
27 private:
28 bool m_destroy;
29 typedef std::list<T*> BaseListType;
30 typedef wxDList<T> ListType;
31
32 public:
33 typedef typename BaseListType::iterator iterator;
34
35 class compatibility_iterator
36 {
37 private:
38 /* Workaround for broken VC6 nested class name resolution */
39 typedef typename BaseListType::iterator iterator;
40 friend class wxDList<T>;
41
42 iterator m_iter;
43 ListType *m_list;
44
45 public:
46 compatibility_iterator()
47 : m_iter(), m_list( NULL ) {}
48 compatibility_iterator( ListType* li, iterator i )
49 : m_iter( i ), m_list( li ) {}
50 compatibility_iterator( const ListType* li, iterator i )
51 : m_iter( i ), m_list( const_cast<ListType*>(li) ) {}
52
53 compatibility_iterator* operator->() { return this; }
54 const compatibility_iterator* operator->() const { return this; }
55
56 bool operator==(const compatibility_iterator& i) const
57 {
58 wxASSERT_MSG( m_list && i.m_list,
59 "comparing invalid iterators is illegal" );
60 return (m_list == i.m_list) && (m_iter == i.m_iter);
61 }
62 bool operator!=(const compatibility_iterator& i) const
63 { return !( operator==( i ) ); }
64 operator bool() const
65 { return m_list ? m_iter != m_list->end() : false; }
66 bool operator !() const
67 { return !( operator bool() ); }
68
69 T* GetData() const { return *m_iter; }
70 void SetData( T* e ) { *m_iter = e; }
71
72 compatibility_iterator GetNext() const
73 {
74 iterator i = m_iter;
75 return compatibility_iterator( m_list, ++i );
76 }
77
78 compatibility_iterator GetPrevious() const
79 {
80 if ( m_iter == m_list->begin() )
81 return compatibility_iterator();
82
83 iterator i = m_iter;
84 return compatibility_iterator( m_list, --i );
85 }
86
87 int IndexOf() const
88 {
89 return *this ? std::distance( m_list->begin(), m_iter )
90 : wxNOT_FOUND;
91 }
92 };
93
94 public:
95 wxDList() : m_destroy( false ) {}
96
97 ~wxDList() { Clear(); }
98
99 compatibility_iterator Find( const T* e ) const
100 {
101 return compatibility_iterator( this,
102 std::find( const_cast<ListType*>(this)->begin(),
103 const_cast<ListType*>(this)->end(), e ) );
104 }
105
106 bool IsEmpty() const
107 { return this->empty(); }
108 size_t GetCount() const
109 { return this->size(); }
110
111 compatibility_iterator Item( size_t idx ) const
112 {
113 iterator i = const_cast<ListType*>(this)->begin();
114 std::advance( i, idx );
115 return compatibility_iterator( this, i );
116 }
117
118 T* operator[](size_t idx) const
119 {
120 return Item(idx).GetData();
121 }
122
123 compatibility_iterator GetFirst() const
124 {
125 return compatibility_iterator( this, const_cast<ListType*>(this)->begin() );
126 }
127 compatibility_iterator GetLast() const
128 {
129 iterator i = const_cast<ListType*>(this)->end();
130 return compatibility_iterator( this, !(this->empty()) ? --i : i );
131 }
132 compatibility_iterator Member( T* e ) const
133 { return Find( e ); }
134 compatibility_iterator Nth( int n ) const
135 { return Item( n ); }
136 int IndexOf( T* e ) const
137 { return Find( e ).IndexOf(); }
138
139 compatibility_iterator Append( T* e )
140 {
141 this->push_back( e );
142 return GetLast();
143 }
144
145 compatibility_iterator Insert( T* e )
146 {
147 this->push_front( e );
148 return compatibility_iterator( this, this->begin() );
149 }
150
151 compatibility_iterator Insert( compatibility_iterator & i, T* e )
152 {
153 return compatibility_iterator( this, this->insert( i.m_iter, e ) );
154 }
155
156 compatibility_iterator Insert( size_t idx, T* e )
157 {
158 return compatibility_iterator( this,
159 this->insert( Item( idx ).m_iter, e ) );
160 }
161
162 void DeleteContents( bool destroy )
163 { m_destroy = destroy; }
164
165 bool GetDeleteContents() const
166 { return m_destroy; }
167
168 void Erase( const compatibility_iterator& i )
169 {
170 if ( m_destroy )
171 delete i->GetData();
172 this->erase( i.m_iter );
173 }
174
175 bool DeleteNode( const compatibility_iterator& i )
176 {
177 if( i )
178 {
179 Erase( i );
180 return true;
181 }
182 return false;
183 }
184
185 bool DeleteObject( T* e )
186 {
187 return DeleteNode( Find( e ) );
188 }
189
190 void Clear()
191 {
192 if ( m_destroy )
193 {
194 iterator it, en;
195 for ( it = this->begin(), en = this->end(); it != en; ++it )
196 delete *it;
197 }
198 this->clear();
199 }
200 };
201
202 #else // !wxUSE_STD_CONTAINERS
203
204 template <typename T>
205 class wxDList
206 {
207 public:
208 class Node
209 {
210 public:
211 Node(wxDList<T> *list = NULL,
212 Node *previous = NULL,
213 Node *next = NULL,
214 T *data = NULL)
215 {
216 m_list = list;
217 m_previous = previous;
218 m_next = next;
219 m_data = data;
220 if (previous)
221 previous->m_next = this;
222 if (next)
223 next->m_previous = this;
224 }
225
226 ~Node()
227 {
228 // handle the case when we're being deleted from the list by
229 // the user (i.e. not by the list itself from DeleteNode) -
230 // we must do it for compatibility with old code
231 if (m_list != NULL)
232 m_list->DetachNode(this);
233 }
234
235 void DeleteData()
236 {
237 delete m_data;
238 }
239
240 Node *GetNext() const { return m_next; }
241 Node *GetPrevious() const { return m_previous; }
242 T *GetData() const { return m_data; }
243 T **GetDataPtr() const { return &(wx_const_cast(nodetype*,this)->m_data); }
244 void SetData( T *data ) { m_data = data; }
245
246 int IndexOf() const
247 {
248 wxCHECK_MSG( m_list, wxNOT_FOUND,
249 "node doesn't belong to a list in IndexOf" );
250
251 int i;
252 Node *prev = m_previous;
253 for( i = 0; prev; i++ )
254 prev = prev->m_previous;
255 return i;
256 }
257
258 private:
259 T *m_data; // user data
260 Node *m_next, // next and previous nodes in the list
261 *m_previous;
262 wxDList<T> *m_list; // list we belong to
263
264 friend class wxDList<T>;
265 };
266
267 typedef Node nodetype;
268
269 class compatibility_iterator
270 {
271 public:
272 compatibility_iterator(nodetype *ptr = NULL) : m_ptr(ptr) { }
273 nodetype *operator->() const { return m_ptr; }
274 operator nodetype *() const { return m_ptr; }
275
276 private:
277 nodetype *m_ptr;
278 };
279
280 private:
281 void Init()
282 {
283 m_nodeFirst =
284 m_nodeLast = NULL;
285 m_count = 0;
286 m_destroy = false;
287 }
288
289 void DoDeleteNode( nodetype *node )
290 {
291 if ( m_destroy )
292 node->DeleteData();
293 // so that the node knows that it's being deleted by the list
294 node->m_list = NULL;
295 delete node;
296 }
297
298 size_t m_count; // number of elements in the list
299 bool m_destroy; // destroy user data when deleting list items?
300 nodetype *m_nodeFirst, // pointers to the head and tail of the list
301 *m_nodeLast;
302
303 public:
304 wxDList()
305 {
306 Init();
307 }
308
309 wxDList( const wxDList<T>& list )
310 {
311 Init();
312 Assign(list);
313 }
314
315 wxDList( size_t count, T *elements[] )
316 {
317 Init();
318 size_t n;
319 for (n = 0; n < count; n++)
320 Append( elements[n] );
321 }
322
323 wxDList& operator=( const wxDList<T>& list )
324 {
325 if (&list != this)
326 Assign(list);
327 return *this;
328 }
329
330 ~wxDList()
331 {
332 nodetype *each = m_nodeFirst;
333 while ( each != NULL )
334 {
335 nodetype *next = each->GetNext();
336 DoDeleteNode(each);
337 each = next;
338 }
339 }
340
341 void Assign(const wxDList<T> &list)
342 {
343 wxASSERT_MSG( !list.m_destroy,
344 "copying list which owns it's elements is a bad idea" );
345 Clear();
346 m_destroy = list.m_destroy;
347 m_nodeFirst = NULL;
348 m_nodeLast = NULL;
349 nodetype* node;
350 for (node = list.GetFirst(); node; node = node->GetNext() )
351 Append(node->GetData());
352 wxASSERT_MSG( m_count == list.m_count, "logic error in Assign()" );
353 }
354
355 nodetype *Append( T *object )
356 {
357 nodetype *node = new nodetype( this, m_nodeLast, NULL, object );
358
359 if ( !m_nodeFirst )
360 {
361 m_nodeFirst = node;
362 m_nodeLast = m_nodeFirst;
363 }
364 else
365 {
366 m_nodeLast->m_next = node;
367 m_nodeLast = node;
368 }
369 m_count++;
370 return node;
371 }
372
373 nodetype *Insert( T* object )
374 {
375 return Insert( NULL, object );
376 }
377
378 nodetype *Insert( size_t pos, T* object )
379 {
380 if (pos == m_count)
381 return Append( object );
382 else
383 return Insert( Item(pos), object );
384 }
385
386 nodetype *Insert( nodetype *position, T* object )
387 {
388 wxCHECK_MSG( !position || position->m_list == this, NULL,
389 "can't insert before a node from another list" );
390
391 // previous and next node for the node being inserted
392 nodetype *prev, *next;
393 if ( position )
394 {
395 prev = position->GetPrevious();
396 next = position;
397 }
398 else
399 {
400 // inserting in the beginning of the list
401 prev = NULL;
402 next = m_nodeFirst;
403 }
404 nodetype *node = new nodetype( this, prev, next, object );
405 if ( !m_nodeFirst )
406 m_nodeLast = node;
407 if ( prev == NULL )
408 m_nodeFirst = node;
409 m_count++;
410 return node;
411 }
412
413 nodetype *GetFirst() const { return m_nodeFirst; }
414 nodetype *GetLast() const { return m_nodeLast; }
415 size_t GetCount() const { return m_count; }
416 bool IsEmpty() const { return m_count == 0; }
417
418 void DeleteContents(bool destroy) { m_destroy = destroy; }
419 bool GetDeleteContents() const { return m_destroy; }
420
421 nodetype *Item(size_t index) const
422 {
423 for ( nodetype *current = GetFirst(); current; current = current->GetNext() )
424 {
425 if ( index-- == 0 )
426 return current;
427 }
428 wxFAIL_MSG( "invalid index in Item()" );
429 return NULL;
430 }
431
432 T *operator[](size_t index) const
433 {
434 nodetype *node = Item(index);
435 return node ? node->GetData() : NULL;
436 }
437
438 nodetype *DetachNode( nodetype *node )
439 {
440 wxCHECK_MSG( node, NULL, "detaching NULL wxNodeBase" );
441 wxCHECK_MSG( node->m_list == this, NULL,
442 "detaching node which is not from this list" );
443 // update the list
444 nodetype **prevNext = node->GetPrevious() ? &node->GetPrevious()->m_next
445 : &m_nodeFirst;
446 nodetype **nextPrev = node->GetNext() ? &node->GetNext()->m_previous
447 : &m_nodeLast;
448 *prevNext = node->GetNext();
449 *nextPrev = node->GetPrevious();
450 m_count--;
451 // mark the node as not belonging to this list any more
452 node->m_list = NULL;
453 return node;
454 }
455
456 void Erase( nodetype *node )
457 {
458 DeleteNode(node);
459 }
460
461 bool DeleteNode( nodetype *node )
462 {
463 if ( !DetachNode(node) )
464 return false;
465 DoDeleteNode(node);
466 return true;
467 }
468
469 bool DeleteObject( T *object )
470 {
471 for ( nodetype *current = GetFirst(); current; current = current->GetNext() )
472 {
473 if ( current->GetData() == object )
474 {
475 DeleteNode(current);
476 return true;
477 }
478 }
479 // not found
480 return false;
481 }
482
483 nodetype *Find(const T *object) const
484 {
485 for ( nodetype *current = GetFirst(); current; current = current->GetNext() )
486 {
487 if ( current->GetData() == object )
488 return current;
489 }
490 // not found
491 return NULL;
492 }
493
494 int IndexOf(const T *object) const
495 {
496 int n = 0;
497 for ( nodetype *current = GetFirst(); current; current = current->GetNext() )
498 {
499 if ( current->GetData() == object )
500 return n;
501 n++;
502 }
503 return wxNOT_FOUND;
504 }
505
506 void Clear()
507 {
508 nodetype *current = m_nodeFirst;
509 while ( current )
510 {
511 nodetype *next = current->GetNext();
512 DoDeleteNode(current);
513 current = next;
514 }
515 m_nodeFirst =
516 m_nodeLast = NULL;
517 m_count = 0;
518 }
519
520 void Reverse()
521 {
522 nodetype * node = m_nodeFirst;
523 nodetype* tmp;
524 while (node)
525 {
526 // swap prev and next pointers
527 tmp = node->m_next;
528 node->m_next = node->m_previous;
529 node->m_previous = tmp;
530 // this is the node that was next before swapping
531 node = tmp;
532 }
533 // swap first and last node
534 tmp = m_nodeFirst; m_nodeFirst = m_nodeLast; m_nodeLast = tmp;
535 }
536
537 void DeleteNodes(nodetype* first, nodetype* last)
538 {
539 nodetype * node = first;
540 while (node != last)
541 {
542 nodetype* next = node->GetNext();
543 DeleteNode(node);
544 node = next;
545 }
546 }
547
548 void ForEach(wxListIterateFunction F)
549 {
550 for ( nodetype *current = GetFirst(); current; current = current->GetNext() )
551 (*F)(current->GetData());
552 }
553
554 T *FirstThat(wxListIterateFunction F)
555 {
556 for ( nodetype *current = GetFirst(); current; current = current->GetNext() )
557 {
558 if ( (*F)(current->GetData()) )
559 return current->GetData();
560 }
561 return NULL;
562 }
563
564 T *LastThat(wxListIterateFunction F)
565 {
566 for ( nodetype *current = GetLast(); current; current = current->GetPrevious() )
567 {
568 if ( (*F)(current->GetData()) )
569 return current->GetData();
570 }
571 return NULL;
572 }
573
574 /* STL interface */
575 public:
576 typedef size_t size_type;
577 typedef int difference_type;
578 typedef T* value_type;
579 typedef value_type& reference;
580 typedef const value_type& const_reference;
581
582 class iterator
583 {
584 public:
585 typedef nodetype Node;
586 typedef iterator itor;
587 typedef T* value_type;
588 typedef value_type* ptr_type;
589 typedef value_type& reference;
590
591 Node* m_node;
592 Node* m_init;
593 public:
594 typedef reference reference_type;
595 typedef ptr_type pointer_type;
596
597 iterator(Node* node, Node* init) : m_node(node), m_init(init) {}
598 iterator() : m_node(NULL), m_init(NULL) { }
599 reference_type operator*() const
600 { return *m_node->GetDataPtr(); }
601 // ptrop
602 itor& operator++() { m_node = m_node->GetNext(); return *this; }
603 const itor operator++(int)
604 { itor tmp = *this; m_node = m_node->GetNext(); return tmp; }
605 itor& operator--()
606 {
607 m_node = m_node ? m_node->GetPrevious() : m_init;
608 return *this;
609 }
610 const itor operator--(int)
611 {
612 itor tmp = *this;
613 m_node = m_node ? m_node->GetPrevious() : m_init;
614 return tmp;
615 }
616 bool operator!=(const itor& it) const
617 { return it.m_node != m_node; }
618 bool operator==(const itor& it) const
619 { return it.m_node == m_node; }
620 };
621 class const_iterator
622 {
623 public:
624 typedef nodetype Node;
625 typedef T* value_type;
626 typedef const value_type& const_reference;
627 typedef const_iterator itor;
628 typedef value_type* ptr_type;
629
630 Node* m_node;
631 Node* m_init;
632 public:
633 typedef const_reference reference_type;
634 typedef const ptr_type pointer_type;
635
636 const_iterator(Node* node, Node* init)
637 : m_node(node), m_init(init) { }
638 const_iterator() : m_node(NULL), m_init(NULL) { }
639 const_iterator(const iterator& it)
640 : m_node(it.m_node), m_init(it.m_init) { }
641 reference_type operator*() const
642 { return *m_node->GetDataPtr(); }
643 // ptrop
644 itor& operator++() { m_node = m_node->GetNext(); return *this; }
645 const itor operator++(int)
646 { itor tmp = *this; m_node = m_node->GetNext(); return tmp; }
647 itor& operator--()
648 {
649 m_node = m_node ? m_node->GetPrevious() : m_init;
650 return *this;
651 }
652 const itor operator--(int)
653 {
654 itor tmp = *this;
655 m_node = m_node ? m_node->GetPrevious() : m_init;
656 return tmp;
657 }
658 bool operator!=(const itor& it) const
659 { return it.m_node != m_node; }
660 bool operator==(const itor& it) const
661 { return it.m_node == m_node; }
662 };
663
664 class reverse_iterator
665 {
666 public:
667 typedef nodetype Node;
668 typedef T* value_type;
669 typedef reverse_iterator itor;
670 typedef value_type* ptr_type;
671 typedef value_type& reference;
672
673 Node* m_node;
674 Node* m_init;
675 public:
676 typedef reference reference_type;
677 typedef ptr_type pointer_type;
678
679 reverse_iterator(Node* node, Node* init)
680 : m_node(node), m_init(init) { }
681 reverse_iterator() : m_node(NULL), m_init(NULL) { }
682 reference_type operator*() const
683 { return *m_node->GetDataPtr(); }
684 // ptrop
685 itor& operator++()
686 { m_node = m_node->GetPrevious(); return *this; }
687 const itor operator++(int)
688 { itor tmp = *this; m_node = m_node->GetPrevious(); return tmp; }
689 itor& operator--()
690 { m_node = m_node ? m_node->GetNext() : m_init; return *this; }
691 const itor operator--(int)
692 {
693 itor tmp = *this;
694 m_node = m_node ? m_node->GetNext() : m_init;
695 return tmp;
696 }
697 bool operator!=(const itor& it) const
698 { return it.m_node != m_node; }
699 bool operator==(const itor& it) const
700 { return it.m_node == m_node; }
701 };
702
703 class const_reverse_iterator
704 {
705 public:
706 typedef nodetype Node;
707 typedef T* value_type;
708 typedef const_reverse_iterator itor;
709 typedef value_type* ptr_type;
710 typedef const value_type& const_reference;
711
712 Node* m_node;
713 Node* m_init;
714 public:
715 typedef const_reference reference_type;
716 typedef const ptr_type pointer_type;
717
718 const_reverse_iterator(Node* node, Node* init)
719 : m_node(node), m_init(init) { }
720 const_reverse_iterator() : m_node(NULL), m_init(NULL) { }
721 const_reverse_iterator(const reverse_iterator& it)
722 : m_node(it.m_node), m_init(it.m_init) { }
723 reference_type operator*() const
724 { return *m_node->GetDataPtr(); }
725 // ptrop
726 itor& operator++()
727 { m_node = m_node->GetPrevious(); return *this; }
728 const itor operator++(int)
729 { itor tmp = *this; m_node = m_node->GetPrevious(); return tmp; }
730 itor& operator--()
731 { m_node = m_node ? m_node->GetNext() : m_init; return *this;}
732 const itor operator--(int)
733 {
734 itor tmp = *this;
735 m_node = m_node ? m_node->GetNext() : m_init;
736 return tmp;
737 }
738 bool operator!=(const itor& it) const
739 { return it.m_node != m_node; }
740 bool operator==(const itor& it) const
741 { return it.m_node == m_node; }
742 };
743
744 wxEXPLICIT wxDList(size_type n, const_reference v = value_type())
745 { assign(n, v); }
746 wxDList(const const_iterator& first, const const_iterator& last)
747 { assign(first, last); }
748 iterator begin() { return iterator(GetFirst(), GetLast()); }
749 const_iterator begin() const
750 { return const_iterator(GetFirst(), GetLast()); }
751 iterator end() { return iterator(NULL, GetLast()); }
752 const_iterator end() const { return const_iterator(NULL, GetLast()); }
753 reverse_iterator rbegin()
754 { return reverse_iterator(GetLast(), GetFirst()); }
755 const_reverse_iterator rbegin() const
756 { return const_reverse_iterator(GetLast(), GetFirst()); }
757 reverse_iterator rend() { return reverse_iterator(NULL, GetFirst()); }
758 const_reverse_iterator rend() const
759 { return const_reverse_iterator(NULL, GetFirst()); }
760 void resize(size_type n, value_type v = value_type())
761 {
762 while (n < size())
763 pop_back();
764 while (n > size())
765 push_back(v);
766 }
767 size_type size() const { return GetCount(); }
768 size_type max_size() const { return INT_MAX; }
769 bool empty() const { return IsEmpty(); }
770 reference front() { return *begin(); }
771 const_reference front() const { return *begin(); }
772 reference back() { iterator tmp = end(); return *--tmp; }
773 const_reference back() const { const_iterator tmp = end(); return *--tmp; }
774 void push_front(const_reference v = value_type())
775 { Insert(GetFirst(), v); }
776 void pop_front() { DeleteNode(GetFirst()); }
777 void push_back(const_reference v = value_type())
778 { Append( v ); }
779 void pop_back() { DeleteNode(GetLast()); }
780 void assign(const_iterator first, const const_iterator& last)
781 {
782 clear();
783 for(; first != last; ++first)
784 Append(*first);
785 }
786 void assign(size_type n, const_reference v = value_type())
787 {
788 clear();
789 for(size_type i = 0; i < n; ++i)
790 Append(v);
791 }
792 iterator insert(const iterator& it, const_reference v)
793 {
794 if (it == end())
795 Append( v );
796 else
797 Insert(it.m_node,v);
798 iterator itprev(it);
799 return itprev--;
800 }
801 void insert(const iterator& it, size_type n, const_reference v)
802 {
803 for(size_type i = 0; i < n; ++i)
804 Insert(it.m_node, v);
805 }
806 void insert(const iterator& it, const_iterator first, const const_iterator& last)
807 {
808 for(; first != last; ++first)
809 Insert(it.m_node, *first);
810 }
811 iterator erase(const iterator& it)
812 {
813 iterator next = iterator(it.m_node->GetNext(), GetLast());
814 DeleteNode(it.m_node); return next;
815 }
816 iterator erase(const iterator& first, const iterator& last)
817 {
818 iterator next = last; ++next;
819 DeleteNodes(first.m_node, last.m_node);
820 return next;
821 }
822 void clear() { Clear(); }
823 void splice(const iterator& it, wxDList<T>& l, const iterator& first, const iterator& last)
824 { insert(it, first, last); l.erase(first, last); }
825 void splice(const iterator& it, wxDList<T>& l)
826 { splice(it, l, l.begin(), l.end() ); }
827 void splice(const iterator& it, wxDList<T>& l, const iterator& first)
828 {
829 iterator tmp = first; ++tmp;
830 if(it == first || it == tmp) return;
831 insert(it, *first);
832 l.erase(first);
833 }
834 void remove(const_reference v)
835 { DeleteObject(v); }
836 void reverse()
837 { Reverse(); }
838 /* void swap(list<T>& l)
839 {
840 { size_t t = m_count; m_count = l.m_count; l.m_count = t; }
841 { bool t = m_destroy; m_destroy = l.m_destroy; l.m_destroy = t; }
842 { wxNodeBase* t = m_nodeFirst; m_nodeFirst = l.m_nodeFirst; l.m_nodeFirst = t; }
843 { wxNodeBase* t = m_nodeLast; m_nodeLast = l.m_nodeLast; l.m_nodeLast = t; }
844 { wxKeyType t = m_keyType; m_keyType = l.m_keyType; l.m_keyType = t; }
845 } */
846 };
847
848 #endif // wxUSE_STD_CONTAINERS/!wxUSE_STD_CONTAINERS
849
850 #endif // _WX_DLIST_H_