130 likes | 417 Views
Doubly Linked Lists. prev. prev. prev. elem. elem. elem. next. next. next. Doubly Linked Lists. One powerful variation of a linked list is the doubly linked list. The doubly linked list structure is one in which each node has a pointer to both its successor and its predecessor. head.
E N D
prev prev prev elem elem elem next next next Doubly Linked Lists One powerful variation of a linked list is the doubly linked list. The doubly linked list structure is one in which each node has a pointer to both its successor and its predecessor. head tail
Doubly Linked Lists struct Node { char element; Node *prev; Node *next; Node(const char& e=char(), Node *p=NULL, Node *n=NULL) : element(e), prev(p), next(n) { } };
prev NULL prev prev prev elem elem elem tail head NULL next next next next Sentinel Nodes As always, implementation of a data structure is up to the individual. However, one way of implementing a double linked list is to create sentinel nodes at the beginning and end of the list. • Pointers to the sentinel nodes can be stored in a data structure as data members • Advantage: Not necessary to treat the front or rear differently when inserting or removing
prev NULL NULL next head tail Empty Double Linked List head = new Node; tail = new Node; head->next = tail; tail->prev = head; sz = 0;
Deque - Double-Ended Queues A Deque (pronounced ‘deck’) is a data structure in which items may be added to or deleted from the head or the tail. They are also known as doubly-ended queues. The Deque is typically implemented with a linked list, providing easy access to the front and the back of the list, although a dynamic array could also be used for this.
Deque - Double-Ended Queues The deque data structure typically has the following features: • How are the data related? • Sequentially • Operations • insertFirst - inserts an element at the front of a deque • insertLast - inserts an element at the rear of a deque • removeFirst - removes an element from the front of a deque • removeLast - removes an element from the rear of a deque (Note that the previous 2 functions did not return and data values) • First - returns a reference to the element at the front • last - returns a reference to the element at the rear • size, isEmpty
Deque Advantages • Removing a node from the rear of a singly linked list was inefficient because we had to find the next-to-last by searching from the head • The deque is implemented with a doubly linked list. Therefore, now, removing from the rear is not a problem.
prev prev prev prev u head tail t next next NULL next Algorithm: insertFirst() //Create a new node t //Make “t->prev” point to node head //Make “t->next” point to node head->next (i.e., u) Node *t = new Node(e,head,head->next); //Put the address of t into head->next’s “prev” pointer //Put the address of t into head’s “next” pointer head->next->prev = t; head->next = t;
Algorithm: insertFirst() Node *t = new Node(e,head,head->next); head->next->prev = t; head->next = t; sz++;
prev prev NULL prev tail p head old next next next next Algorithm: removeLast() //Save the address of the last node as “old” Node *old = tail->prev; //Make “old->prev->next” point to node “tail” old->prev->next = tail; //Make “tail->prev” point to node “old->prev” tail->prev = old->prev; //Delete “old” delete old-;
Algorithm: removeLast() Node *old = tail->prev; old->prev->next = tail; tail->prev = old->prev; delete old; //Recover the memory sz--;