c++——雙向迴圈連結串列常見操作
阿新 • • 發佈:2019-02-09
雙向迴圈連結串列示意圖:
程式碼:
#ifndef __LIST_H__
#define __LIST_H__
#include <stdio.h>
#include<iostream>
#include<assert.h>
using namespace std;
class Listnode
{
public:
int _data;
Listnode * prev; //前續指標
Listnode* next; //後續指標
Listnode(Listnode* _next = NULL,Listnode*_prev = NULL)
: next(_next)
, prev(_prev)
{}
Listnode(const int data, Listnode* _next = NULL, Listnode*_prev = NULL)
:_data(data)
, prev(_prev)
, next(_next)
{ }
void Setdata(int data)
{
this->_data = data;
}
};
class List :public Listnode
{
public:
List();//建構函式
~List();//解構函式
bool Empty() // 清空
{
return this->size == 0;
}
int sizelist()
{
return this->size;
}
void pushfront(const int& data); //頭插
void pushback(const int& data); //尾插
void push_val(const int& data, int pos); //任意位置插入
void popfront(); //頭刪
void popback();//尾刪
void pop_val(int pos);//任意位置刪除
Listnode* findnode(int pos);//指定位置查詢
void reserse();//連結串列的逆置
void sortlist();//連結串列排序
void printlist();
private:
Listnode* head; //頭指標
Listnode* tail; //尾指標
int size;
};
int Getpushfront(); //異常警告
int Getpush_val();
int Getpopfront();
int Getpop_val();
Listnode* Condata(const int& data);
#endif
#include "list.h"
Listnode* Condata(const int& data)//構造一個新的節點
{
Listnode*newnode = new Listnode(data);
if (newnode == NULL)
throw Getpushfront(); //丟擲異常
return newnode;
}
Listnode* List::findnode(int pos)//得到pos位置的節點
{
Listnode* tempnode = head->next;
for (int i = 1; i < pos; i++)
{
tempnode = tempnode->next;
}
return tempnode;
}
List::List()//建構函式構造頭結點
{
head = tail = new Listnode;
head->next = tail;
tail->prev = head;
tail->next = head;
head->prev = tail;
size = 0;
}
List::~List()
{
Listnode*pdel;
Listnode*ptemp;
pdel = head->next; //找到第一個節點
while (pdel != head) //迴圈頭刪
{
ptemp = pdel->next;//定義兩個指標變數 更好釋放
head->next = ptemp;
ptemp->prev = head;
//head->next = pdel->next 一個變數釋放
//pdel->next->prev = head
delete pdel;
pdel = ptemp;
}
delete head;
}
void List::pushfront(const int& data)//頭插
{
Listnode* newnode = Condata(data);
if (size == 0) //本來沒有節點
{
newnode->next = tail;
tail->prev = newnode;
head->next = newnode;
newnode->prev = head;
size++;
return ;
}
newnode->next = head->next;
head->next = newnode;
newnode->next->prev = newnode;
newnode->prev = head;
size++;
}
void List::pushback(const int& data) //尾插
{
Listnode* newnode = Condata(data);
if (size == 0)
{
pushfront(data); //
return;
}
tail->prev->next = newnode;
newnode->prev = tail->prev;
newnode->next = tail;
tail->prev = newnode;
size++;
}
void List::push_val(const int& data, int pos) //任意位置插入
{
Listnode* newnode = Condata(data);
if (pos>(size+1))
{
throw Getpush_val();//丟擲異常
return;
}
if ( (pos==1)||(pos == (size + 1))) //頭插或尾插
{
if (pos== 1)
List::pushfront(data);
else
List::pushback(data);
return;
}
Listnode* tempnode = findnode(pos);//找到這個位置的節點
newnode->next = tempnode; //插入操作
tempnode->prev->next = newnode;
newnode->prev = tempnode;
tempnode->prev = newnode;
/*Listnode* _next =tempnode; //定義兩個變數進行插入操作
Listnode* _prev = tempnode->prev;
_prev->next = newnode;
newnode->next = _next;
newnode->prev = _prev;
_next->prev = newnode;
*/
size++;
}
void List::popfront() //頭刪
{
if (size == 0)
{
throw Getpopfront();
return;
}
Listnode* tempnode = head->next;
head->next = head->next->next;
delete(tempnode);
tempnode = NULL;
size--;
}
void List::popback()//尾刪
{
Listnode* tempnode = tail->prev;
tempnode->prev->next = tail;
tail->prev = tempnode->prev;
delete(tempnode);
tempnode = NULL;
size--;
}
void List::printlist() //列印連結串列
{
Listnode*tempnode = head->next;
if (size == 0)
{
cout << "連結串列為空" << endl;
return;
}
for (int i =0;i<size;i++)
{
printf("%2d " ,tempnode->_data);
tempnode = tempnode->next;
}
printf("\n");
}
void List::pop_val(int pos)//任意位置刪除
{
if (pos<0 || pos>size)
throw Getpop_val(); //丟擲異常
if (pos == 1 || pos == size)
return pos == 1 ? List::popfront() : List::popback();
Listnode* tempnode = findnode(pos);
tempnode->prev->next = tempnode->next;
tempnode->next->prev = tempnode->prev;
delete(tempnode);
tempnode = NULL;
size--;
}
void List::reserse() //逆置
{
Listnode* left = head->next;
Listnode* right = tail->prev;
while (left != right)
{
int data = left->_data;
left->_data = right->_data;
right->_data = data;
left = left->next;
right = right->prev;
}
}
void List::sortlist () //排序
{
Listnode*i_tempnode = head->next;
for (int i = 0; i < size; i++)
{
Listnode* j_tempnode = i_tempnode->next;
for (int j = 0; j < size - i - 1; j++)
{
if (i_tempnode->_data < j_tempnode->_data)
{
int data = j_tempnode->_data;
j_tempnode->_data = i_tempnode->_data;
i_tempnode->_data = data;
}
j_tempnode = j_tempnode->next;
}
i_tempnode = i_tempnode->next;
}
}
int Getpushfront()
{
cout << "開闢節點失敗" << endl;
return 0;
}
int Getpush_val()
{
cout << "任意插入位置非法" << endl;
return 0;
}
int Getpopfront()
{
cout << "連結串列為空,刪除節點失敗" << endl;
return 0;
}
int Getpop_val()
{
cout << "刪除位置不合法" << endl;
return 0;
}
測試程式碼:
#include "list.h"
int main()
{
List list;
list.pushfront(5);
list.pushfront(4);
/*list.pushfront(3);
list.pushfront(2);
list.pushfront(1);
list.pushback(9);
list.pushback(8);
list.pushback(7);*/
list.pushback(6);
/*list.printlist();
list.push_val(11, 4);
list.push_val(11, 1);
list.printlist();*/
///*list.push_val(11, 30);*/
//list.printlist();
//list.popfront();
//list.printlist();
//list.popback();
//list.printlist();
//list.pop_val(1);
//list.printlist();
list.pushback(9);
list.pushback(1);
list.printlist();
/*list.reserse();
list.printlist();*/
list.sortlist();
list.printlist();
return 0;
}