# 数据结构与算法：双向链表

## 双向链表的表示

• 双向链表的结点也由数据域和指针域组成；
• 结点之间通过指针域相连，Prev指针指向直接前趋，Next指针指向直接后继；
• 头指针指向首元结点；
• 首元结点的Prev指针为空指针，尾结点的Next指针为空指针。

## 基本操作

——在链表尾部插入一个结点

——在链表中某个结点后插入一个结点

——删除最后一个结点

——删除指定结点后的一个结点

——倒序遍历

## 插入操作

``````//insert link at the first location
void insertFirst(int key, int data) {

struct node *link = (struct node*) malloc(sizeof(struct node));

if(isEmpty()) {
} else {
}

//point it to old first link

//point first to new first link
}``````

## 删除操作

``````//delete first item
struct node* deleteFirst() {

last = NULL;
} else {
}

}``````

## 在链表尾部插入一个结点

``````//insert link at the last location
void insertLast(int key, int data) {

struct node *link = (struct node*) malloc(sizeof(struct node));

if(isEmpty()) {
} else {

//mark old last node as prev of new link
}

//point last to new last node
}``````

## C语言实现

``````
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <stdbool.h>

struct node {
int data;
int key;

struct node *next;
struct node *prev;
};

struct node *last = NULL;

struct node *current = NULL;

//is list empty
bool isEmpty() {
}

int length() {
int length = 0;
struct node *current;

for(current = head; current != NULL; current = current->next){
length++;
}

return length;
}

//display the list in from first to last
void displayForward() {

//start from the beginning

//navigate till the end of the list
printf("\n[ ");

while(ptr != NULL) {
printf("(%d,%d) ",ptr->key,ptr->data);
ptr = ptr->next;
}

printf(" ]");
}

//display the list from last to first
void displayBackward() {

//start from the last
struct node *ptr = last;

//navigate till the start of the list
printf("\n[ ");

while(ptr != NULL) {

//print data
printf("(%d,%d) ",ptr->key,ptr->data);

//move to next item
ptr = ptr ->prev;
printf(" ");
}

printf(" ]");
}

//insert link at the first location
void insertFirst(int key, int data) {

struct node *link = (struct node*) malloc(sizeof(struct node));

if(isEmpty()) {
} else {
}

//point it to old first link

//point first to new first link
}

//insert link at the last location
void insertLast(int key, int data) {

struct node *link = (struct node*) malloc(sizeof(struct node));

if(isEmpty()) {
} else {

//mark old last node as prev of new link
}

//point last to new last node
}

//delete first item
struct node* deleteFirst() {

last = NULL;
} else {
}

}

//delete link at the last location

struct node* deleteLast() {

} else {
last->prev->next = NULL;
}

last = last->prev;

}

//delete a link with given key

struct node* delete(int key) {

struct node* previous = NULL;

//if list is empty
return NULL;
}

//navigate through list
while(current->key != key) {
//if it is last node

if(current->next == NULL) {
return NULL;
} else {
previous = current;

current = current->next;
}
}

//found a match, update the link
//change first to point to next link
} else {
current->prev->next = current->next;
}

if(current == last) {
//change last to point to prev link
last = current->prev;
} else {
current->next->prev = current->prev;
}

return current;
}

bool insertAfter(int key, int newKey, int data) {

//if list is empty
return false;
}

//navigate through list
while(current->key != key) {

//if it is last node
if(current->next == NULL) {
return false;
} else {
current = current->next;
}
}

struct node *newLink = (struct node*) malloc(sizeof(struct node));

if(current == last) {
} else {
}

return true;
}

main() {
insertFirst(1,10);
insertFirst(2,20);
insertFirst(3,30);
insertFirst(4,1);
insertFirst(5,40);
insertFirst(6,56);

printf("\nList (First to Last): ");
displayForward();

printf("\n");
printf("\nList (Last to first): ");
displayBackward();

printf("\nList , after deleting first record: ");
deleteFirst();
displayForward();

printf("\nList , after deleting last record: ");
deleteLast();
displayForward();

printf("\nList , insert after key(4) : ");
insertAfter(4,7, 13);
displayForward();

printf("\nList  , after delete key(4) : ");
delete(4);
displayForward();
}``````

```List (First to Last): [ (6,56) (5,40) (4,1) (3,30) (2,20) (1,10) ]

List (Last to first): [ (1,10) (2,20) (3,30) (4,1) (5,40) (6,56) ]
List , after deleting first record: [ (5,40) (4,1) (3,30) (2,20) (1,10) ]
List , after deleting last record: [ (5,40) (4,1) (3,30) (2,20) ]
List , insert after key(4) : [ (5,40) (4,1) (4,13) (3,30) (2,20) ]
List , after delete key(4) : [ (5,40) (4,13) (3,30) (2,20) ]```