1. The sequence table is so good, why do you need a linked list?
Disadvantages of sequence table:
Second, the definition of singly linked list
Three, the node form of the singly linked list
Fourth, the overall form of the singly linked list
Setting up the head node in the singly linked list is to facilitate the insertion and deletion of nodes at the head of the linked list.
The head node and data node of the singly linked list we talked about in this section are the same type.
Sometimes for convenience, a pointer to the head of the linked list, a pointer to the end of the linked list and an integer representing the length of the linked list can be set in the head node . At this time, the type of the head node is different from the type of the linked list node.
Five, the C++ description of the linked list node
template<typename T>class list
{//One-way linked list
struct node
{ T data; node* next; }; node* head;//Head node pointer int length;//Record the number of element nodes
}
In this way, head is the head pointer, and length records the number of element nodes in the linked list, excluding the head node.
Six, generate a node
node* creatNode(T x)
{//为x生成结点,返回结点地址
node* t;
t = new node;
if (t == 0)
return 0;
t->data = x;
t->next = 0;
return t;
}
Use the new operator to apply for node type space from the operating system.
If the operating system says that I am not rich, and refuses it, it returns 0, which is a null pointer, otherwise it returns the address of the new node.
Seven, initialization
At the beginning, a head node is generated and implemented in the constructor.
void init()
{
head = new node;
head->next = 0;
length = 0;
}
list()
{
init();
}
head is a variable, which stores the address, which is the address of the head node, which has no name.
8. Insert an element after a certain node
void insert(node* p, node* q)
{//p是链表中某个结点的指针,q是一个新结点的指针
//将q插入到p的后面
q->next = p->next;
p->next = q;
length++;
}
void insert(node* p, T x)
{//在指针p所指的结点后面插入x
node* q, * t;
t = creatNode(x);
insert(p, t);
}
C++ function overloading has the same function name but different parameters.
Insert the q node after the node p. You must not disconnect the pointer after p first. Before disconnecting, there must be a pointer to the node after the original p.
Otherwise, the node will be lost.
Nine, insert elements after the head node
void push_front(T x)
{
insert(head, x);
}
With the foreshadowing of the previous insert function, the operation of inserting a node at the head is so simple.
10. Insert a node at the end of the linked list
void push_back(T x)
{
node* p;
p = head;
while (p->next)
{
p = p->next;
}
insert(p, x);
}
First find the end node of the linked list, point to it with pointer p, and then insert data after p.
11. Get the address of the i-th node
node* Address(int i)
{//得到第i个元素结点的地址
if (i<0 || i>length)
return 0;
if (i == 0)
return head;
if (i == 1)
return head->next;
int j = 0;
node* p = head;
while (j < i)
{
p = p->next;
j++;
}
return p;
}
Finding the i-th node in the singly linked list is a basic operation.
12. Insert data before the i-th node
void insert(int i, T x)
{//在链表的第i个数据前面插入x
//即在第i-1个元素后面插入x
node* p;
if (i == 1)
push_front(x);
else if (i == length + 1)
push_back(x);
else
{
p = Address(i - 1);
insert(p, x);
}
}
To insert data at the i-th node, insert data after the i-1th node, and you need to find the i-1th node first.
13. Delete the i-th node
void erase(int i)
{//删除第i个元素结点
if (i<1 || i>length)
return;
node* q, * t;
t = Address(i - 1);
q = t->next;
t->next = q->next;
delete q;
length--;
}
To delete the i-th node, you need to find the i-1th node first.
14. Search in the linked list
node* find(T x)
{//查找元素x,若存在返回地址,否则返回空指针0
node* p = head->next;
while (p != 0)
{
if (p->data == x)
return p;
p = p->next;
}
return 0;
}
15. Release the space occupied by the singly linked list
Implemented in the destructor
~list()
{
node* p;
node* q;
while (head->next)
{
p = head->next;
head->next = p->next;
delete p;
}
delete head;
head = 0;
length = 0;
}
16. Complete code
//#include "stdafx.h" //vc下面工程带的头文件,用dev编译时注释掉即可
#include <iostream>
using namespace std;
template<typename T>class list
{//单向链表
struct node
{
T data;
node* next;
};
node* head;//头结点
int length;
public:
void init()
{
head = new node;
head->next = 0;
length = 0;
}
list()
{
init();
}
int size()
{
return length;
}
void print()
{
node* p;
p = head->next;
while (p != 0)
{
cout << p->data << " ";
p = p->next;
}
cout << endl;
}
node* creatNode(T x)
{//为x生成结点,返回结点地址
node* t;
t = new node;
t->data = x;
t->next = 0;
return t;
}
void insert(node* p, node* q)
{//p是链表中某个结点的指针,q是一个新结点的指针
//将q插入到p的后面
q->next = p->next;
p->next = q;
length++;
}
void insert(node* p, T x)
{//在指针p所指的结点后面插入x
node* q, * t;
t = creatNode(x);
insert(p, t);
}
void push_front(T x)
{
insert(head, x);
}
void push_back(T x)
{
node* p;
p = head;
while (p->next)
{
p = p->next;
}
insert(p, x);
}
node* Address(int i)
{//得到第i个元素结点的地址
if (i<0 || i>length)
return 0;
if (i == 0)
return head;
if (i == 1)
return head->next;
int j = 0;
node* p = head;
while (j < i)
{
p = p->next;
j++;
}
return p;
}
void insert(int i, T x)
{//在链表的第i个数据前面插入x
//即在第i-1个元素后面插入x
node* p;
if (i == 1)
push_front(x);
else if (i == length + 1)
push_back(x);
else
{
p = Address(i - 1);
insert(p, x);
}
}
void erase(int i)
{//删除第i个元素结点
if (i<1 || i>length)
return;
node* q, * t;
t = Address(i - 1);
q = t->next;
t->next = q->next;
delete q;
length--;
}
node* find(T x)
{
node* p = head->next;
while (p != 0)
{
if (p->data == x)
return p;
p = p->next;
}
return 0;
}
~list()
{
node* p;
node* q;
while (head->next)
{
p = head->next;
head->next = p->next;
delete p;
}
delete head;
head = 0;
length = 0;
}
};
int main()
{
list<int> L;
L.push_front(3);
L.push_front(2);
L.push_front(1);
L.print();
L.push_back(4);
L.push_back(5);
L.push_back(6);
L.print();
cout << L.size() << endl;
cout << (L.Address(6)->data) << endl;
L.insert(1, 44);
L.print();
L.insert(3, 55);
L.print();
L.insert(8, 66);
L.print();
cout << "begin to delete:\n";
L.erase(1);
L.print();
L.erase(L.size());
L.print();
L.erase(3);
L.print();
cout << L.find(55)->data << endl;
return 0;
}