什么是链表?
链表是节点的集合,节点中存储着数据并连接到其他的节点。通过这种方式,节点可以位于内存中的任何位置,每个节点都存储着链表中其他节点的地址,因此数据很容易从一个节点到达另一个节点。
一、单向链表
如果一个节点将指向另一个节点的指针作为数据成员,那么多个这样的节点可以连接起来,只用一个变量就能访问整个节点序列。
若序列中的节点只包含指向后继节点的链接,则该链表就称为单向链表。
参考例子:剑指offer面试题24——反转链表
#include<iostream>
#include<vector>
#include<stack>
#include<list>
using namespace std;
struct ListNode{
int val;
struct ListNode *next;
ListNode(int x):
val(x),next(NULL){}
};
class Solution{
public:
vector<int> printListFromTailToHead(ListNode* head){
stack<int> nodes; //后进后出的栈
vector<int> result;//先进后出的容器
ListNode* node = head;
while ((node != NULL))
{
nodes.push(node->val);
node = node->next;
}
while (!nodes.empty()){
result.push_back(nodes.top());
nodes.pop();
}
return result;
}
};
int main(){
ListNode *one = new ListNode(1);
ListNode *two = new ListNode(2);
ListNode *three = new ListNode(3);
ListNode *four = new ListNode(4);
ListNode *five = new ListNode(5);
ListNode *six = new ListNode(6);
one->next=two;
two->next=three;
three->next=four;
four->next=five;
five->next=six;
six->next=NULL;
Solution s;
vector<int> v;
v=s.printListFromTailToHead(one);
int len=v.size();
for(int i=0;i<len;i++)
cout<<v[i]<<' ';
cout<<endl;
return 0;
}
二、双向链表
在单向链表中存在着一个固有的问题,这种链表中的节点只包含指向后继节点的指针,从而无法快速访问前驱节点。而为了加快链表处理的速度,可以重新定义链表,该链表中的每个节点有两个指针,一个指向前驱,一个指向后继,而这种链表称为双向链表。
#include <iostream>
using namespace std;
struct node
{
int date;
node* prev;
node* next;
};
class doublelink
{
public:
int doublelink_insert(doublelink* ptr,int position,int member);
int doublelink_erase(doublelink* ptr, int position);
void doublelink_display(doublelink* ptr, int num);
int doublelink_getlength(doublelink* ptr);
doublelink()
{
root = new node;
root->prev = NULL;
root->next = NULL;
length = 0;
}
protected:
private:
int length;
node* root;
};
int doublelink::doublelink_erase(doublelink* ptr, int position)
{
if (ptr->doublelink_getlength(ptr) == 0)
{
cout<<"链表为空,oop!!"<<endl;
return 0;
}
else
{
if (ptr->doublelink_getlength(ptr) == 1)
{
ptr->root->next = NULL;
ptr->length--;
}
else
{
node* deletenode = root->next;
for (int i = 0 ; i < position; i++)
{
deletenode = deletenode->next;
}
deletenode->prev->next = deletenode->next;
deletenode->next->prev = deletenode->prev;
delete deletenode;
ptr->length--;
}
}
}
void doublelink::doublelink_display(doublelink* ptr, int num)
{
node* current = root->next;
for (int i = 0; i < num; i++)
{
cout<<current->date<<" ";
current = current->next;
}
cout<<endl;
}
int doublelink::doublelink_getlength(doublelink* ptr)
{
return ptr->length;
}
int doublelink::doublelink_insert(doublelink *ptr, int position, int member)
{
node* nodeinsert = new node;
nodeinsert->date = member;
if (ptr->doublelink_getlength(ptr) == 0)
{
root->next = nodeinsert;
nodeinsert->prev = nodeinsert;
nodeinsert->next = nodeinsert;
ptr->length++;
return 0;
}
else
{
if (position == 0)
{
/* root->next->prev = nodeinsert;
nodeinsert->prev = root->next->prev;
nodeinsert->next = root->next;
root->next->prev = nodeinsert;*/
nodeinsert->prev = root->next->prev;
nodeinsert->next = root->next;
root->next->prev->next = nodeinsert;
root->next->prev = nodeinsert;
root->next = nodeinsert;
ptr->length++;
return 0;
}
else
{
node* current = root->next;
for (int i = 0; i < position; i++)
{
current = current->next;
}
nodeinsert->next = current;
nodeinsert->prev = current->prev;
current->prev->next = nodeinsert;
//nodeinsert->next = nodeinsert;
current->prev = nodeinsert;
ptr->length++;
return 0;
}
}
}
int main()
{
doublelink* doublelink_ptr = new doublelink;
for (int i = 0; i < 10; i++)
{
doublelink_ptr->doublelink_insert(doublelink_ptr,0,i);
}
doublelink_ptr->doublelink_display(doublelink_ptr,20);
doublelink_ptr->doublelink_erase(doublelink_ptr,2);
doublelink_ptr->doublelink_display(doublelink_ptr,20);
return 0;
}