activemq-cpp-3.4.0

src/main/decaf/util/LinkedList.h

Go to the documentation of this file.
00001 /*
00002  * Licensed to the Apache Software Foundation (ASF) under one or more
00003  * contributor license agreements.  See the NOTICE file distributed with
00004  * this work for additional information regarding copyright ownership.
00005  * The ASF licenses this file to You under the Apache License, Version 2.0
00006  * (the "License"); you may not use this file except in compliance with
00007  * the License.  You may obtain a copy of the License at
00008  *
00009  *     http://www.apache.org/licenses/LICENSE-2.0
00010  *
00011  * Unless required by applicable law or agreed to in writing, software
00012  * distributed under the License is distributed on an "AS IS" BASIS,
00013  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00014  * See the License for the specific language governing permissions and
00015  * limitations under the License.
00016  */
00017 
00018 #ifndef _DECAF_UTIL_LINKEDLIST_H_
00019 #define _DECAF_UTIL_LINKEDLIST_H_
00020 
00021 #include <list>
00022 #include <memory>
00023 #include <decaf/util/NoSuchElementException.h>
00024 #include <decaf/lang/exceptions/UnsupportedOperationException.h>
00025 #include <decaf/lang/exceptions/IndexOutOfBoundsException.h>
00026 #include <decaf/lang/System.h>
00027 #include <decaf/lang/Integer.h>
00028 #include <decaf/util/Config.h>
00029 #include <decaf/util/Deque.h>
00030 #include <decaf/util/ArrayList.h>
00031 #include <decaf/util/Iterator.h>
00032 #include <decaf/util/ListIterator.h>
00033 #include <decaf/util/AbstractSequentialList.h>
00034 
00035 namespace decaf {
00036 namespace util {
00037 
00038     using decaf::lang::System;
00039 
00054     template< typename E >
00055     class LinkedList : public AbstractSequentialList<E>, public Deque<E> {
00056     private:
00057 
00058         template< typename U >
00059         class ListNode {
00060         public:
00061 
00062             U value;
00063             ListNode<U>* prev;
00064             ListNode<U>* next;
00065 
00066         private:
00067 
00068             ListNode( const ListNode& );
00069             ListNode& operator= ( const ListNode& );
00070 
00071         public:
00072 
00073             ListNode() : value(), prev(NULL), next(NULL) {
00074             }
00075 
00076             ListNode( const U& value ) : value(value), prev(NULL), next(NULL) {
00077             }
00078 
00079             ListNode( ListNode<U>* prev, ListNode<U>* next, const U& value ) :
00080                 value(value), prev(prev), next(next) {
00081             }
00082 
00083         };
00084 
00085     private:
00086 
00087         int listSize;
00088         ListNode<E> head;
00089         ListNode<E> tail;
00090 
00091     public:
00092 
00093         LinkedList() :
00094             AbstractSequentialList<E>(), listSize(0), head(), tail() {
00095 
00096             this->head.next = &this->tail;
00097             this->tail.prev = &this->head;
00098         }
00099 
00100         LinkedList( const LinkedList<E>& list ) :
00101             AbstractSequentialList<E>(), listSize(0), head(), tail() {
00102 
00103             this->head.next = &this->tail;
00104             this->tail.prev = &this->head;
00105 
00106             this->addAllAtLocation( 0, list );
00107         }
00108 
00109         LinkedList( const Collection<E>& collection ) :
00110             AbstractSequentialList<E>(), listSize(0), head(), tail() {
00111 
00112             this->head.next = &this->tail;
00113             this->tail.prev = &this->head;
00114 
00115             this->addAllAtLocation( 0, collection );
00116         }
00117 
00118         virtual ~LinkedList() {
00119             try{
00120                 this->purgeList();
00121             } catch(...) {}
00122         }
00123 
00124     public:
00125 
00126         LinkedList<E>& operator= ( const LinkedList<E>& list ) {
00127             this->clear();
00128             this->addAllAtLocation( 0, list );
00129             return *this;
00130         }
00131 
00132         LinkedList<E>& operator= ( const Collection<E>& collection ) {
00133             this->clear();
00134             this->addAllAtLocation( 0, collection );
00135             return *this;
00136         }
00137 
00138     public:
00139 
00140         virtual E get( int index ) const {
00141 
00142             if( index < 0 || index >= this->listSize ) {
00143                 throw decaf::lang::exceptions::IndexOutOfBoundsException(
00144                     __FILE__, __LINE__, "Index given is outside bounds of this list {%d}", index );
00145             }
00146 
00147             const ListNode<E>* location = NULL;
00148 
00149             if( index < this->listSize / 2 ) {
00150                 location = &this->head;
00151                 for( int i = 0; i <= index; ++i ) {
00152                     location = location->next;
00153                 }
00154             } else {
00155                 location = &this->tail;
00156                 for( int i = this->listSize; i > index; --i ) {
00157                     location = location->prev;
00158                 }
00159             }
00160 
00161             return location->value;
00162         }
00163 
00164         virtual E set( int index, const E& element ) {
00165 
00166             if( index < 0 || index >= this->listSize ) {
00167                 throw decaf::lang::exceptions::IndexOutOfBoundsException(
00168                     __FILE__, __LINE__, "Index given is outside bounds of this list {%d}", index );
00169             }
00170 
00171             ListNode<E>* location = NULL;
00172 
00173             if( index < this->listSize / 2 ) {
00174                 location = &this->head;
00175                 for( int i = 0; i <= index; ++i ) {
00176                     location = location->next;
00177                 }
00178             } else {
00179                 location = &this->tail;
00180                 for( int i = this->listSize; i > index; --i ) {
00181                     location = location->prev;
00182                 }
00183             }
00184 
00185             E oldValue = location->value;
00186             location->value = element;
00187 
00188             return oldValue;
00189         }
00190 
00191         virtual bool add( const E& value ) {
00192             this->addToEnd( value );
00193             return true;
00194         }
00195 
00196         virtual void add( int index, const E& value ) {
00197 
00198             if( index < 0 || index > this->listSize ) {
00199                 throw decaf::lang::exceptions::IndexOutOfBoundsException(
00200                     __FILE__, __LINE__, "Index given is outside bounds of this list {%d}", index );
00201             }
00202 
00203             this->addAtLocation( index, value );
00204         }
00205 
00206         virtual bool addAll( const Collection<E>& collection ) {
00207             return this->addAllAtLocation( this->listSize, collection );
00208         }
00209 
00210         virtual bool addAll( int index, const Collection<E>& collection ) {
00211             return this->addAllAtLocation( index, collection );
00212         }
00213 
00214         virtual void copy( const Collection<E>& collection ) {
00215             this->clear();
00216             this->addAllAtLocation( 0, collection );
00217         }
00218 
00219         virtual bool remove( const E& value ) {
00220             return this->removeFirstOccurrence( value );
00221         }
00222 
00223         virtual bool isEmpty() const {
00224             return this->listSize == 0;
00225         }
00226 
00227         virtual int size() const {
00228             return this->listSize;
00229         }
00230 
00231         virtual void clear() {
00232             this->purgeList();
00233             this->head.next = &this->tail;
00234             this->tail.prev = &this->head;
00235             this->listSize = 0;
00236             AbstractList<E>::modCount++;
00237         }
00238 
00239         virtual bool contains( const E& value ) const {
00240             return this->indexOf( value ) != -1;
00241         }
00242 
00243         virtual int indexOf( const E& value ) const {
00244 
00245             if( this->listSize == 0 ) {
00246                 return -1;
00247             }
00248 
00249             const ListNode<E>* location = this->head.next;
00250 
00251             for( int i = 0; location != &this->tail; ++i, location = location->next ) {
00252                 if( location->value == value ) {
00253                     return i;
00254                 }
00255             }
00256 
00257             return -1;
00258         }
00259 
00260         virtual int lastIndexOf( const E& value ) const {
00261 
00262             if( this->listSize == 0 ) {
00263                 return -1;
00264             }
00265 
00266             const ListNode<E>* location = this->tail.prev;
00267 
00268             for( int i = this->listSize - 1; location != &this->head; --i, location = location->prev ) {
00269                 if( location->value == value ) {
00270                     return i;
00271                 }
00272             }
00273 
00274             return -1;
00275         }
00276 
00277         virtual std::vector<E> toArray() const {
00278 
00279             std::vector<E> result;
00280             result.reserve( this->listSize );
00281 
00282             const ListNode<E>* current = this->head.next;
00283 
00284             while( current != &this->tail ) {
00285                 result.push_back( current->value );
00286                 current = current->next;
00287             }
00288 
00289             return result;
00290         }
00291 
00292     public:  // Deque interface implementation.
00293 
00294         virtual bool offer( const E& value ) {
00295             this->addLast( value );
00296             return true;
00297         }
00298 
00299         virtual bool poll( E& result ) {
00300 
00301             if( this->listSize == 0 ) {
00302                 return false;
00303             }
00304 
00305             result = this->head.next->value;
00306             this->removeAtFront();
00307             return true;
00308         }
00309 
00310         virtual E remove() {
00311             return this->removeAtFront();
00312         }
00313 
00314         virtual bool peek( E& result ) const {
00315 
00316             if( this->listSize == 0 ) {
00317                 return false;
00318             }
00319 
00320             result = this->head.next->value;
00321             return true;
00322         }
00323 
00324         virtual E element() const {
00325             if( this->listSize == 0 ) {
00326                 throw decaf::util::NoSuchElementException(
00327                     __FILE__, __LINE__, "The list is Empty" );
00328             }
00329 
00330             return this->head.next->value;
00331         }
00332 
00333         virtual void addFirst( const E& value ) {
00334             this->addToFront( value );
00335         }
00336 
00337         virtual void addLast( const E& value ) {
00338             this->addToEnd( value );
00339         }
00340 
00341         virtual E& getFirst() {
00342             if( this->listSize == 0 ) {
00343                 throw decaf::util::NoSuchElementException(
00344                     __FILE__, __LINE__, "The list is Empty" );
00345             }
00346 
00347             return this->head.next->value;
00348         }
00349 
00350         virtual const E& getFirst() const {
00351             if( this->listSize == 0 ) {
00352                 throw decaf::util::NoSuchElementException(
00353                     __FILE__, __LINE__, "The list is Empty" );
00354             }
00355 
00356             return this->head.next->value;
00357         }
00358 
00359         virtual E& getLast() {
00360             if( this->listSize == 0 ) {
00361                 throw decaf::util::NoSuchElementException(
00362                     __FILE__, __LINE__, "The list is Empty" );
00363             }
00364 
00365             return this->tail.prev->value;
00366         }
00367 
00368         virtual const E& getLast() const {
00369             if( this->listSize == 0 ) {
00370                 throw decaf::util::NoSuchElementException(
00371                     __FILE__, __LINE__, "The list is Empty" );
00372             }
00373 
00374             return this->tail.prev->value;
00375         }
00376 
00377         virtual bool offerFirst( const E& element ) {
00378             this->addToFront( element );
00379             return true;
00380         }
00381 
00382         virtual bool offerLast( const E& element ) {
00383             this->addToEnd( element );
00384             return true;
00385         }
00386 
00387         virtual E removeFirst() {
00388             return this->removeAtFront();
00389         }
00390 
00391         virtual E removeLast() {
00392             return this->removeAtEnd();
00393         }
00394 
00395         virtual bool pollFirst( E& result ) {
00396             if( this->listSize == 0 ) {
00397                 return false;
00398             }
00399 
00400             result = this->head.next->value;
00401             this->removeAtFront();
00402             return true;
00403         }
00404 
00405         virtual bool pollLast( E& result ) {
00406             if( this->listSize == 0 ) {
00407                 return false;
00408             }
00409 
00410             result = this->tail.prev->value;
00411             this->removeAtEnd();
00412             return true;
00413         }
00414 
00415         virtual bool peekFirst( E& result ) const {
00416             if( this->listSize == 0 ) {
00417                 return false;
00418             }
00419 
00420             result = this->head.next->value;
00421             return true;
00422         }
00423 
00424         virtual bool peekLast( E& result ) const {
00425             if( this->listSize == 0 ) {
00426                 return false;
00427             }
00428 
00429             result = this->tail.prev->value;
00430             return true;
00431         }
00432 
00433         virtual E pop() {
00434             return this->removeAtFront();
00435         }
00436 
00437         virtual void push( const E& element ) {
00438             this->addToFront( element );
00439         }
00440 
00441         virtual bool removeFirstOccurrence( const E& value ) {
00442             std::auto_ptr< Iterator<E> > iter( this->iterator() );
00443             while( iter->hasNext() ) {
00444                 if( iter->next() == value ) {
00445                     iter->remove();
00446                     return true;
00447                 }
00448             }
00449 
00450             return false;
00451         }
00452         virtual bool removeLastOccurrence( const E& value ) {
00453             std::auto_ptr< Iterator<E> > iter( this->descendingIterator() );
00454             while( iter->hasNext() ) {
00455                 if( iter->next() == value ) {
00456                     iter->remove();
00457                     return true;
00458                 }
00459             }
00460 
00461             return false;
00462         }
00463 
00464     private:
00465 
00466         class LinkedListIterator : public ListIterator<E> {
00467         private:
00468 
00469             mutable LinkedList<E>* list;
00470             ListNode<E>* current;
00471             ListNode<E>* lastReturned;
00472             int index;
00473             int expectedModCount;
00474 
00475         private:
00476 
00477             LinkedListIterator( const LinkedListIterator& );
00478             LinkedListIterator operator= ( const LinkedListIterator& );
00479 
00480         public:
00481 
00482             LinkedListIterator( LinkedList<E>* list, int index ) :
00483                 ListIterator<E>(), list(list), current(NULL), lastReturned(NULL), index(-1), expectedModCount(0) {
00484 
00485                 if( list == NULL ) {
00486                     throw decaf::lang::exceptions::NullPointerException(
00487                         __FILE__, __LINE__, "Parent LinkedList pointer was Null." );
00488                 }
00489 
00490                 if( index < 0 || index > list->listSize ) {
00491                     throw decaf::lang::exceptions::IndexOutOfBoundsException(
00492                         __FILE__, __LINE__, "Given index {%d} is out of range.", index );
00493                 }
00494 
00495                 this->expectedModCount = list->modCount;
00496 
00497                 // index starts at -1 to indicate that we are before begin or that the
00498                 // list is empty.  We always want to start out one before so that the call
00499                 // to next moves us onto the element in question;
00500 
00501                 if( index < this->list->listSize / 2 ) {
00502                     this->current = &this->list->head;
00503                     for( this->index = -1; this->index + 1 < index; ++this->index ) {
00504                         this->current = this->current->next;
00505                     }
00506                 } else {
00507                     this->current = &this->list->tail;
00508                     for( this->index = this->list->listSize; this->index >= index; --this->index ) {
00509                         this->current = this->current->prev;
00510                     }
00511                 }
00512             }
00513 
00514             virtual ~LinkedListIterator() {}
00515 
00516             virtual E next() {
00517 
00518                 if( this->expectedModCount != this->list->modCount ) {
00519                     throw ConcurrentModificationException(
00520                         __FILE__, __LINE__, "List modified outside of this Iterator." );
00521                 }
00522 
00523                 if( this->current->next == &(this->list->tail) ) {
00524                     throw NoSuchElementException(
00525                         __FILE__, __LINE__, "No more elements to return from next()" );
00526                 }
00527 
00528                 this->current = this->current->next;
00529                 this->lastReturned = this->current;
00530                 this->index++;
00531 
00532                 return this->current->value;
00533             }
00534 
00535             virtual bool hasNext() const {
00536                 return ( this->current->next != &(this->list->tail) );
00537             }
00538 
00539 
00540             virtual E previous() {
00541                 if( this->expectedModCount != this->list->modCount ) {
00542                     throw ConcurrentModificationException(
00543                         __FILE__, __LINE__, "List modified outside of this Iterator." );
00544                 }
00545 
00546                 if( this->current == &(this->list->head) ) {
00547                     throw decaf::lang::exceptions::IllegalStateException(
00548                         __FILE__, __LINE__,
00549                         "No previous element, must call next() before calling previous()." );
00550                 }
00551 
00552                 this->lastReturned = this->current;
00553                 this->current = this->current->prev;
00554                 this->index--;
00555 
00556                 return this->lastReturned->value;
00557             }
00558 
00559             virtual bool hasPrevious() const {
00560                 return ( this->current != &(this->list->head) );
00561             }
00562 
00563             virtual void remove() {
00564                 if( this->expectedModCount != this->list->modCount ) {
00565                     throw ConcurrentModificationException(
00566                         __FILE__, __LINE__, "List modified outside of this Iterator." );
00567                 }
00568 
00569                 if( this->lastReturned == NULL ) {
00570                     throw lang::exceptions::IllegalStateException(
00571                         __FILE__, __LINE__,
00572                         "Invalid State to call remove, must call next() before remove()" );
00573                 }
00574 
00575                 ListNode<E>* next = this->lastReturned->next;
00576                 ListNode<E>* previous = this->lastReturned->prev;
00577 
00578                 next->prev = previous;
00579                 previous->next = next;
00580 
00581                 // When iterating in reverse this would not be true
00582                 if( this->current == this->lastReturned ) {
00583                     this->index--;
00584                 }
00585                 this->current = previous;
00586 
00587                 delete this->lastReturned;
00588                 this->lastReturned = NULL;
00589 
00590                 this->list->listSize--;
00591                 this->list->modCount++;
00592 
00593                 this->expectedModCount++;
00594             }
00595 
00596             virtual void add( const E& e ) {
00597                 if( this->expectedModCount != this->list->modCount ) {
00598                     throw ConcurrentModificationException(
00599                         __FILE__, __LINE__, "List modified outside of this Iterator." );
00600                 }
00601 
00602                 ListNode<E>* newNode = new ListNode<E>( this->current, this->current->next, e );
00603 
00604                 this->current->next->prev = newNode;
00605                 this->current->next = newNode;
00606 
00607                 this->current = newNode;
00608                 this->lastReturned = NULL;
00609 
00610                 this->index++;
00611                 this->expectedModCount++;
00612                 this->list->modCount++;
00613                 this->list->listSize++;
00614             }
00615 
00616             virtual void set( const E& e ) {
00617 
00618                 if( this->expectedModCount != this->list->modCount ) {
00619                     throw ConcurrentModificationException(
00620                         __FILE__, __LINE__, "List modified outside of this Iterator." );
00621                 }
00622 
00623                 if( this->lastReturned != NULL ) {
00624                     this->lastReturned->value = e;
00625                 } else {
00626                     throw decaf::lang::exceptions::IllegalStateException(
00627                         __FILE__, __LINE__, "Iterator next has not been called." );
00628                 }
00629             }
00630 
00631             virtual int nextIndex() const {
00632                 return this->index + 1;
00633             }
00634 
00635             virtual int previousIndex() const {
00636                 return this->index;
00637             }
00638         };
00639 
00640         class ConstLinkedListIterator : public ListIterator<E> {
00641         private:
00642 
00643             const LinkedList<E>* list;
00644             const ListNode<E>* current;
00645             const ListNode<E>* lastReturned;
00646             int index;
00647 
00648         private:
00649 
00650             ConstLinkedListIterator( const ConstLinkedListIterator& );
00651             ConstLinkedListIterator operator= ( const ConstLinkedListIterator& );
00652 
00653         public:
00654 
00655             ConstLinkedListIterator( const LinkedList<E>* list, int index ) :
00656                 ListIterator<E>(), list(list), current(NULL), lastReturned(NULL), index(-1) {
00657 
00658                 if( list == NULL ) {
00659                     throw decaf::lang::exceptions::NullPointerException(
00660                         __FILE__, __LINE__, "Parent LinkedList pointer was Null." );
00661                 }
00662 
00663                 if( index < 0 || index > list->listSize ) {
00664                     throw decaf::lang::exceptions::IndexOutOfBoundsException(
00665                         __FILE__, __LINE__, "Given index {%d} is out of range.", index );
00666                 }
00667 
00668                 // index starts at -1 to indicate that we are before begin or that the
00669                 // list is empty.  We always want to start out one before so that the call
00670                 // to next moves us onto the element in question;
00671 
00672                 if( index < this->list->listSize / 2 ) {
00673                     this->current = &this->list->head;
00674                     for( this->index = -1; this->index + 1 < index; ++this->index ) {
00675                         this->current = this->current->next;
00676                     }
00677                 } else {
00678                     this->current = &this->list->tail;
00679                     for( this->index = this->list->listSize; this->index >= index; --this->index ) {
00680                         this->current = this->current->prev;
00681                     }
00682                 }
00683             }
00684 
00685             virtual ~ConstLinkedListIterator() {}
00686 
00687             virtual E next() {
00688 
00689                 if( this->current->next == &(this->list->tail) ) {
00690                     throw NoSuchElementException(
00691                         __FILE__, __LINE__, "No more elements to return from this ListIterator" );
00692                 }
00693 
00694                 this->current = this->current->next;
00695                 this->lastReturned = this->current;
00696                 this->index++;
00697 
00698                 return this->current->value;
00699             }
00700 
00701             virtual bool hasNext() const {
00702                 return ( this->current->next != &(this->list->tail) );
00703             }
00704 
00705             virtual E previous() {
00706 
00707                 if( this->current == &(this->list->head) ) {
00708                     throw decaf::lang::exceptions::IllegalStateException(
00709                         __FILE__, __LINE__,
00710                         "No previous element, must call next() before calling previous()." );
00711                 }
00712 
00713                 this->lastReturned = this->current;
00714                 this->current = this->current->prev;
00715                 this->index--;
00716 
00717                 return this->lastReturned->value;
00718             }
00719 
00720             virtual bool hasPrevious() const {
00721                 return ( this->current != &(this->list->head) );
00722             }
00723 
00724             virtual void remove() {
00725                 throw lang::exceptions::UnsupportedOperationException(
00726                     __FILE__, __LINE__, "Cannot write to a const ListIterator." );
00727             }
00728 
00729             virtual void add( const E& e DECAF_UNUSED ) {
00730                 throw lang::exceptions::UnsupportedOperationException(
00731                     __FILE__, __LINE__, "Cannot write to a const ListIterator." );
00732             }
00733 
00734             virtual void set( const E& e DECAF_UNUSED ) {
00735                 throw lang::exceptions::UnsupportedOperationException(
00736                     __FILE__, __LINE__, "Cannot write to a const ListIterator." );
00737             }
00738 
00739             virtual int nextIndex() const {
00740                 return this->index + 1;
00741             }
00742 
00743             virtual int previousIndex() const {
00744                 return this->index;
00745             }
00746         };
00747 
00748         class ReverseIterator : public Iterator<E> {
00749         private:
00750 
00751             LinkedList<E>* list;
00752             ListNode<E>* current;
00753             int expectedModCount;
00754             bool canRemove;
00755 
00756         private:
00757 
00758             ReverseIterator( const ReverseIterator& );
00759             ReverseIterator operator= ( const ReverseIterator& );
00760 
00761         public:
00762 
00763             ReverseIterator( LinkedList<E>* list ) :
00764                 Iterator<E>(), list( list ), current(NULL), expectedModCount(0), canRemove(false) {
00765 
00766                 if( list == NULL ) {
00767                     throw decaf::lang::exceptions::NullPointerException(
00768                         __FILE__, __LINE__, "Parent LinkedList pointer was Null." );
00769                 }
00770 
00771                 this->expectedModCount = this->list->modCount;
00772                 this->current = &list->tail;
00773             }
00774 
00775             virtual ~ReverseIterator() {}
00776 
00777             virtual bool hasNext() const {
00778                 return this->current->prev != &(this->list->head);
00779             }
00780 
00781             virtual E next() {
00782 
00783                 if( this->expectedModCount != this->list->modCount ) {
00784                     throw ConcurrentModificationException(
00785                         __FILE__, __LINE__, "List modified outside of this Iterator." );
00786                 }
00787 
00788                 if( this->current->prev == &(this->list->head) ) {
00789                     throw NoSuchElementException(
00790                         __FILE__, __LINE__, "No more elements to return from next()" );
00791                 }
00792 
00793                 this->current = this->current->prev;
00794                 this->canRemove = true;
00795 
00796                 return this->current->value;
00797             }
00798 
00799             virtual void remove() {
00800                 if( this->expectedModCount != this->list->modCount ) {
00801                     throw ConcurrentModificationException(
00802                         __FILE__, __LINE__, "List modified outside of this Iterator." );
00803                 }
00804 
00805                 if( !this->canRemove ) {
00806                     throw lang::exceptions::IllegalStateException(
00807                         __FILE__, __LINE__,
00808                         "Invalid State to call remove, must call next() before remove()" );
00809                 }
00810 
00811                 ListNode<E>* next = this->current->prev;
00812                 ListNode<E>* prev = this->current->next;
00813 
00814                 next->next = prev;
00815                 prev->prev = next;
00816 
00817                 delete this->current;
00818 
00819                 this->current = prev;
00820 
00821                 this->list->listSize--;
00822                 this->list->modCount++;
00823                 this->expectedModCount++;
00824                 this->canRemove = false;
00825             }
00826         };
00827 
00828         class ConstReverseIterator : public Iterator<E> {
00829         private:
00830 
00831             const LinkedList<E>* list;
00832             const ListNode<E>* current;
00833 
00834         private:
00835 
00836             ConstReverseIterator( const ConstReverseIterator& );
00837             ConstReverseIterator operator= ( const ConstReverseIterator& );
00838 
00839         public:
00840 
00841             ConstReverseIterator( const LinkedList<E>* list ) :
00842                 Iterator<E>(), list( list ), current(NULL) {
00843 
00844                 if( list == NULL ) {
00845                     throw decaf::lang::exceptions::NullPointerException(
00846                         __FILE__, __LINE__, "Parent LinkedList pointer was Null." );
00847                 }
00848 
00849                 this->current = &list->tail;
00850             }
00851 
00852             virtual ~ConstReverseIterator() {}
00853 
00854             virtual bool hasNext() const {
00855                 return this->current->prev != &(this->list->head);
00856             }
00857 
00858             virtual E next() {
00859 
00860                 if( this->current->prev == &(this->list->head) ) {
00861                     throw NoSuchElementException(
00862                         __FILE__, __LINE__, "No more elements to return from next()" );
00863                 }
00864 
00865                 this->current = this->current->prev;
00866 
00867                 return this->current->value;
00868             }
00869 
00870             virtual void remove() {
00871                 throw lang::exceptions::UnsupportedOperationException(
00872                     __FILE__, __LINE__, "Cannot write to a const Iterator." );
00873             }
00874         };
00875 
00876     public:
00877 
00878         using AbstractSequentialList<E>::listIterator;
00879 
00880         virtual ListIterator<E>* listIterator( int index ) {
00881             return new LinkedListIterator( this, index );
00882         }
00883         virtual ListIterator<E>* listIterator( int index ) const {
00884             return new ConstLinkedListIterator( this, index );
00885         }
00886 
00887         virtual Iterator<E>* descendingIterator() {
00888             return new ReverseIterator( this );
00889         }
00890         virtual Iterator<E>* descendingIterator() const {
00891             return new ConstReverseIterator( this );
00892         }
00893 
00894     private:
00895 
00896         E removeAtFront() {
00897 
00898             if( this->head.next == &this->tail ) {
00899                 throw NoSuchElementException(
00900                     __FILE__, __LINE__, "The Collection is empty." );
00901             }
00902 
00903             ListNode<E>* oldNode = this->head.next;
00904             E result = oldNode->value;
00905 
00906             this->head.next = oldNode->next;
00907             this->head.next->prev = &this->head;
00908 
00909             delete oldNode;
00910 
00911             this->listSize--;
00912             AbstractList<E>::modCount++;
00913 
00914             return result;
00915         }
00916 
00917         E removeAtEnd() {
00918 
00919             if( this->head.next == &this->tail ) {
00920                 throw NoSuchElementException(
00921                     __FILE__, __LINE__, "The Collection is empty." );
00922             }
00923 
00924             ListNode<E>* oldNode = this->tail.prev;
00925             E result = oldNode->value;
00926 
00927             this->tail.prev = oldNode->prev;
00928             this->tail.prev->next = &this->tail;
00929 
00930             delete oldNode;
00931 
00932             this->listSize--;
00933             AbstractList<E>::modCount++;
00934 
00935             return result;
00936         }
00937 
00938         void addToFront( const E& value ) {
00939 
00940             ListNode<E>* newHead = new ListNode<E>( &this->head, this->head.next, value );
00941 
00942             (this->head.next)->prev = newHead;
00943             this->head.next = newHead;
00944 
00945             this->listSize++;
00946             AbstractList<E>::modCount++;
00947         }
00948 
00949         void addToEnd( const E& value ) {
00950 
00951             ListNode<E>* newTail = new ListNode<E>( this->tail.prev, &this->tail, value );
00952 
00953             (this->tail.prev)->next = newTail;
00954             this->tail.prev = newTail;
00955 
00956             this->listSize++;
00957             AbstractList<E>::modCount++;
00958         }
00959 
00960         void addAtLocation( int index, const E& value ) {
00961 
00962             ListNode<E>* location = NULL;
00963 
00964             if( index <= this->listSize / 2 ) {
00965                 location = this->head.next;
00966                 for( int i = 0; i < index; ++i ) {
00967                     location = location->next;
00968                 }
00969             } else {
00970                 location = &this->tail;
00971                 for( int i = this->listSize; i > index; --i ) {
00972                     location = location->prev;
00973                 }
00974             }
00975 
00976             ListNode<E>* newNode = new ListNode<E>( location->prev, location, value );
00977 
00978             (location->prev)->next = newNode;
00979             location->prev = newNode;
00980 
00981             this->listSize++;
00982             AbstractList<E>::modCount++;
00983         }
00984 
00985         bool addAllAtLocation( int index, const Collection<E>& collection ) {
00986 
00987             if( index < 0 || index > this->listSize ) {
00988                 throw decaf::lang::exceptions::IndexOutOfBoundsException(
00989                     __FILE__, __LINE__, "Index for add is outside bounds of this LinkedList." );
00990             }
00991 
00992             int csize = collection.size();
00993             if( csize == 0 ) {
00994                 return false;
00995             }
00996 
00997             std::auto_ptr< ArrayList<E> > copy;
00998             std::auto_ptr< Iterator<E> > iter;
00999 
01000             if( this == &collection ) {
01001                 copy.reset( new ArrayList<E>( collection ) );
01002                 iter.reset( copy->iterator() );
01003             } else {
01004                 iter.reset( collection.iterator() );
01005             }
01006 
01007             ListNode<E>* newNode = NULL;
01008             ListNode<E>* previous = NULL;
01009 
01010             if( index < this->listSize / 2 ) {
01011                 previous = &this->head;
01012                 for( int i = 0; i < index; ++i ) {
01013                     previous = previous->next;
01014                 }
01015             } else {
01016                 previous = &this->tail;
01017                 for( int i = this->listSize; i >= index; --i ) {
01018                     previous = previous->prev;
01019                 }
01020             }
01021 
01022             while( iter->hasNext() ) {
01023                 newNode = new ListNode<E>( previous, previous->next, iter->next() );
01024                 previous->next->prev = newNode;
01025                 previous->next = newNode;
01026                 previous = newNode;
01027             }
01028 
01029             this->listSize += csize;
01030             AbstractList<E>::modCount++;
01031 
01032             return true;
01033         }
01034 
01035         void purgeList() {
01036             ListNode<E>* current = this->head.next;
01037             ListNode<E>* temp = NULL;
01038             while( current != &this->tail ) {
01039                 temp = current;
01040                 current = current->next;
01041                 delete temp;
01042             }
01043         }
01044     };
01045 
01046 }}
01047 
01048 #endif /* _DECAF_UTIL_LINKEDLIST_H_ */