-
From f1b6947e01b34583a9986b3bf02c66e621f6cb96 Mon Sep 17 00:00:00 2001
From: Mathias Bartl <mathiasbartl@web.de>
Date: Wed, 4 Apr 2012 11:06:29 +0200
Subject: [PATCH 1/6] ALL: Replace uses of List.reverse_begin() with
List.legacy_reverse_begin()
Common::List.legacy_reverse_begin() works like the old reverse_begin() did, for compitability, but is deprecated.
reverse_begin() did not work like in the STL, but did return an bidirectional forward iterator pointing at the end of the list,
instead of an bidirectional reverse iterator pointing at the end of the list.
Unit tests test for reverse iterators like in the STL, and fail the old implementation of reverse_begin().
All code that previously used reverse_begin() uses legacy_reverse_begin(), but works like before.
New code should not use legacy_reverse_begin()
Changes are for constant iterators as well as for iterators.
---
common/list.h | 14 ++++++++++++--
engines/agi/menu.cpp | 10 +++++-----
engines/agi/sprite.cpp | 4 ++--
engines/cine/various.cpp | 4 ++--
engines/composer/composer.cpp | 2 +-
engines/composer/graphics.cpp | 2 +-
engines/draci/animation.cpp | 2 +-
engines/dreamweb/stubs.cpp | 6 +++---
engines/gob/minigames/geisha/diving.cpp | 2 +-
engines/mohawk/livingbooks.cpp | 2 +-
engines/sci/engine/gc.cpp | 2 +-
engines/sci/graphics/animate.cpp | 4 ++--
engines/sci/graphics/ports.cpp | 2 +-
engines/sci/resource.cpp | 2 +-
engines/teenagent/scene.cpp | 2 +-
engines/tsage/debugger.cpp | 2 +-
engines/tsage/ringworld2/ringworld2_scenes0.cpp | 2 +-
test/common/list.h | 6 +++---
18 files changed, 40 insertions(+), 30 deletions(-)
diff --git a/common/list.h b/common/list.h
index 9792042..d2aaca3 100644
a
|
b
|
public:
|
211 | 211 | } |
212 | 212 | |
213 | 213 | iterator reverse_begin() { |
| 214 | return iterator(_anchor._prev);///<TODO FIXME use an actual backwards Iterator instead of an Forward Iterator |
| 215 | } |
| 216 | |
| 217 | /**DEPRACATED This is the old buggy version of reverse_begin(), use reverse_begin() instead, as sone as it has been fixed*/ |
| 218 | iterator legacy_reverse_begin(){ |
214 | 219 | return iterator(_anchor._prev); |
215 | 220 | } |
216 | 221 | |
… |
… |
public:
|
222 | 227 | return const_iterator(_anchor._next); |
223 | 228 | } |
224 | 229 | |
225 | | const_iterator reverse_begin() const { |
| 230 | /**DEPRACATED This is the old buggy version of reverse_begin(), use reverse_begin() instead, as sone as it has been fixed*/ |
| 231 | const_iterator legacy_reverse_begin() const { |
226 | 232 | return const_iterator(_anchor._prev); |
227 | 233 | } |
228 | 234 | |
| 235 | const_iterator reverse_begin() const { |
| 236 | return const_iterator(_anchor._prev);///<TODO FIXME use an actual backwards Iterator instead of an Forward Iterator |
| 237 | } |
| 238 | |
229 | 239 | const_iterator end() const { |
230 | 240 | return const_iterator(const_cast<NodeBase *>(&_anchor)); |
231 | 241 | } |
… |
… |
protected:
|
252 | 262 | newNode->_prev->_next = newNode; |
253 | 263 | newNode->_next->_prev = newNode; |
254 | 264 | } |
255 | | }; |
| 265 | };///< TODO add reverse_end() |
256 | 266 | |
257 | 267 | } // End of namespace Common |
258 | 268 | |
-
diff --git a/engines/agi/menu.cpp b/engines/agi/menu.cpp
index cac1701..ae711ed 100644
a
|
b
|
Menu::Menu(AgiEngine *vm, GfxMgr *gfx, PictureMgr *picture) {
|
177 | 177 | |
178 | 178 | Menu::~Menu() { |
179 | 179 | MenuList::iterator iterh; |
180 | | for (iterh = _menubar.reverse_begin(); iterh != _menubar.end(); ) { |
| 180 | for (iterh = _menubar.legacy_reverse_begin(); iterh != _menubar.end(); ) { |
181 | 181 | AgiMenu *m = *iterh; |
182 | 182 | |
183 | 183 | debugC(3, kDebugLevelMenu, "deiniting hmenu %s", m->text); |
184 | 184 | |
185 | 185 | MenuOptionList::iterator iterv; |
186 | 186 | |
187 | | for (iterv = m->down.reverse_begin(); iterv != m->down.end(); ) { |
| 187 | for (iterv = m->down.legacy_reverse_begin(); iterv != m->down.end(); ) { |
188 | 188 | AgiMenuOption *d = *iterv; |
189 | 189 | |
190 | 190 | debugC(3, kDebugLevelMenu, " deiniting vmenu %s", d->text); |
… |
… |
void Menu::addItem(const char *s, int code) {
|
233 | 233 | d->index = _vIndex++; |
234 | 234 | |
235 | 235 | // add to last menu in list |
236 | | assert(_menubar.reverse_begin() != _menubar.end()); |
237 | | AgiMenu *m = *_menubar.reverse_begin(); |
| 236 | assert(_menubar.legacy_reverse_begin() != _menubar.end()); |
| 237 | AgiMenu *m = *_menubar.legacy_reverse_begin(); |
238 | 238 | m->height++; |
239 | 239 | |
240 | 240 | _vMaxMenu[m->index] = d->index; |
… |
… |
void Menu::submit() {
|
259 | 259 | |
260 | 260 | // If a menu has no options, delete it |
261 | 261 | MenuList::iterator iter; |
262 | | for (iter = _menubar.reverse_begin(); iter != _menubar.end(); ) { |
| 262 | for (iter = _menubar.legacy_reverse_begin(); iter != _menubar.end(); ) { |
263 | 263 | AgiMenu *m = *iter; |
264 | 264 | |
265 | 265 | if (m->down.empty()) { |
-
diff --git a/engines/agi/sprite.cpp b/engines/agi/sprite.cpp
index ea2d329..f4ab696 100644
a
|
b
|
void SpritesMgr::buildNonupdBlitlist() {
|
375 | 375 | */ |
376 | 376 | void SpritesMgr::freeList(SpriteList &l) { |
377 | 377 | SpriteList::iterator iter; |
378 | | for (iter = l.reverse_begin(); iter != l.end(); ) { |
| 378 | for (iter = l.legacy_reverse_begin(); iter != l.end(); ) { |
379 | 379 | Sprite* s = *iter; |
380 | 380 | |
381 | 381 | poolRelease(s->buffer); |
… |
… |
void SpritesMgr::commitSprites(SpriteList &l, bool immediate) {
|
422 | 422 | */ |
423 | 423 | void SpritesMgr::eraseSprites(SpriteList &l) { |
424 | 424 | SpriteList::iterator iter; |
425 | | for (iter = l.reverse_begin(); iter != l.end(); --iter) { |
| 425 | for (iter = l.legacy_reverse_begin(); iter != l.end(); --iter) { |
426 | 426 | Sprite *s = *iter; |
427 | 427 | objsRestoreArea(s); |
428 | 428 | } |
-
diff --git a/engines/cine/various.cpp b/engines/cine/various.cpp
index 9b73ae1..d069547 100644
a
|
b
|
int16 getObjectUnderCursor(uint16 x, uint16 y) {
|
222 | 222 | int width; |
223 | 223 | |
224 | 224 | // reverse_iterator would be nice |
225 | | for (it = g_cine->_overlayList.reverse_begin(); it != g_cine->_overlayList.end(); --it) { |
| 225 | for (it = g_cine->_overlayList.legacy_reverse_begin(); it != g_cine->_overlayList.end(); --it) { |
226 | 226 | if (it->type >= 2 || !g_cine->_objectTable[it->objIdx].name[0]) { |
227 | 227 | continue; |
228 | 228 | } |
… |
… |
void resetGfxEntityEntry(uint16 objIdx) {
|
1471 | 1471 | } |
1472 | 1472 | |
1473 | 1473 | if (g_cine->_objectTable[objIdx].mask > objectMask) { // Check for B objects' cut point |
1474 | | bObjsCutPoint = bObjs.reverse_begin(); |
| 1474 | bObjsCutPoint = bObjs.legacy_reverse_begin(); |
1475 | 1475 | foundCutPoint = true; |
1476 | 1476 | } |
1477 | 1477 | } |
-
diff --git a/engines/composer/composer.cpp b/engines/composer/composer.cpp
index 556dad7..e9b40a2 100644
a
|
b
|
bool Button::contains(const Common::Point &pos) const {
|
630 | 630 | |
631 | 631 | const Button *ComposerEngine::getButtonFor(const Sprite *sprite, const Common::Point &pos) { |
632 | 632 | for (Common::List<Library>::iterator l = _libraries.begin(); l != _libraries.end(); l++) { |
633 | | for (Common::List<Button>::iterator i = l->_buttons.reverse_begin(); i != l->_buttons.end(); --i) { |
| 633 | for (Common::List<Button>::iterator i = l->_buttons.legacy_reverse_begin(); i != l->_buttons.end(); --i) { |
634 | 634 | if (!i->_active) |
635 | 635 | continue; |
636 | 636 | |
-
diff --git a/engines/composer/graphics.cpp b/engines/composer/graphics.cpp
index 1314e90..d514d91 100644
a
|
b
|
void ComposerEngine::removeSprite(uint16 id, uint16 animId) {
|
493 | 493 | } |
494 | 494 | |
495 | 495 | const Sprite *ComposerEngine::getSpriteAtPos(const Common::Point &pos) { |
496 | | for (Common::List<Sprite>::iterator i = _sprites.reverse_begin(); i != _sprites.end(); --i) { |
| 496 | for (Common::List<Sprite>::iterator i = _sprites.legacy_reverse_begin(); i != _sprites.end(); --i) { |
497 | 497 | // avoid highest-level objects (e.g. the cursor) |
498 | 498 | if (!i->_zorder) |
499 | 499 | continue; |
-
diff --git a/engines/draci/animation.cpp b/engines/draci/animation.cpp
index 6e6f167..f114aee 100644
a
|
b
|
const Animation *AnimationManager::getTopAnimation(int x, int y) const {
|
499 | 499 | // Get transparent color for the current screen |
500 | 500 | const int transparent = _vm->_screen->getSurface()->getTransparentColor(); |
501 | 501 | |
502 | | for (it = _animations.reverse_begin(); it != _animations.end(); --it) { |
| 502 | for (it = _animations.legacy_reverse_begin(); it != _animations.end(); --it) { |
503 | 503 | |
504 | 504 | Animation *anim = *it; |
505 | 505 | |
-
diff --git a/engines/dreamweb/stubs.cpp b/engines/dreamweb/stubs.cpp
index 8226982..d1d1b84 100644
a
|
b
|
bool DreamWebEngine::checkIfPerson(uint8 x, uint8 y) {
|
1222 | 1222 | |
1223 | 1223 | bool DreamWebEngine::checkIfFree(uint8 x, uint8 y) { |
1224 | 1224 | Common::List<ObjPos>::const_iterator i; |
1225 | | for (i = _freeList.reverse_begin(); i != _freeList.end(); --i) { |
| 1225 | for (i = _freeList.legacy_reverse_begin(); i != _freeList.end(); --i) { |
1226 | 1226 | const ObjPos &pos = *i; |
1227 | 1227 | assert(pos.index != 0xff); |
1228 | 1228 | if (!pos.contains(x,y)) |
… |
… |
bool DreamWebEngine::checkIfFree(uint8 x, uint8 y) {
|
1235 | 1235 | |
1236 | 1236 | bool DreamWebEngine::checkIfEx(uint8 x, uint8 y) { |
1237 | 1237 | Common::List<ObjPos>::const_iterator i; |
1238 | | for (i = _exList.reverse_begin(); i != _exList.end(); --i) { |
| 1238 | for (i = _exList.legacy_reverse_begin(); i != _exList.end(); --i) { |
1239 | 1239 | const ObjPos &pos = *i; |
1240 | 1240 | assert(pos.index != 0xff); |
1241 | 1241 | if (!pos.contains(x,y)) |
… |
… |
void DreamWebEngine::showIcon() {
|
1747 | 1747 | |
1748 | 1748 | bool DreamWebEngine::checkIfSet(uint8 x, uint8 y) { |
1749 | 1749 | Common::List<ObjPos>::const_iterator i; |
1750 | | for (i = _setList.reverse_begin(); i != _setList.end(); --i) { |
| 1750 | for (i = _setList.legacy_reverse_begin(); i != _setList.end(); --i) { |
1751 | 1751 | const ObjPos &pos = *i; |
1752 | 1752 | assert(pos.index != 0xff); |
1753 | 1753 | if (!pos.contains(x,y)) |
-
diff --git a/engines/gob/minigames/geisha/diving.cpp b/engines/gob/minigames/geisha/diving.cpp
index 6f4c6e1..e69d344 100644
a
|
b
|
void Diving::updateAnims() {
|
703 | 703 | int16 left, top, right, bottom; |
704 | 704 | |
705 | 705 | // Clear the previous animation frames |
706 | | for (Common::List<ANIObject *>::iterator a = _anims.reverse_begin(); |
| 706 | for (Common::List<ANIObject *>::iterator a = _anims.legacy_reverse_begin(); |
707 | 707 | a != _anims.end(); --a) { |
708 | 708 | |
709 | 709 | (*a)->clear(*_vm->_draw->_backSurface, left, top, right, bottom); |
-
diff --git a/engines/mohawk/livingbooks.cpp b/engines/mohawk/livingbooks.cpp
index 708478a..4f40214 100644
a
|
b
|
void MohawkEngine_LivingBooks::updatePage() {
|
606 | 606 | _items[i]->update(); |
607 | 607 | |
608 | 608 | if (_needsRedraw) { |
609 | | for (Common::List<LBItem *>::const_iterator i = _orderedItems.reverse_begin(); i != _orderedItems.end(); --i) |
| 609 | for (Common::List<LBItem *>::const_iterator i = _orderedItems.legacy_reverse_begin(); i != _orderedItems.end(); --i) |
610 | 610 | (*i)->draw(); |
611 | 611 | |
612 | 612 | _needsRedraw = false; |
-
diff --git a/engines/sci/engine/gc.cpp b/engines/sci/engine/gc.cpp
index 2d71878..00b96a6 100644
a
|
b
|
AddrSet *findAllActiveReferences(EngineState *s) {
|
106 | 106 | |
107 | 107 | // Initialize value stack |
108 | 108 | // We do this one by hand since the stack doesn't know the current execution stack |
109 | | Common::List<ExecStack>::const_iterator iter = s->_executionStack.reverse_begin(); |
| 109 | Common::List<ExecStack>::const_iterator iter = s->_executionStack.legacy_reverse_begin(); |
110 | 110 | |
111 | 111 | // Skip fake kernel stack frame if it's on top |
112 | 112 | if ((*iter).type == EXEC_STACK_TYPE_KERNEL) |
-
diff --git a/engines/sci/graphics/animate.cpp b/engines/sci/graphics/animate.cpp
index 983e697..a2d0514 100644
a
|
b
|
void GfxAnimate::update() {
|
328 | 328 | const AnimateList::iterator end = _list.end(); |
329 | 329 | |
330 | 330 | // Remove all no-update cels, if requested |
331 | | for (it = _list.reverse_begin(); it != end; --it) { |
| 331 | for (it = _list.legacy_reverse_begin(); it != end; --it) { |
332 | 332 | if (it->signal & kSignalNoUpdate) { |
333 | 333 | if (!(it->signal & kSignalRemoveView)) { |
334 | 334 | bitsHandle = readSelector(_s->_segMan, it->object, SELECTOR(underBits)); |
… |
… |
void GfxAnimate::restoreAndDelete(int argc, reg_t *argv) {
|
474 | 474 | writeSelectorValue(_s->_segMan, it->object, SELECTOR(signal), it->signal); |
475 | 475 | } |
476 | 476 | |
477 | | for (it = _list.reverse_begin(); it != end; --it) { |
| 477 | for (it = _list.legacy_reverse_begin(); it != end; --it) { |
478 | 478 | // We read out signal here again, this is not by accident but to ensure |
479 | 479 | // that we got an up-to-date signal |
480 | 480 | it->signal = readSelectorValue(_s->_segMan, it->object, SELECTOR(signal)); |
-
diff --git a/engines/sci/graphics/ports.cpp b/engines/sci/graphics/ports.cpp
index 6b4c818..259b558 100644
a
|
b
|
int16 GfxPorts::isFrontWindow(Window *pWnd) {
|
242 | 242 | |
243 | 243 | void GfxPorts::beginUpdate(Window *wnd) { |
244 | 244 | Port *oldPort = setPort(_wmgrPort); |
245 | | PortList::iterator it = _windowList.reverse_begin(); |
| 245 | PortList::iterator it = _windowList.legacy_reverse_begin(); |
246 | 246 | const PortList::iterator end = Common::find(_windowList.begin(), _windowList.end(), wnd); |
247 | 247 | while (it != end) { |
248 | 248 | // We also store Port objects in the window list, but they |
-
diff --git a/engines/sci/resource.cpp b/engines/sci/resource.cpp
index 77a6a40..8af25d5 100644
a
|
b
|
void ResourceManager::printLRU() {
|
1034 | 1034 | void ResourceManager::freeOldResources() { |
1035 | 1035 | while (MAX_MEMORY < _memoryLRU) { |
1036 | 1036 | assert(!_LRU.empty()); |
1037 | | Resource *goner = *_LRU.reverse_begin(); |
| 1037 | Resource *goner = *_LRU.legacy_reverse_begin(); |
1038 | 1038 | removeFromLRU(goner); |
1039 | 1039 | goner->unalloc(); |
1040 | 1040 | #ifdef SCI_VERBOSE_RESMAN |
-
diff --git a/engines/teenagent/scene.cpp b/engines/teenagent/scene.cpp
index e8c2dec..5286bff 100644
a
|
b
|
Animation *Scene::getAnimation(byte slot) {
|
458 | 458 | } |
459 | 459 | |
460 | 460 | byte Scene::peekFlagEvent(uint16 addr) const { |
461 | | for (EventList::const_iterator i = events.reverse_begin(); i != events.end(); --i) { |
| 461 | for (EventList::const_iterator i = events.legacy_reverse_begin(); i != events.end(); --i) { |
462 | 462 | const SceneEvent &e = *i; |
463 | 463 | if (e.type == SceneEvent::kSetFlag && e.callback == addr) |
464 | 464 | return e.color; |
-
diff --git a/engines/tsage/debugger.cpp b/engines/tsage/debugger.cpp
index 82645f2..f01b7e2 100644
a
|
b
|
bool Debugger::Cmd_Hotspots(int argc, const char **argv) {
|
287 | 287 | |
288 | 288 | // Iterate through the scene items |
289 | 289 | SynchronizedList<SceneItem *>::iterator i; |
290 | | for (i = g_globals->_sceneItems.reverse_begin(); i != g_globals->_sceneItems.end(); --i, ++colIndex) { |
| 290 | for (i = g_globals->_sceneItems.legacy_reverse_begin(); i != g_globals->_sceneItems.end(); --i, ++colIndex) { |
291 | 291 | SceneItem *o = *i; |
292 | 292 | |
293 | 293 | // Draw the contents of the hotspot area |
-
diff --git a/engines/tsage/ringworld2/ringworld2_scenes0.cpp b/engines/tsage/ringworld2/ringworld2_scenes0.cpp
index 4c98fcf..507af10 100644
a
|
b
|
void Scene160::Action1::signal() {
|
1314 | 1314 | breakFlag = true; |
1315 | 1315 | do { |
1316 | 1316 | if (!scene->_lineNum || ((scene->_lineNum != -1) && |
1317 | | (((*scene->_creditsList.reverse_begin())->_position.y < 164) || !breakFlag))) { |
| 1317 | (((*scene->_creditsList.legacy_reverse_begin())->_position.y < 164) || !breakFlag))) { |
1318 | 1318 | breakFlag = true; |
1319 | 1319 | Common::String msg = g_resourceManager->getMessage(160, scene->_lineNum++); |
1320 | 1320 | |
-
diff --git a/test/common/list.h b/test/common/list.h
index 232aa82..2905d93 100644
a
|
b
|
class ListTestSuite : public CxxTest::TestSuite
|
218 | 218 | |
219 | 219 | |
220 | 220 | TS_ASSERT_EQUALS(*iter, -11); |
221 | | --iter; |
| 221 | ++iter; |
222 | 222 | TS_ASSERT_DIFFERS(iter, container.end()); |
223 | 223 | |
224 | 224 | TS_ASSERT_EQUALS(*iter, 33); |
225 | | --iter; |
| 225 | ++ter; |
226 | 226 | TS_ASSERT_DIFFERS(iter, container.end()); |
227 | 227 | |
228 | 228 | TS_ASSERT_EQUALS(*iter, 17); |
229 | | --iter; |
| 229 | ++ter; |
230 | 230 | TS_ASSERT_EQUALS(iter, container.end()); |
231 | 231 | |
232 | 232 | iter = container.reverse_begin(); |
-
--
1.7.5.4
From ab8de641fbeebc92ccc6fa24223e75c67c7d7e76 Mon Sep 17 00:00:00 2001
From: Mathias Bartl <mathiasbartl@web.de>
Date: Fri, 6 Apr 2012 00:30:30 +0200
Subject: [PATCH 2/6] COMMON: Bidirectional reverse iterator for List
Common::List.reverse_begin() returns a bidirectional reverse iterator,
also constant bidirectional iterator.
List.reverse_end() is functionally identical and interchangable to List.end().
Due to the implementation, both iterators and reverse iterators waste one byte space per iterator,
and one conditional jump for each iteration.
---
common/list.h | 16 ++++--
common/list_intern.h | 140 +++++++++++++++++++++++++++++++++++++++++++++-----
test/common/list.h | 27 +++++++++-
3 files changed, 163 insertions(+), 20 deletions(-)
diff --git a/common/list.h b/common/list.h
index d2aaca3..56cc0ab 100644
a
|
b
|
public:
|
211 | 211 | } |
212 | 212 | |
213 | 213 | iterator reverse_begin() { |
214 | | return iterator(_anchor._prev);///<TODO FIXME use an actual backwards Iterator instead of an Forward Iterator |
| 214 | return iterator(_anchor._prev, false); |
| 215 | } |
| 216 | iterator reverse_end() { |
| 217 | return iterator(&_anchor, false); |
215 | 218 | } |
216 | 219 | |
217 | | /**DEPRACATED This is the old buggy version of reverse_begin(), use reverse_begin() instead, as sone as it has been fixed*/ |
| 220 | /**FIXME DEPRACATED This is the old version of reverse_begin(), use reverse_begin() instead, witch gets an actual backwartsiterator */ |
218 | 221 | iterator legacy_reverse_begin(){ |
219 | 222 | return iterator(_anchor._prev); |
220 | 223 | } |
… |
… |
public:
|
227 | 230 | return const_iterator(_anchor._next); |
228 | 231 | } |
229 | 232 | |
230 | | /**DEPRACATED This is the old buggy version of reverse_begin(), use reverse_begin() instead, as sone as it has been fixed*/ |
| 233 | /**FIXME DEPRACATED This is the old version of reverse_begin(), use reverse_begin() instead*/ |
231 | 234 | const_iterator legacy_reverse_begin() const { |
232 | 235 | return const_iterator(_anchor._prev); |
233 | 236 | } |
234 | 237 | |
235 | 238 | const_iterator reverse_begin() const { |
236 | | return const_iterator(_anchor._prev);///<TODO FIXME use an actual backwards Iterator instead of an Forward Iterator |
| 239 | return const_iterator(_anchor._prev, false); |
237 | 240 | } |
238 | 241 | |
239 | 242 | const_iterator end() const { |
240 | 243 | return const_iterator(const_cast<NodeBase *>(&_anchor)); |
241 | 244 | } |
| 245 | const_iterator reverse_end() const { |
| 246 | return const_iterator(const_cast<NodeBase *>(&_anchor), false); |
| 247 | } |
242 | 248 | |
243 | 249 | protected: |
244 | 250 | NodeBase erase(NodeBase *pos) { |
… |
… |
protected:
|
262 | 268 | newNode->_prev->_next = newNode; |
263 | 269 | newNode->_next->_prev = newNode; |
264 | 270 | } |
265 | | };///< TODO add reverse_end() |
| 271 | };///< TODO add reverse_end() for constat iterator |
266 | 272 | |
267 | 273 | } // End of namespace Common |
268 | 274 | |
-
diff --git a/common/list_intern.h b/common/list_intern.h
index fef32fb..092b5b6 100644
a
|
b
|
namespace ListInternal {
|
53 | 53 | typedef T ValueType; |
54 | 54 | |
55 | 55 | NodeBase *_node; |
| 56 | friend class ConstIterator<T>; |
| 57 | private: |
| 58 | bool _forward; |
| 59 | public: |
56 | 60 | |
57 | 61 | Iterator() : _node(0) {} |
58 | | explicit Iterator(NodeBase *node) : _node(node) {} |
| 62 | explicit Iterator(NodeBase *node) : _node(node), _forward(true) {} |
| 63 | explicit Iterator(NodeBase *node,bool forward) : _node(node), _forward(forward) {} |
59 | 64 | |
60 | 65 | // Prefix inc |
61 | 66 | Self &operator++() { |
62 | | if (_node) |
63 | | _node = _node->_next; |
| 67 | if (_node) { |
| 68 | if (_forward) |
| 69 | _node = _node->_next; |
| 70 | else |
| 71 | _node = _node->_prev; |
| 72 | } |
64 | 73 | return *this; |
65 | 74 | } |
66 | 75 | // Postfix inc |
… |
… |
namespace ListInternal {
|
71 | 80 | } |
72 | 81 | // Prefix dec |
73 | 82 | Self &operator--() { |
74 | | if (_node) |
75 | | _node = _node->_prev; |
| 83 | if (_node) { |
| 84 | if (_forward) |
| 85 | _node = _node->_prev; |
| 86 | else |
| 87 | _node = _node->_next; |
| 88 | } |
76 | 89 | return *this; |
77 | 90 | } |
78 | 91 | // Postfix dec |
… |
… |
namespace ListInternal {
|
97 | 110 | return _node != x._node; |
98 | 111 | } |
99 | 112 | }; |
| 113 | /* |
| 114 | template<typename T> |
| 115 | struct ReverseIterator: private Iterator<T> { |
| 116 | |
| 117 | typedef ReverseIterator<T> Self;//TODO Think about this |
| 118 | typedef Node<T> * NodePtr; |
| 119 | typedef T & ValueRef; |
| 120 | typedef T * ValuePtr; |
| 121 | typedef T ValueType; |
| 122 | NodeBase *_node; |
| 123 | |
| 124 | ReverseIterator() : _node(0) {} |
| 125 | explicit ReverseIterator(NodeBase *node) : _node(node) { _node = node; }//FIXME |
| 126 | |
| 127 | // Prefix inc |
| 128 | Self &operator++() { |
| 129 | if (_node) |
| 130 | _node = _node->_prev; |
| 131 | return *this; |
| 132 | } |
| 133 | // Postfix inc |
| 134 | Self operator++(int) { |
| 135 | Self tmp(_node); |
| 136 | ++(*this); |
| 137 | return tmp; |
| 138 | } |
| 139 | // Prefix dec |
| 140 | Self &operator--() { |
| 141 | if (_node) |
| 142 | _node = _node->_next; |
| 143 | return *this; |
| 144 | } |
| 145 | // Postfix dec |
| 146 | Self operator--(int) { |
| 147 | Self tmp(_node); |
| 148 | --(*this); |
| 149 | return tmp; |
| 150 | } |
| 151 | ValueRef operator*() const { |
| 152 | assert(_node);//TODO Why is that here? |
| 153 | return static_cast<NodePtr>(_node)->_data; |
| 154 | } |
| 155 | ValuePtr operator->() const { |
| 156 | return &(operator*()); |
| 157 | } |
| 158 | |
| 159 | bool operator==(const Self &x) const { |
| 160 | return _node == x._node; |
| 161 | } |
| 162 | |
| 163 | bool operator!=(const Self &x) const { |
| 164 | return _node != x._node; |
| 165 | } |
| 166 | bool operator==(const Iterator<T> &x) const { |
| 167 | return _node == x._node; |
| 168 | } |
| 169 | |
| 170 | bool operator!=(const Iterator<T> &x) const { |
| 171 | return _node != x._node; |
| 172 | } |
| 173 | |
| 174 | };*/ |
100 | 175 | |
101 | 176 | template<typename T> |
102 | 177 | struct ConstIterator { |
… |
… |
namespace ListInternal {
|
106 | 181 | typedef const T * ValuePtr; |
107 | 182 | |
108 | 183 | const NodeBase *_node; |
109 | | |
110 | | ConstIterator() : _node(0) {} |
111 | | explicit ConstIterator(const NodeBase *node) : _node(node) {} |
112 | | ConstIterator(const Iterator<T> &x) : _node(x._node) {} |
| 184 | private: |
| 185 | bool _forward; |
| 186 | public: |
| 187 | ConstIterator() : _node(0), _forward(true) {} |
| 188 | explicit ConstIterator(const NodeBase *node) : _node(node), _forward(true) {} |
| 189 | explicit ConstIterator(const NodeBase *node, bool forward) : _node(node), _forward(true) {} |
| 190 | ConstIterator(const Iterator<T> &x) : _node(x._node), _forward(x._forward) {} |
113 | 191 | |
114 | 192 | // Prefix inc |
115 | 193 | Self &operator++() { |
116 | | if (_node) |
117 | | _node = _node->_next; |
| 194 | if (_node) { |
| 195 | if (_forward) |
| 196 | _node = _node->_next; |
| 197 | else |
| 198 | _node = _node->_prev; |
| 199 | } |
118 | 200 | return *this; |
119 | 201 | } |
120 | 202 | // Postfix inc |
… |
… |
namespace ListInternal {
|
125 | 207 | } |
126 | 208 | // Prefix dec |
127 | 209 | Self &operator--() { |
128 | | if (_node) |
129 | | _node = _node->_prev; |
| 210 | if (_node) { |
| 211 | if (_forward) |
| 212 | _node = _node->_prev; |
| 213 | else |
| 214 | _node = _node->_next; |
| 215 | } |
130 | 216 | return *this; |
131 | 217 | } |
132 | 218 | // Postfix dec |
… |
… |
namespace ListInternal {
|
151 | 237 | return _node != x._node; |
152 | 238 | } |
153 | 239 | }; |
| 240 | /* |
| 241 | template<typename T> |
| 242 | struct ConstReverseIterator: public ConstIterator<T> { |
| 243 | |
| 244 | typedef ConstReverseIterator<T> Self;//TODO Think about this |
| 245 | typedef Node<T> * NodePtr; |
| 246 | typedef T & ValueRef; |
| 247 | typedef T * ValuePtr; |
| 248 | typedef T ValueType; |
| 249 | NodeBase *_node; |
| 250 | |
| 251 | ConstReverseIterator() : _node(0) {} |
| 252 | explicit ConstReverseIterator(const NodeBase *node) : _node(node) {} |
| 253 | ConstReverseIterator(const Iterator<T> &x) : _node(x._node) {}//TODO |
| 254 | |
| 255 | // Prefix inc |
| 256 | Self &operator++() { |
| 257 | if (_node) |
| 258 | _node = _node->_prev; |
| 259 | return *this; |
| 260 | } |
| 261 | // Prefix dec |
| 262 | Self &operator--() { |
| 263 | if (_node) |
| 264 | _node = _node->_next; |
| 265 | return *this; |
| 266 | } |
| 267 | };*/ |
154 | 268 | |
155 | 269 | |
156 | 270 | template<typename T> |
-
diff --git a/test/common/list.h b/test/common/list.h
index 2905d93..4f7211d 100644
a
|
b
|
class ListTestSuite : public CxxTest::TestSuite
|
208 | 208 | Common::List<int> container; |
209 | 209 | Common::List<int>::iterator iter; |
210 | 210 | |
| 211 | TS_ASSERT(container.empty()); |
| 212 | TS_ASSERT_EQUALS(container.reverse_begin(),container.reverse_begin()); |
| 213 | TS_ASSERT_EQUALS(container.reverse_begin(),container.legacy_reverse_begin()); |
211 | 214 | // Fill the container with some random data |
212 | 215 | container.push_back(17); |
213 | 216 | container.push_back(33); |
214 | 217 | container.push_back(-11); |
215 | 218 | |
216 | 219 | iter = container.reverse_begin(); |
| 220 | TS_ASSERT_DIFFERS(iter, container.reverse_end()); |
217 | 221 | TS_ASSERT_DIFFERS(iter, container.end()); |
218 | 222 | |
219 | 223 | |
220 | 224 | TS_ASSERT_EQUALS(*iter, -11); |
221 | 225 | ++iter; |
222 | 226 | TS_ASSERT_DIFFERS(iter, container.end()); |
| 227 | TS_ASSERT_DIFFERS(iter, container.reverse_end()); |
223 | 228 | |
224 | 229 | TS_ASSERT_EQUALS(*iter, 33); |
225 | | ++ter; |
| 230 | ++iter; |
| 231 | TS_ASSERT_DIFFERS(iter, container.reverse_end()); |
226 | 232 | TS_ASSERT_DIFFERS(iter, container.end()); |
227 | 233 | |
228 | 234 | TS_ASSERT_EQUALS(*iter, 17); |
229 | | ++ter; |
| 235 | ++iter; |
| 236 | TS_ASSERT_EQUALS(iter, container.reverse_end()); |
230 | 237 | TS_ASSERT_EQUALS(iter, container.end()); |
231 | 238 | |
232 | 239 | iter = container.reverse_begin(); |
| 240 | TS_ASSERT_DIFFERS(iter, container.reverse_end()); |
| 241 | |
| 242 | |
| 243 | TS_ASSERT_EQUALS(*iter, -11); |
| 244 | iter++; |
| 245 | TS_ASSERT_DIFFERS(iter, container.reverse_end()); |
| 246 | |
| 247 | TS_ASSERT_EQUALS(*iter, 33); |
| 248 | iter++; |
| 249 | TS_ASSERT_DIFFERS(iter, container.reverse_end()); |
| 250 | |
| 251 | TS_ASSERT_EQUALS(*iter, 17); |
| 252 | iter++; |
| 253 | TS_ASSERT_EQUALS(iter, container.reverse_end()); |
| 254 | |
| 255 | iter = container.reverse_begin(); |
233 | 256 | |
234 | 257 | iter = container.reverse_erase(iter); |
235 | 258 | TS_ASSERT_DIFFERS(iter, container.end()); |
-
--
1.7.5.4
From c1d5f2d427c0bc6b94a492496651a6974ed5f15b Mon Sep 17 00:00:00 2001
From: Mathias Bartl <mathiasbartl@web.de>
Date: Fri, 6 Apr 2012 00:33:43 +0200
Subject: [PATCH 3/6] COMMON: Removes unused reverse iterator code
Removes List_intern::ReverseIterator, List_intern::ReverseConstIterator, which were commented out.
I tryed a more performant oo implemetation of reverse iterators, but did not get it to work.
---
common/list_intern.h | 88 --------------------------------------------------
1 files changed, 0 insertions(+), 88 deletions(-)
diff --git a/common/list_intern.h b/common/list_intern.h
index 092b5b6..834d92c 100644
a
|
b
|
namespace ListInternal {
|
110 | 110 | return _node != x._node; |
111 | 111 | } |
112 | 112 | }; |
113 | | /* |
114 | | template<typename T> |
115 | | struct ReverseIterator: private Iterator<T> { |
116 | 113 | |
117 | | typedef ReverseIterator<T> Self;//TODO Think about this |
118 | | typedef Node<T> * NodePtr; |
119 | | typedef T & ValueRef; |
120 | | typedef T * ValuePtr; |
121 | | typedef T ValueType; |
122 | | NodeBase *_node; |
123 | | |
124 | | ReverseIterator() : _node(0) {} |
125 | | explicit ReverseIterator(NodeBase *node) : _node(node) { _node = node; }//FIXME |
126 | | |
127 | | // Prefix inc |
128 | | Self &operator++() { |
129 | | if (_node) |
130 | | _node = _node->_prev; |
131 | | return *this; |
132 | | } |
133 | | // Postfix inc |
134 | | Self operator++(int) { |
135 | | Self tmp(_node); |
136 | | ++(*this); |
137 | | return tmp; |
138 | | } |
139 | | // Prefix dec |
140 | | Self &operator--() { |
141 | | if (_node) |
142 | | _node = _node->_next; |
143 | | return *this; |
144 | | } |
145 | | // Postfix dec |
146 | | Self operator--(int) { |
147 | | Self tmp(_node); |
148 | | --(*this); |
149 | | return tmp; |
150 | | } |
151 | | ValueRef operator*() const { |
152 | | assert(_node);//TODO Why is that here? |
153 | | return static_cast<NodePtr>(_node)->_data; |
154 | | } |
155 | | ValuePtr operator->() const { |
156 | | return &(operator*()); |
157 | | } |
158 | | |
159 | | bool operator==(const Self &x) const { |
160 | | return _node == x._node; |
161 | | } |
162 | | |
163 | | bool operator!=(const Self &x) const { |
164 | | return _node != x._node; |
165 | | } |
166 | | bool operator==(const Iterator<T> &x) const { |
167 | | return _node == x._node; |
168 | | } |
169 | | |
170 | | bool operator!=(const Iterator<T> &x) const { |
171 | | return _node != x._node; |
172 | | } |
173 | | |
174 | | };*/ |
175 | 114 | |
176 | 115 | template<typename T> |
177 | 116 | struct ConstIterator { |
… |
… |
namespace ListInternal {
|
237 | 176 | return _node != x._node; |
238 | 177 | } |
239 | 178 | }; |
240 | | /* |
241 | | template<typename T> |
242 | | struct ConstReverseIterator: public ConstIterator<T> { |
243 | | |
244 | | typedef ConstReverseIterator<T> Self;//TODO Think about this |
245 | | typedef Node<T> * NodePtr; |
246 | | typedef T & ValueRef; |
247 | | typedef T * ValuePtr; |
248 | | typedef T ValueType; |
249 | | NodeBase *_node; |
250 | 179 | |
251 | | ConstReverseIterator() : _node(0) {} |
252 | | explicit ConstReverseIterator(const NodeBase *node) : _node(node) {} |
253 | | ConstReverseIterator(const Iterator<T> &x) : _node(x._node) {}//TODO |
254 | | |
255 | | // Prefix inc |
256 | | Self &operator++() { |
257 | | if (_node) |
258 | | _node = _node->_prev; |
259 | | return *this; |
260 | | } |
261 | | // Prefix dec |
262 | | Self &operator--() { |
263 | | if (_node) |
264 | | _node = _node->_next; |
265 | | return *this; |
266 | | } |
267 | | };*/ |
268 | 180 | |
269 | 181 | |
270 | 182 | template<typename T> |
-
--
1.7.5.4
From 3e0e9c38eda11a2947d41df87b608b38af9a5895 Mon Sep 17 00:00:00 2001
From: Mathias Bartl <mathiasbartl@web.de>
Date: Sun, 15 Apr 2012 18:02:13 +0200
Subject: [PATCH 4/6] COMMON: Internal structure of iterators is private.
List::Iterator, List::ConstIterator: reference to underlying List is private.
Small refactoring for oo code quality only.
---
common/list_intern.h | 9 ++++++---
test/common/list.h | 14 ++++++++++++++
2 files changed, 20 insertions(+), 3 deletions(-)
diff --git a/common/list_intern.h b/common/list_intern.h
index 834d92c..f064add 100644
a
|
b
|
namespace ListInternal {
|
52 | 52 | typedef T * ValuePtr; |
53 | 53 | typedef T ValueType; |
54 | 54 | |
55 | | NodeBase *_node; |
| 55 | |
56 | 56 | friend class ConstIterator<T>; |
57 | | private: |
| 57 | friend class List<T>; |
| 58 | private: |
| 59 | NodeBase *_node; |
58 | 60 | bool _forward; |
59 | 61 | public: |
60 | 62 | |
… |
… |
namespace ListInternal {
|
119 | 121 | typedef const T & ValueRef; |
120 | 122 | typedef const T * ValuePtr; |
121 | 123 | |
122 | | const NodeBase *_node; |
| 124 | friend class List<T>; |
123 | 125 | private: |
| 126 | const NodeBase *_node; |
124 | 127 | bool _forward; |
125 | 128 | public: |
126 | 129 | ConstIterator() : _node(0), _forward(true) {} |
-
diff --git a/test/common/list.h b/test/common/list.h
index 4f7211d..95e4ee4 100644
a
|
b
|
class ListTestSuite : public CxxTest::TestSuite
|
295 | 295 | TS_ASSERT_EQUALS(container.front(), 99); |
296 | 296 | TS_ASSERT_EQUALS(container.back(), 99); |
297 | 297 | } |
| 298 | /** Test equality opertors between Iterators ans ConstIterators*/ |
| 299 | void test_iterator_equality(){ |
| 300 | Common::List<int> container; |
| 301 | Common::List<int>::iterator iter; |
| 302 | Common::List<int>::const_iterator cIter; |
| 303 | container.push_back(17); |
| 304 | iter = container.begin(); |
| 305 | cIter = container.begin(); |
| 306 | TS_ASSERT( iter == cIter); |
| 307 | TS_ASSERT(cIter == iter); |
| 308 | TS_ASSERT( !(iter != cIter)); |
| 309 | TS_ASSERT(!(cIter != iter)); |
| 310 | |
| 311 | } |
298 | 312 | }; |
-
--
1.7.5.4
From 77cb81bf7b85e9b9ebb0a4cf4f6b7931c9a52c02 Mon Sep 17 00:00:00 2001
From: Mathias Bartl <mathiasbartl@web.de>
Date: Sun, 15 Apr 2012 19:56:14 +0200
Subject: [PATCH 5/6] COMMON: ==,!= operators work with iterators
Fixes bug in previous commit.
---
common/list_intern.h | 313 +++++++++++++++++++++++++------------------------
test/common/list.h | 23 ++--
2 files changed, 171 insertions(+), 165 deletions(-)
diff --git a/common/list_intern.h b/common/list_intern.h
index f064add..78c648a 100644
a
|
b
|
template<typename T> class List;
|
30 | 30 | |
31 | 31 | |
32 | 32 | namespace ListInternal { |
33 | | struct NodeBase { |
34 | | NodeBase *_prev; |
35 | | NodeBase *_next; |
36 | | }; |
37 | | |
38 | | template<typename T> |
39 | | struct Node : public NodeBase { |
40 | | T _data; |
41 | | |
42 | | Node(const T &x) : _data(x) {} |
43 | | }; |
44 | | |
45 | | template<typename T> struct ConstIterator; |
46 | | |
47 | | template<typename T> |
48 | | struct Iterator { |
49 | | typedef Iterator<T> Self; |
50 | | typedef Node<T> * NodePtr; |
51 | | typedef T & ValueRef; |
52 | | typedef T * ValuePtr; |
53 | | typedef T ValueType; |
54 | | |
55 | | |
56 | | friend class ConstIterator<T>; |
57 | | friend class List<T>; |
58 | | private: |
59 | | NodeBase *_node; |
60 | | bool _forward; |
61 | | public: |
62 | | |
63 | | Iterator() : _node(0) {} |
64 | | explicit Iterator(NodeBase *node) : _node(node), _forward(true) {} |
65 | | explicit Iterator(NodeBase *node,bool forward) : _node(node), _forward(forward) {} |
66 | | |
67 | | // Prefix inc |
68 | | Self &operator++() { |
69 | | if (_node) { |
70 | | if (_forward) |
71 | | _node = _node->_next; |
72 | | else |
73 | | _node = _node->_prev; |
74 | | } |
75 | | return *this; |
76 | | } |
77 | | // Postfix inc |
78 | | Self operator++(int) { |
79 | | Self tmp(_node); |
80 | | ++(*this); |
81 | | return tmp; |
82 | | } |
83 | | // Prefix dec |
84 | | Self &operator--() { |
85 | | if (_node) { |
86 | | if (_forward) |
87 | | _node = _node->_prev; |
88 | | else |
89 | | _node = _node->_next; |
90 | | } |
91 | | return *this; |
92 | | } |
93 | | // Postfix dec |
94 | | Self operator--(int) { |
95 | | Self tmp(_node); |
96 | | --(*this); |
97 | | return tmp; |
98 | | } |
99 | | ValueRef operator*() const { |
100 | | assert(_node); |
101 | | return static_cast<NodePtr>(_node)->_data; |
102 | | } |
103 | | ValuePtr operator->() const { |
104 | | return &(operator*()); |
105 | | } |
| 33 | struct NodeBase { |
| 34 | NodeBase *_prev; |
| 35 | NodeBase *_next; |
| 36 | }; |
| 37 | |
| 38 | template<typename T> |
| 39 | struct Node : public NodeBase { |
| 40 | T _data; |
| 41 | |
| 42 | Node(const T &x) : _data(x) {} |
| 43 | }; |
| 44 | |
| 45 | template<typename T> struct ConstIterator; |
| 46 | |
| 47 | template<typename T> |
| 48 | struct Iterator { |
| 49 | typedef Iterator<T> Self; |
| 50 | typedef Node<T> * NodePtr; |
| 51 | typedef T &ValueRef; |
| 52 | typedef T *ValuePtr; |
| 53 | typedef T ValueType; |
| 54 | |
| 55 | template <typename TT> |
| 56 | friend bool operator==(const Iterator<TT>& a, const ConstIterator<TT>& b); |
| 57 | template <typename TT> |
| 58 | friend bool operator!=(const Iterator<TT>& a, const ConstIterator<TT>& b); |
| 59 | friend class ConstIterator<T>; |
| 60 | friend class List<T>; |
| 61 | private: |
| 62 | NodeBase *_node; |
| 63 | bool _forward; |
| 64 | public: |
| 65 | |
| 66 | Iterator() : _node(0) {} |
| 67 | explicit Iterator(NodeBase *node) : _node(node), _forward(true) {} |
| 68 | explicit Iterator(NodeBase *node, bool forward) : _node(node), _forward(forward) {} |
| 69 | |
| 70 | // Prefix inc |
| 71 | Self &operator++() { |
| 72 | if (_node) { |
| 73 | if (_forward) |
| 74 | _node = _node->_next; |
| 75 | else |
| 76 | _node = _node->_prev; |
| 77 | } |
| 78 | return *this; |
| 79 | } |
| 80 | // Postfix inc |
| 81 | Self operator++(int) { |
| 82 | Self tmp(_node); |
| 83 | ++(*this); |
| 84 | return tmp; |
| 85 | } |
| 86 | // Prefix dec |
| 87 | Self &operator--() { |
| 88 | if (_node) { |
| 89 | if (_forward) |
| 90 | _node = _node->_prev; |
| 91 | else |
| 92 | _node = _node->_next; |
| 93 | } |
| 94 | return *this; |
| 95 | } |
| 96 | // Postfix dec |
| 97 | Self operator--(int) { |
| 98 | Self tmp(_node); |
| 99 | --(*this); |
| 100 | return tmp; |
| 101 | } |
| 102 | ValueRef operator*() const { |
| 103 | assert(_node); |
| 104 | return static_cast<NodePtr>(_node)->_data; |
| 105 | } |
| 106 | ValuePtr operator->() const { |
| 107 | return &(operator*()); |
| 108 | } |
106 | 109 | |
107 | | bool operator==(const Self &x) const { |
108 | | return _node == x._node; |
109 | | } |
| 110 | bool operator==(const Self &x) const { |
| 111 | return _node == x._node; |
| 112 | } |
110 | 113 | |
111 | | bool operator!=(const Self &x) const { |
112 | | return _node != x._node; |
113 | | } |
114 | | }; |
115 | | |
116 | | |
117 | | template<typename T> |
118 | | struct ConstIterator { |
119 | | typedef ConstIterator<T> Self; |
120 | | typedef const Node<T> * NodePtr; |
121 | | typedef const T & ValueRef; |
122 | | typedef const T * ValuePtr; |
123 | | |
124 | | friend class List<T>; |
125 | | private: |
126 | | const NodeBase *_node; |
127 | | bool _forward; |
128 | | public: |
129 | | ConstIterator() : _node(0), _forward(true) {} |
130 | | explicit ConstIterator(const NodeBase *node) : _node(node), _forward(true) {} |
131 | | explicit ConstIterator(const NodeBase *node, bool forward) : _node(node), _forward(true) {} |
132 | | ConstIterator(const Iterator<T> &x) : _node(x._node), _forward(x._forward) {} |
133 | | |
134 | | // Prefix inc |
135 | | Self &operator++() { |
136 | | if (_node) { |
137 | | if (_forward) |
138 | | _node = _node->_next; |
139 | | else |
140 | | _node = _node->_prev; |
141 | | } |
142 | | return *this; |
143 | | } |
144 | | // Postfix inc |
145 | | Self operator++(int) { |
146 | | Self tmp(_node); |
147 | | ++(*this); |
148 | | return tmp; |
149 | | } |
150 | | // Prefix dec |
151 | | Self &operator--() { |
152 | | if (_node) { |
153 | | if (_forward) |
154 | | _node = _node->_prev; |
155 | | else |
156 | | _node = _node->_next; |
157 | | } |
158 | | return *this; |
159 | | } |
160 | | // Postfix dec |
161 | | Self operator--(int) { |
162 | | Self tmp(_node); |
163 | | --(*this); |
164 | | return tmp; |
165 | | } |
166 | | ValueRef operator*() const { |
167 | | assert(_node); |
168 | | return static_cast<NodePtr>(_node)->_data; |
169 | | } |
170 | | ValuePtr operator->() const { |
171 | | return &(operator*()); |
172 | | } |
| 114 | bool operator!=(const Self &x) const { |
| 115 | return _node != x._node; |
| 116 | } |
| 117 | }; |
| 118 | |
| 119 | |
| 120 | template<typename T> |
| 121 | struct ConstIterator { |
| 122 | typedef ConstIterator<T> Self; |
| 123 | typedef const Node<T> * NodePtr; |
| 124 | typedef const T &ValueRef; |
| 125 | typedef const T *ValuePtr; |
| 126 | |
| 127 | template <typename TT> |
| 128 | friend bool operator==(const Iterator<TT>& a, const ConstIterator<TT>& b); |
| 129 | template <typename TT> |
| 130 | friend bool operator!=(const Iterator<TT>& a, const ConstIterator<TT>& b); |
| 131 | friend class List<T>; |
| 132 | private: |
| 133 | const NodeBase *_node; |
| 134 | bool _forward; |
| 135 | public: |
| 136 | ConstIterator() : _node(0), _forward(true) {} |
| 137 | explicit ConstIterator(const NodeBase *node) : _node(node), _forward(true) {} |
| 138 | explicit ConstIterator(const NodeBase *node, bool forward) : _node(node), _forward(true) {} |
| 139 | ConstIterator(const Iterator<T> &x) : _node(x._node), _forward(x._forward) {} |
| 140 | |
| 141 | // Prefix inc |
| 142 | Self &operator++() { |
| 143 | if (_node) { |
| 144 | if (_forward) |
| 145 | _node = _node->_next; |
| 146 | else |
| 147 | _node = _node->_prev; |
| 148 | } |
| 149 | return *this; |
| 150 | } |
| 151 | // Postfix inc |
| 152 | Self operator++(int) { |
| 153 | Self tmp(_node); |
| 154 | ++(*this); |
| 155 | return tmp; |
| 156 | } |
| 157 | // Prefix dec |
| 158 | Self &operator--() { |
| 159 | if (_node) { |
| 160 | if (_forward) |
| 161 | _node = _node->_prev; |
| 162 | else |
| 163 | _node = _node->_next; |
| 164 | } |
| 165 | return *this; |
| 166 | } |
| 167 | // Postfix dec |
| 168 | Self operator--(int) { |
| 169 | Self tmp(_node); |
| 170 | --(*this); |
| 171 | return tmp; |
| 172 | } |
| 173 | ValueRef operator*() const { |
| 174 | assert(_node); |
| 175 | return static_cast<NodePtr>(_node)->_data; |
| 176 | } |
| 177 | ValuePtr operator->() const { |
| 178 | return &(operator*()); |
| 179 | } |
173 | 180 | |
174 | | bool operator==(const Self &x) const { |
175 | | return _node == x._node; |
176 | | } |
| 181 | bool operator==(const Self &x) const { |
| 182 | return _node == x._node; |
| 183 | } |
177 | 184 | |
178 | | bool operator!=(const Self &x) const { |
179 | | return _node != x._node; |
180 | | } |
181 | | }; |
| 185 | bool operator!=(const Self &x) const { |
| 186 | return _node != x._node; |
| 187 | } |
| 188 | }; |
182 | 189 | |
183 | 190 | |
184 | 191 | |
185 | | template<typename T> |
186 | | bool operator==(const Iterator<T>& a, const ConstIterator<T>& b) { |
187 | | return a._node == b._node; |
188 | | } |
| 192 | template<typename T> |
| 193 | bool operator==(const Iterator<T>& a, const ConstIterator<T>& b) { |
| 194 | return a._node == b._node; |
| 195 | } |
189 | 196 | |
190 | | template<typename T> |
191 | | bool operator!=(const Iterator<T>& a, const ConstIterator<T>& b) { |
192 | | return a._node != b._node; |
193 | | } |
| 197 | template<typename T> |
| 198 | bool operator!=(const Iterator<T>& a, const ConstIterator<T>& b) { |
| 199 | return a._node != b._node; |
| 200 | } |
194 | 201 | } |
195 | 202 | |
196 | 203 | |
-
diff --git a/test/common/list.h b/test/common/list.h
index 95e4ee4..e614dd3 100644
a
|
b
|
|
2 | 2 | |
3 | 3 | #include "common/list.h" |
4 | 4 | |
5 | | class ListTestSuite : public CxxTest::TestSuite |
6 | | { |
7 | | public: |
| 5 | class ListTestSuite : public CxxTest::TestSuite { |
| 6 | public: |
8 | 7 | void test_empty_clear() { |
9 | 8 | Common::List<int> container; |
10 | 9 | TS_ASSERT(container.empty()); |
… |
… |
class ListTestSuite : public CxxTest::TestSuite
|
15 | 14 | TS_ASSERT(container.empty()); |
16 | 15 | } |
17 | 16 | |
18 | | public: |
| 17 | public: |
19 | 18 | void test_size() { |
20 | 19 | Common::List<int> container; |
21 | 20 | TS_ASSERT_EQUALS(container.size(), (unsigned int)0); |
… |
… |
class ListTestSuite : public CxxTest::TestSuite
|
208 | 207 | Common::List<int> container; |
209 | 208 | Common::List<int>::iterator iter; |
210 | 209 | |
211 | | TS_ASSERT(container.empty()); |
212 | | TS_ASSERT_EQUALS(container.reverse_begin(),container.reverse_begin()); |
213 | | TS_ASSERT_EQUALS(container.reverse_begin(),container.legacy_reverse_begin()); |
| 210 | TS_ASSERT(container.empty()); |
| 211 | TS_ASSERT_EQUALS(container.reverse_begin(), container.reverse_begin()); |
| 212 | TS_ASSERT_EQUALS(container.reverse_begin(), container.legacy_reverse_begin()); |
214 | 213 | // Fill the container with some random data |
215 | 214 | container.push_back(17); |
216 | 215 | container.push_back(33); |
… |
… |
class ListTestSuite : public CxxTest::TestSuite
|
272 | 271 | void test_front_back_push_pop() { |
273 | 272 | Common::List<int> container; |
274 | 273 | |
275 | | container.push_back( 42); |
| 274 | container.push_back(42); |
276 | 275 | container.push_back(-23); |
277 | 276 | |
278 | 277 | TS_ASSERT_EQUALS(container.front(), 42); |
… |
… |
class ListTestSuite : public CxxTest::TestSuite
|
296 | 295 | TS_ASSERT_EQUALS(container.back(), 99); |
297 | 296 | } |
298 | 297 | /** Test equality opertors between Iterators ans ConstIterators*/ |
299 | | void test_iterator_equality(){ |
| 298 | void test_iterator_equality() { |
300 | 299 | Common::List<int> container; |
301 | 300 | Common::List<int>::iterator iter; |
302 | 301 | Common::List<int>::const_iterator cIter; |
303 | 302 | container.push_back(17); |
304 | 303 | iter = container.begin(); |
305 | 304 | cIter = container.begin(); |
306 | | TS_ASSERT( iter == cIter); |
| 305 | TS_ASSERT(iter == cIter); |
307 | 306 | TS_ASSERT(cIter == iter); |
308 | | TS_ASSERT( !(iter != cIter)); |
| 307 | TS_ASSERT(!(iter != cIter)); |
309 | 308 | TS_ASSERT(!(cIter != iter)); |
310 | | |
| 309 | |
311 | 310 | } |
312 | 311 | }; |
-
--
1.7.5.4
From 8aae1fe32a8f0ff86a2ff73b738c7602006e2097 Mon Sep 17 00:00:00 2001
From: Mathias Bartl <mathiasbartl@web.de>
Date: Mon, 16 Apr 2012 08:30:40 +0200
Subject: [PATCH 6/6] COMMON: Pretty printing
---
common/list.h | 32 ++++++++++++++++----------------
1 files changed, 16 insertions(+), 16 deletions(-)
diff --git a/common/list.h b/common/list.h
index 56cc0ab..60947b3 100644
a
|
b
|
namespace Common {
|
33 | 33 | template<typename t_T> |
34 | 34 | class List { |
35 | 35 | protected: |
36 | | typedef ListInternal::NodeBase NodeBase; |
37 | | typedef ListInternal::Node<t_T> Node; |
| 36 | typedef ListInternal::NodeBase NodeBase; |
| 37 | typedef ListInternal::Node<t_T> Node; |
38 | 38 | |
39 | 39 | NodeBase _anchor; |
40 | 40 | |
41 | 41 | public: |
42 | | typedef ListInternal::Iterator<t_T> iterator; |
43 | | typedef ListInternal::ConstIterator<t_T> const_iterator; |
| 42 | typedef ListInternal::Iterator<t_T> iterator; |
| 43 | typedef ListInternal::ConstIterator<t_T> const_iterator; |
44 | 44 | |
45 | 45 | typedef t_T value_type; |
46 | 46 | typedef uint size_type; |
… |
… |
public:
|
169 | 169 | const_iterator i2; |
170 | 170 | const_iterator e2 = list.end(); |
171 | 171 | |
172 | | for (i = begin(), i2 = list.begin(); (i != e) && (i2 != e2) ; ++i, ++i2) { |
| 172 | for (i = begin(), i2 = list.begin(); (i != e) && (i2 != e2) ; ++i, ++i2) { |
173 | 173 | static_cast<Node *>(i._node)->_data = static_cast<const Node *>(i2._node)->_data; |
174 | 174 | } |
175 | 175 | |
… |
… |
public:
|
206 | 206 | } |
207 | 207 | |
208 | 208 | |
209 | | iterator begin() { |
| 209 | iterator begin() { |
210 | 210 | return iterator(_anchor._next); |
211 | 211 | } |
212 | 212 | |
213 | | iterator reverse_begin() { |
| 213 | iterator reverse_begin() { |
214 | 214 | return iterator(_anchor._prev, false); |
215 | 215 | } |
216 | | iterator reverse_end() { |
| 216 | iterator reverse_end() { |
217 | 217 | return iterator(&_anchor, false); |
218 | 218 | } |
219 | 219 | |
220 | 220 | /**FIXME DEPRACATED This is the old version of reverse_begin(), use reverse_begin() instead, witch gets an actual backwartsiterator */ |
221 | | iterator legacy_reverse_begin(){ |
| 221 | iterator legacy_reverse_begin() { |
222 | 222 | return iterator(_anchor._prev); |
223 | 223 | } |
224 | 224 | |
225 | | iterator end() { |
| 225 | iterator end() { |
226 | 226 | return iterator(&_anchor); |
227 | 227 | } |
228 | 228 | |
229 | | const_iterator begin() const { |
| 229 | const_iterator begin() const { |
230 | 230 | return const_iterator(_anchor._next); |
231 | 231 | } |
232 | 232 | |
233 | 233 | /**FIXME DEPRACATED This is the old version of reverse_begin(), use reverse_begin() instead*/ |
234 | | const_iterator legacy_reverse_begin() const { |
| 234 | const_iterator legacy_reverse_begin() const { |
235 | 235 | return const_iterator(_anchor._prev); |
236 | 236 | } |
237 | 237 | |
238 | | const_iterator reverse_begin() const { |
| 238 | const_iterator reverse_begin() const { |
239 | 239 | return const_iterator(_anchor._prev, false); |
240 | 240 | } |
241 | 241 | |
242 | | const_iterator end() const { |
| 242 | const_iterator end() const { |
243 | 243 | return const_iterator(const_cast<NodeBase *>(&_anchor)); |
244 | 244 | } |
245 | | const_iterator reverse_end() const { |
| 245 | const_iterator reverse_end() const { |
246 | 246 | return const_iterator(const_cast<NodeBase *>(&_anchor), false); |
247 | 247 | } |
248 | 248 | |
… |
… |
protected:
|
268 | 268 | newNode->_prev->_next = newNode; |
269 | 269 | newNode->_next->_prev = newNode; |
270 | 270 | } |
271 | | };///< TODO add reverse_end() for constat iterator |
| 271 | }; |
272 | 272 | |
273 | 273 | } // End of namespace Common |
274 | 274 | |