qiterator.h

Go to the documentation of this file.
00001 /****************************************************************************
00002 **
00003 ** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
00004 ** All rights reserved.
00005 ** Contact: Nokia Corporation (qt-info@nokia.com)
00006 **
00007 ** This file is part of the QtCore module of the Qt Toolkit.
00008 **
00009 ** $QT_BEGIN_LICENSE:LGPL$
00010 ** Commercial Usage
00011 ** Licensees holding valid Qt Commercial licenses may use this file in
00012 ** accordance with the Qt Commercial License Agreement provided with the
00013 ** Software or, alternatively, in accordance with the terms contained in
00014 ** a written agreement between you and Nokia.
00015 **
00016 ** GNU Lesser General Public License Usage
00017 ** Alternatively, this file may be used under the terms of the GNU Lesser
00018 ** General Public License version 2.1 as published by the Free Software
00019 ** Foundation and appearing in the file LICENSE.LGPL included in the
00020 ** packaging of this file.  Please review the following information to
00021 ** ensure the GNU Lesser General Public License version 2.1 requirements
00022 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
00023 **
00024 ** In addition, as a special exception, Nokia gives you certain additional
00025 ** rights.  These rights are described in the Nokia Qt LGPL Exception
00026 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this module.
00027 **
00028 ** GNU General Public License Usage
00029 ** Alternatively, this file may be used under the terms of the GNU
00030 ** General Public License version 3.0 as published by the Free Software
00031 ** Foundation and appearing in the file LICENSE.GPL included in the
00032 ** packaging of this file.  Please review the following information to
00033 ** ensure the GNU General Public License version 3.0 requirements will be
00034 ** met: http://www.gnu.org/copyleft/gpl.html.
00035 **
00036 ** If you have questions regarding the use of this file, please contact
00037 ** Nokia at qt-info@nokia.com.
00038 ** $QT_END_LICENSE$
00039 **
00040 ****************************************************************************/
00041 
00042 #ifndef QITERATOR_H
00043 #define QITERATOR_H
00044 
00045 #include <QtCore/qglobal.h>
00046 
00047 QT_BEGIN_HEADER
00048 
00049 namespace std {
00050     struct bidirectional_iterator_tag;
00051     struct random_access_iterator_tag;
00052 }
00053 
00054 QT_BEGIN_NAMESPACE
00055 
00056 QT_MODULE(Core)
00057 
00058 #define Q_DECLARE_SEQUENTIAL_ITERATOR(C) \
00059 \
00060 template <class T> \
00061 class Q##C##Iterator \
00062 { \
00063     typedef typename Q##C<T>::const_iterator const_iterator; \
00064     Q##C<T> c; \
00065     const_iterator i; \
00066 public: \
00067     inline Q##C##Iterator(const Q##C<T> &container) \
00068         : c(container), i(c.constBegin()) {} \
00069     inline Q##C##Iterator &operator=(const Q##C<T> &container) \
00070     { c = container; i = c.constBegin(); return *this; } \
00071     inline void toFront() { i = c.constBegin(); } \
00072     inline void toBack() { i = c.constEnd(); } \
00073     inline bool hasNext() const { return i != c.constEnd(); } \
00074     inline const T &next() { return *i++; } \
00075     inline const T &peekNext() const { return *i; } \
00076     inline bool hasPrevious() const { return i != c.constBegin(); } \
00077     inline const T &previous() { return *--i; } \
00078     inline const T &peekPrevious() const { const_iterator p = i; return *--p; } \
00079     inline bool findNext(const T &t) \
00080     { while (i != c.constEnd()) if (*i++ == t) return true; return false; } \
00081     inline bool findPrevious(const T &t) \
00082     { while (i != c.constBegin()) if (*(--i) == t) return true; \
00083       return false;  } \
00084 };
00085 
00086 #define Q_DECLARE_MUTABLE_SEQUENTIAL_ITERATOR(C) \
00087 \
00088 template <class T> \
00089 class QMutable##C##Iterator \
00090 { \
00091     typedef typename Q##C<T>::iterator iterator; \
00092     typedef typename Q##C<T>::const_iterator const_iterator; \
00093     Q##C<T> *c; \
00094     iterator i, n; \
00095     inline bool item_exists() const { return const_iterator(n) != c->constEnd(); } \
00096 public: \
00097     inline QMutable##C##Iterator(Q##C<T> &container) \
00098         : c(&container) \
00099     { c->setSharable(false); i = c->begin(); n = c->end(); } \
00100     inline ~QMutable##C##Iterator() \
00101     { c->setSharable(true); } \
00102     inline QMutable##C##Iterator &operator=(Q##C<T> &container) \
00103     { c->setSharable(true); c = &container; c->setSharable(false); \
00104       i = c->begin(); n = c->end(); return *this; } \
00105     inline void toFront() { i = c->begin(); n = c->end(); } \
00106     inline void toBack() { i = c->end(); n = i; } \
00107     inline bool hasNext() const { return c->constEnd() != const_iterator(i); } \
00108     inline T &next() { n = i++; return *n; } \
00109     inline T &peekNext() const { return *i; } \
00110     inline bool hasPrevious() const { return c->constBegin() != const_iterator(i); } \
00111     inline T &previous() { n = --i; return *n; } \
00112     inline T &peekPrevious() const { iterator p = i; return *--p; } \
00113     inline void remove() \
00114     { if (c->constEnd() != const_iterator(n)) { i = c->erase(n); n = c->end(); } } \
00115     inline void setValue(const T &t) const { if (c->constEnd() != const_iterator(n)) *n = t; } \
00116     inline T &value() { Q_ASSERT(item_exists()); return *n; } \
00117     inline const T &value() const { Q_ASSERT(item_exists()); return *n; } \
00118     inline void insert(const T &t) { n = i = c->insert(i, t); ++i; } \
00119     inline bool findNext(const T &t) \
00120     { while (c->constEnd() != const_iterator(n = i)) if (*i++ == t) return true; return false; } \
00121     inline bool findPrevious(const T &t) \
00122     { while (c->constBegin() != const_iterator(i)) if (*(n = --i) == t) return true; \
00123       n = c->end(); return false;  } \
00124 };
00125 
00126 #define Q_DECLARE_ASSOCIATIVE_ITERATOR(C) \
00127 \
00128 template <class Key, class T> \
00129 class Q##C##Iterator \
00130 { \
00131     typedef typename Q##C<Key,T>::const_iterator const_iterator; \
00132     typedef const_iterator Item; \
00133     Q##C<Key,T> c; \
00134     const_iterator i, n; \
00135     inline bool item_exists() const { return n != c.constEnd(); } \
00136 public: \
00137     inline Q##C##Iterator(const Q##C<Key,T> &container) \
00138         : c(container), i(c.constBegin()), n(c.constEnd()) {} \
00139     inline Q##C##Iterator &operator=(const Q##C<Key,T> &container) \
00140     { c = container; i = c.constBegin(); n = c.constEnd(); return *this; } \
00141     inline void toFront() { i = c.constBegin(); n = c.constEnd(); } \
00142     inline void toBack() { i = c.constEnd(); n = c.constEnd(); } \
00143     inline bool hasNext() const { return i != c.constEnd(); } \
00144     inline Item next() { n = i++; return n; } \
00145     inline Item peekNext() const { return i; } \
00146     inline bool hasPrevious() const { return i != c.constBegin(); } \
00147     inline Item previous() { n = --i; return n; } \
00148     inline Item peekPrevious() const { const_iterator p = i; return --p; } \
00149     inline const T &value() const { Q_ASSERT(item_exists()); return *n; } \
00150     inline const Key &key() const { Q_ASSERT(item_exists()); return n.key(); } \
00151     inline bool findNext(const T &t) \
00152     { while ((n = i) != c.constEnd()) if (*i++ == t) return true; return false; } \
00153     inline bool findPrevious(const T &t) \
00154     { while (i != c.constBegin()) if (*(n = --i) == t) return true; \
00155       n = c.constEnd(); return false; } \
00156 };
00157 
00158 #define Q_DECLARE_MUTABLE_ASSOCIATIVE_ITERATOR(C) \
00159 \
00160 template <class Key, class T> \
00161 class QMutable##C##Iterator \
00162 { \
00163     typedef typename Q##C<Key,T>::iterator iterator; \
00164     typedef typename Q##C<Key,T>::const_iterator const_iterator; \
00165     typedef iterator Item; \
00166     Q##C<Key,T> *c; \
00167     iterator i, n; \
00168     inline bool item_exists() const { return const_iterator(n) != c->constEnd(); } \
00169 public: \
00170     inline QMutable##C##Iterator(Q##C<Key,T> &container) \
00171         : c(&container) \
00172     { c->setSharable(false); i = c->begin(); n = c->end(); } \
00173     inline ~QMutable##C##Iterator() \
00174     { c->setSharable(true); } \
00175     inline QMutable##C##Iterator &operator=(Q##C<Key,T> &container) \
00176     { c->setSharable(true); c = &container; c->setSharable(false); i = c->begin(); n = c->end(); return *this; } \
00177     inline void toFront() { i = c->begin(); n = c->end(); } \
00178     inline void toBack() { i = c->end(); n = c->end(); } \
00179     inline bool hasNext() const { return const_iterator(i) != c->constEnd(); } \
00180     inline Item next() { n = i++; return n; } \
00181     inline Item peekNext() const { return i; } \
00182     inline bool hasPrevious() const { return const_iterator(i) != c->constBegin(); } \
00183     inline Item previous() { n = --i; return n; } \
00184     inline Item peekPrevious() const { iterator p = i; return --p; } \
00185     inline void remove() \
00186     { if (const_iterator(n) != c->constEnd()) { i = c->erase(n); n = c->end(); } } \
00187     inline void setValue(const T &t) { if (const_iterator(n) != c->constEnd()) *n = t; } \
00188     inline T &value() { Q_ASSERT(item_exists()); return *n; } \
00189     inline const T &value() const { Q_ASSERT(item_exists()); return *n; } \
00190     inline const Key &key() const { Q_ASSERT(item_exists()); return n.key(); } \
00191     inline bool findNext(const T &t) \
00192     { while (const_iterator(n = i) != c->constEnd()) if (*i++ == t) return true; return false; } \
00193     inline bool findPrevious(const T &t) \
00194     { while (const_iterator(i) != c->constBegin()) if (*(n = --i) == t) return true; \
00195       n = c->end(); return false; } \
00196 };
00197 
00198 QT_END_NAMESPACE
00199 
00200 QT_END_HEADER
00201 
00202 #endif // QITERATOR_H