考研数据结构——#1 线性表

一、顺序表

1. 顺序表的初始化

#define InitSize 10  //定义最大长度

//静态分配
typedef struct {
	int data[InitList];
	int length;
}SqlList;

//动态分配
typedef struct {
	int* data;
	int length;	//当前长度
	int MaxSize;//最大长度
}SqlList;

//初始化顺序表
void InitList(SqlList& L) {
	L.data = (int*)malloc(InitSize * sizeof(int));
	L.length = 0;
	L.MaxSize = InitSize;
}

//增加顺序表的长度
void IncreaseSize(SqlList& L, int len) {
	int* p = L.data;
	L.data = (int*)malloc((L.MaxSize + len) * sizeof(int));
	for (int i = 0; i < L.length; i++) {
		L.data[i] = p[i];
	}
	L.MaxSize += len;
	free(p);
}

2. 顺序表的插入

//插入元素,在位序i的位置插入元素e
bool ListInsert(SqlList& L, int i, int e) {
	if (i<1 || i>L.length + 1) return false;	//i的范围是否有效
	if (L.length >= L.MaxSize) return false;	//当前存储空间已满,不能插入
	for (int j = L.length; j >= i; j--) {
		L.data[j] = L.data[j - 1];
	}
	L.data[i - 1] = e;
	L.length++;
	return true;
}

3. 顺序表的删除

//删除操作,删除位序i个位置上的元素,e是删除的元素
bool ListDelete(SqlList& L, int i, int& e) {
	if (i<1 || i>L.length) return false;
	e = L.data[i - 1];
	for (int j = i; j < L.length; j++) {
		L.data[j - 1] = L.data[j];
	}
	L.length--;
	return true;
}

//删除值位于s和t之间的数
bool Delete_s_t(SqlList& L, int s, int t) {
	if (L.length == 0 || s >= t) return false;
	int k = 0;
	for (int i = 0; i < L.length; i++) {
		if (L.data[i]<s || L.data[i]>t) {
			L.data[k++] = L.data[i];
		}
	}
	L.length = k;
	return true;
}

4. 顺序表的修改

//修改指定元素
void find(SqlList  &L, int e, int n) {
	int pos = LocateElem(L, e); //调用查找的方法
	L.data[pos] = n;
}

5. 顺序表的索引

//按位查找  返回位序i的元素
int GetElem(SqlList L, int i) {
	if (i<1 || i>L.length) return -1;
	return L.data[i - 1];
}

//查找第一个元素值等于e的元素,并返回其位序
int LocateElem(SqlList L, int e) {
	for (int i = 0; i < L.length; i++) {
		if (L.data[i] == e) return i + 1;
	}
	return -1;
}

6. 顺序表的输出

//C++输出
for (int i = 0; i < L.length; i++) {
    cout << L.data[i] << " ";
}
//C输出
for (int i = 0; i < L.length; i++) {
    printf("%d ", L.data[i]);
}

二、单链表(不带头结点)

1. 初始化

typedef struct LNode {
	int data;
	struct LNode* next;
}LNode, * LinkList;
//struct LNode*  == LinkList
//强调节点  用LNode
//强调链表  用LinkList

//初始化单链表
bool InitList(LinkList& L) {
	L = NULL;
	return true;
}

2. 插入

//不带头节点的插入操作,在第i个位置插入元素e
bool ListInsert(LinkList& L, int i, int e) {
	if (i < 1) return false;
	if (i == 1) {
		LNode* s = (LNode*)malloc(sizeof(LNode));
		s->data = e;
		s->next = L;
		L = s;
		return true;
	}
	LNode* p;
	p = L;
	int j = 1;	//当前p指向的是第几个节点,没有头节点,所以从1开始
	while (p && j < i - 1) {
		p = p->next;
		j++;
	}
	if (!p) return false;
	return InsertNextNode(p, e);
}

//前插操作,在p节点前插入元素e
bool InsertPriorNode(LNode* p, int e) {
	if (!p) return false;
	LNode* s = (LNode*)malloc(sizeof(LNode));
	if (!s) return false;
	s->next = p->next;
	p->next = s;
	s->data = p->data;
	p->data = e;
	return true;
}

//前插操作,在节点p之前插入节点s
bool InsertPriorNode(LNode* p, LNode* s) {
	if (!p || !s) return false;
	s->next = p->next;
	p->next = s;
	swap(s->data, p->data);
	return true;
}

//后插操作,在节点p之后插入元素e
bool InsertNextNode(LNode* p, int e) {
	if (!p) return false;
	LNode* s = (LNode*)malloc(sizeof(LNode));
	if (!s) return false;
	s->data = e;
	s->next = p->next;
	p->next = s;
	return true;
}

//尾插法,不带头结点
LinkList List_TailInsert(LinkList& L) {
	InitList(L);
	LNode* s, * r = L;	//r表示表尾指针
	int x;
	bool is_head = true;
	while (cin >> x) {
		s = (LNode*)malloc(sizeof(LNode));

		if (is_head) {
			is_head = false;
			s->data = x;
			L = s;
			r = s;
		}
		s->data = x;
		r->next = s;
		r = s;

	}
	r->next = NULL;
	return L;
}

//头插法,不带头结点
LinkList List_HeadInsert(LinkList& L) {
	InitList(L);
	LNode* s;
	int x;
	while (cin >> x) {
		s = (LNode*)malloc(sizeof(LNode));
		s->data = x;
		s->next = L;
		L = s;
	}
	return L;
}

3. 删除

//删除位序i的节点,e是i节点的值
bool ListDelete(LinkList& L, int i, int& e) {
	if (L == NULL) {
		e = -1;
		return false;
	}
	if (i < 1) return false;
	if (i > 1) {
		LNode* p = GetElem(L, i - 1);
		if (!p || !(p->next)) return false;
		LNode* q = p->next;
		e = q->data;
		p->next = q->next;
		free(q);
	}
	else {
		if (L->next == NULL) {
			e = L->data;
			L = NULL;
		}
		else {
			e = L->data;
			L = L->next;
		}
	}
	return true;
}

//删除指定节点P
bool DeleteNode(LNode* p) {
	if (p->next == NULL) return false;
	//下面这段代码有bug,不能删除最后一个节点,因此要是删除最后一个节点的话要重新进行操作
	LNode* q = p->next;
	p->data = q->data;
	p->next = q->next;
	free(q);
	return true;
}

4.索引

//按位查找,返回第i个元素(不带带头节点)
LNode* GetElem(LinkList L, int i) {
	if (i <= 0) return NULL;
	int j = 1;
	LNode* p = L;
	while (p && j < i) {
		p = p->next;
		j++;
	}
	return p;
}

//按值查找,找到数据域等于e的节点
LNode* LocateElem(LinkList L, int e) {
	LNode* p = L;
	while (p && p->data != e) {
		p = p->next;
	}
	return p;
}

5. 长度

//统计单链表的长度
int Length(LinkList L) {
	int len = 0;
	LNode* p = L;
	while (p) {
		len++;
		p = p->next;
	}
	return len;
}

6. 输出

void print(LinkList L) {
	LNode* s = L;
	while (s != NULL) {

		cout << s->data << " ";
		s = s->next;
	}
	cout << endl;
}

三、 单链表(带头结点)

1. 初始化

bool InitList(LinkList& L) {
	L = (LNode*)malloc(sizeof(LNode));//分配一个头节点
	if (!L) return false;
	L->next = NULL;
	return true;
}

2. 插入

//后插操作,在节点p之后插入元素e
bool InsertNextNode(LNode* p, int e) {
	if (!p) return false;
	LNode* s = (LNode*)malloc(sizeof(LNode));
	if (!s) return false;
	s->data = e;
	s->next = p->next;
	p->next = s;
	return true;
}

//带头节点的插入操作,在第i个位置插入元素e
bool ListInsert(LinkList& L, int i, int e) {
	if (i < 1) return false;
	LNode* p = GetElem(L, i - 1);
	if (!p) return false;
	return InsertNextNode(p, e);
}

//不带头节点的插入操作,在第i个位置插入元素e
bool NoHead_ListInsert(LinkList& L, int i, int e) {
	if (i < 1) return false;
	if (i == 1) {
		LNode* s = (LNode*)malloc(sizeof(LNode));
		s->data = e;
		s->next = L;
		L = s;
		return true;
	}
	LNode* p;
	p = L;
	int j = 1;	//当前p指向的是第几个节点,没有头节点,所以从1开始
	while (p && j < i - 1) {
		p = p->next;
		j++;
	}
	if (!p) return false;
	return InsertNextNode(p, e);
}

//前插操作,在p节点前插入元素e
bool InsertPriorNode(LNode* p, int e) {
	if (!p) return false;
	LNode* s = (LNode*)malloc(sizeof(LNode));
	if (!s) return false;
	s->next = p->next;
	p->next = s;
	s->data = p->data;
	p->data = e;
	return true;
}

//前插操作,在节点p之前插入节点s
bool InsertPriorNode(LNode* p, LNode* s) {
	if (!p || !s) return false;
	s->next = p->next;
	p->next = s;
	swap(s->data, p->data);
	return true;
}

//尾插法,带头结点
LinkList List_TailInsert(LinkList& L) {
	L = (LinkList)malloc(sizeof(LNode));
	L->next = NULL;
	LNode* s, * r = L;	//r表示表尾指针
	int x;
	while (cin >> x) {
		s = (LNode*)malloc(sizeof(LNode));
		s->data = x;
		r->next = s;
		r = s;
	}
	r->next = NULL;
	return L;
}

//头插法,带头结点
LinkList List_HeadInsert(LinkList& L) {
	L = (LinkList)malloc(sizeof(LNode));
	L->next = NULL;
	LNode* s;
	int x;
	while (cin >> x) {
		s = (LNode*)malloc(sizeof(LNode));
		s->data = x;
		s->next = L->next;
		L->next = s;
	}
	return L;
}

3. 删除

//删除位序i的节点,e是i节点的值
bool ListDelete(LinkList& L, int i, int& e) {
	if (i < 1) return false;
	LNode* p = GetElem(L, i - 1);
	if (!p || !(p->next)) return false;
	LNode* q = p->next;
	e = q->data;
	p->next = q->next;
	free(q);
	return true;
}

//删除指定节点P
bool DeleteNode(LNode* p) {
	if (p->next == NULL) return false;
	//下面这段代码有bug,不能删除最后一个节点,因此要是删除最后一个节点的话要重新进行操作
	LNode* q = p->next;
	p->data = q->data;
	p->next = q->next;
	free(q);
	return true;
}

4. 索引

//按位查找,返回第i个元素(带头节点)
LNode* GetElem(LinkList L, int i) {
	if (i < 0) return NULL;
	int j = 0;
	LNode* p = L;
	while (p && j < i) {
		p = p->next;
		j++;
	}
	return p;
}

//按值查找,找到数据域等于e的节点
LNode* LocateElem(LinkList L, int e) {
	LNode* p = L->next;
	while (p && p->data != e) {
		p = p->next;
	}
	return p;
}

5. 长度

//统计单链表的长度
int Length(LinkList L) {
	int len = 0;
	LNode* p = L;
	while (p->next) {
		len++;
		p = p->next;
	}
	return len;
}

6. 输出

void print(LinkList L) {
	LNode* s = L;
	while (s->next != NULL) {
		s = s->next;
		cout << s->data << " ";
	}
	cout << endl;
}

四、双链表

1. 初始化

typedef int ElemType;

typedef struct DNode {
	ElemType data;
	struct DNode* prior, * next;
}DNode, * DLinkList;

//初始化双链表
bool InitDLinkList(DLinkList& L) {
	L = (DNode*)malloc(sizeof(DNode));
	if (L == NULL) {
		return false;
	}
	L->prior = NULL;
	L->next = NULL;
	return true;
}

2. 判空

//判断双链表是否为空
bool empty(DLinkList L) {
	if (L->next = NULL) {
		return true;
	}
	return false;
}

3. 查找

//按位查找:返回第i个结点
DNode* GetElem(DLinkList L, int i) {
	if (i < 0) return NULL;
	int j = 0;
	DNode* p = L;
	while (p != NULL && j < i) {
		p = p->next;
		j++;
	}
	return p;
}

//按值查找:找到第一个数据域为e的结点
DNode* LocateElem(DLinkList L, ElemType e) {
	DNode* p = L;
	if (p == NULL) return NULL;
	p = p->next;
	while (p != NULL && p->data != e) {
		p = p->next;
	}
	return p;
}

4. 插入

//在p节点之后插入s节点
bool InsertNextDNode(DNode* p, DNode* s) {
	if (p == NULL || s == NULL) {
		return false;
	}
	s->next = p->next;
	if (p->next != NULL)
		p->next->prior = s;
	s->prior = p;
	p->next = s;
}

//在p节点后面插入值是e的节点
bool InsertNextDNode(DNode* p, ElemType e) {
	if (p == NULL) return false;
	DNode* q = (DNode*)malloc(sizeof(DNode));
	if (q == NULL) return false;
	q->data = e;
	q->next = NULL;
	q->prior = p;
	if (p->next != NULL) {
		p->next->prior = q;
		q->next = p->next;
	}
	p->next = q;
	return true;
}

//前插,在p节点前面插入节点s
bool InsertPriorDnode(DNode* p, DNode* s) {
	return InsertNextDNode(p->prior, s);
}

//按位插入,在第i个位置插入值为e的节点(位序i)
bool InsertDLinkList(DLinkList& L, int i, ElemType e) {
	if (i <= 0) return false;
	DNode* p = GetElem(L, i - 1);
	return InsertNextDNode(p, e);
}

//尾插法
DLinkList List_TailInsert(DLinkList& L) {
	InitDLinkList(L);
	DNode* p = L;
	ElemType x;
	while (cin >> x) {
		InsertNextDNode(p, x);
		p = p->next;
	}
	return L;
}

//头插法
DLinkList List_HeadInsert(DLinkList& L) {
	InitDLinkList(L);
	ElemType x;
	while (cin >> x) {
		InsertNextDNode(L, x);
	}
	return L;
}

5. 删除

//删除p节点的后继节点
bool DeleteNextNode(DNode* p) {
	if (p == NULL) return false;
	DNode* q = p->next;
	if (q == NULL) return false;
	p->next = q->next;
	if (q->next != NULL) q->next->prior = p;
	free(q);
	return true;
}

//销毁双链表
bool DestoryList(DLinkList& L) {
	while (L->next != NULL) {
		DeleteNextNode(L);
	}
	free(L);
	L = NULL;
	return true;
}

//删除指定节点s
bool DeleteNode(DNode* s) {
	DNode* p;
	p = s->prior;
	p->next = s->next;
	if (s->next != NULL) {
		s->next->prior = p;
	}
	free(s);
	return true;
}

//删除位序i的节点,e是i节点的值
bool ListDelete(DLinkList& L, int i, ElemType& e) {
	if (i <= 0 || i > Length(L)) return false;
	DNode* s;
	s = GetElem(L, i);
	if (s == NULL) return false;
	e = s->data;
	return DeleteNode(s);
}

6. 长度

int Length(DLinkList L) {
	DNode* p = L;
	int len = 0;
	while (p->next != NULL) {
		len++;
		p = p->next;
	}
	return len;
}

7. 输出

void print(DLinkList L) {
	DNode* p = L->next;
	while (p != NULL) {
		cout << p->data << " ";
		p = p->next;
	}
	cout << endl;
}

五、循环单链表(L指向表头)

1. 初始化

typedef struct LNode {
	int data;
	struct LNode* next;
}LNode, * LinkList;
//struct LNode*  == LinkList
//强调节点  用LNode
//强调链表  用LinkList

bool InitList(LinkList& L) {
	L = (LNode*)malloc(sizeof(LNode));//分配一个头节点
	if (L == NULL) return false;
	L->next = L;
	return true;
}

2. 查找

//按位查找,返回第i个元素(带头节点)
LNode* GetElem(LinkList L, int i) {
	if (i < 0) return NULL;
	if (i == 0) return L;
	int j = 1;
	LNode* p = L->next;
	while (p != L && j < i) {
		p = p->next;
		j++;
	}
	return p;
}

//按值查找,找到数据域等于e的节点
LNode* LocateElem(LinkList L, int e) {
	LNode* p = L->next;
	while (p != L && p->data != e) {
		p = p->next;
	}
	if (p->data == e) return p;
	return NULL;
}

3. 长度

//统计单链表的长度
int Length(LinkList L) {
	int len = 0;
	LNode* p = L;
	while (p->next != L) {
		len++;
		p = p->next;
	}
	return len;
}

4. 插入

//后插操作,在节点p之后插入元素e
bool InsertNextNode(LNode* p, int e) {
	if (!p) return false;
	LNode* s = (LNode*)malloc(sizeof(LNode));
	if (!s) return false;
	s->data = e;
	s->next = p->next;
	p->next = s;
	return true;
}

//带头节点的插入操作,在第i个位置插入元素e
bool ListInsert(LinkList& L, int i, int e) {
	if (i < 1) return false;
	LNode* p = GetElem(L, i - 1);
	if (!p) return false;
	return InsertNextNode(p, e);
}


//前插操作,在p节点前插入元素e
bool InsertPriorNode(LNode* p, int e) {
	if (!p) return false;
	LNode* s = (LNode*)malloc(sizeof(LNode));
	if (!s) return false;
	s->next = p->next;
	p->next = s;
	s->data = p->data;
	p->data = e;
	return true;
}

//前插操作,在节点p之前插入节点s
bool InsertPriorNode(LNode* p, LNode* s) {
	if (!p || !s) return false;
	s->next = p->next;
	p->next = s;
	swap(s->data, p->data);
	return true;
}

//尾插法,带头结点
LinkList List_TailInsert(LinkList& L) {
	InitList(L);
	LNode* s, * r = L;	//r表示表尾指针
	int x;
	while (cin >> x) {
		s = (LNode*)malloc(sizeof(LNode));
		s->data = x;
		r->next = s;
		r = s;
	}
	r->next = L;
	return L;
}

//头插法,带头结点
LinkList List_HeadInsert(LinkList& L) {
	InitList(L);
	LNode* s, * r = L;
	int x;
	bool isFirst = true;
	while (cin >> x) {
		s = (LNode*)malloc(sizeof(LNode));
		s->data = x;
		s->next = L->next;
		L->next = s;
		if (isFirst) {
			r = s;
			isFirst = false;
		}
	}
	r->next = L;
	return L;
}

5. 删除

//删除位序i的节点,e是i节点的值
bool ListDelete(LinkList& L, int i, int& e) {
	if (i < 1) return false;
	LNode* p = GetElem(L, i - 1);
	if (p == NULL || p->next == L) return false;
	LNode* q = p->next;
	e = q->data;
	p->next = q->next;
	free(q);
	return true;
}

//删除指定节点P
bool DeleteNode(LinkList& L, LNode* p) {
	LNode* q = p->next;
	p->data = q->data;
	p->next = q->next;

	if (L == q) {
		L = p;
	}
	free(q);
	return true;
}

6.判空

bool Empty(LinkList L) {
	if (L->next == L) {
		return true;
	}
	return false;
}

7.判尾

//判断是否为表尾节点
bool isTail(LinkList L, LNode* p) {
	if (p->next == L) return true;
	return false;
}

8.输出

void print(LinkList L) {
	LNode* s = L->next;
	while (s != L) {
		cout << s->data << " ";
		s = s->next;
	}
	cout << endl;
}

六、循环单链表(L指向表尾)

1. 初始化

typedef struct LNode {
	int data;
	struct LNode* next;
}LNode, * LinkList;
//struct LNode*  == LinkList
//强调节点  用LNode
//强调链表  用LinkList

bool InitList(LinkList& L) {
	L = (LNode*)malloc(sizeof(LNode));//分配一个头节点
	if (L == NULL) return false;
	L->next = L;
	return true;
}

2. 查找

//按位查找,返回第i个元素(带头节点)
LNode* GetElem(LinkList L, int i) {
	if (i < 0) return NULL;
	if (i == 0) return L->next;
	int j = 1;
	LNode* p = L->next->next;
	while (p != L->next && j < i) {
		p = p->next;
		j++;
	}
	if (p == L->next) return NULL;
	return p;
}

//按值查找,找到数据域等于e的节点
LNode* LocateElem(LinkList L, int e) {
	LNode* p = L->next->next;
	while (p != L->next && p->data != e) {
		p = p->next;
	}
	if (p->data == e) return p;
	return NULL;
}

3. 长度

//统计单链表的长度
int Length(LinkList L) {
	int len = 0;
	LNode* p = L;
	while (p->next != L) {
		len++;
		p = p->next;
	}
	return len;
}

4. 插入

//后插操作,在节点p之后插入元素e
bool InsertNextNode(LinkList& L, LNode* p, int e) {
	if (!p) return false;
	LNode* s = (LNode*)malloc(sizeof(LNode));
	if (!s) return false;
	s->data = e;
	s->next = p->next;
	p->next = s;
	if (p == L) L = s;
	return true;
}

//带头节点的插入操作,在第i个位置插入元素e
bool ListInsert(LinkList& L, int i, int e) {
	if (i < 1) return false;
	LNode* p = GetElem(L, i - 1);
	if (!p) return false;
	return InsertNextNode(L, p, e);
}


//前插操作,在p节点前插入元素e
bool InsertPriorNode(LNode* p, int e) {
	if (!p) return false;
	LNode* s = (LNode*)malloc(sizeof(LNode));
	if (!s) return false;
	s->next = p->next;
	p->next = s;
	s->data = p->data;
	p->data = e;
	return true;
}

//前插操作,在节点p之前插入节点s
bool InsertPriorNode(LNode* p, LNode* s) {
	if (!p || !s) return false;
	s->next = p->next;
	p->next = s;
	swap(s->data, p->data);
	return true;
}

//尾插法,带头结点
LinkList List_TailInsert(LinkList& L) {
	InitList(L);
	LNode* s, * r = L;	//r表示表尾指针
	int x;
	while (cin >> x) {
		s = (LNode*)malloc(sizeof(LNode));
		s->data = x;
		r->next = s;
		r = s;
	}
	r->next = L;
	L = r;
	return L;
}

//头插法,带头结点
LinkList List_HeadInsert(LinkList& L) {
	InitList(L);
	LNode* s, * r = L;
	int x;
	bool isFirst = true;
	while (cin >> x) {
		s = (LNode*)malloc(sizeof(LNode));
		s->data = x;
		s->next = L->next;
		L->next = s;
		if (isFirst) {
			r = s;
			isFirst = false;
		}
	}
	r->next = L;
	L = r;
	return r;
}

5. 删除

//删除位序i的节点,e是i节点的值
bool ListDelete(LinkList& L, int i, int& e) {
	if (i < 1) return false;
	LNode* p = GetElem(L, i - 1);
	if (p == NULL || p == L) return false;
	if (p->next == L) {
		L = p;
	}
	LNode* q = p->next;
	e = q->data;
	p->next = q->next;
	free(q);
	return true;
}


//删除指定节点P
bool DeleteNode(LinkList& L, LNode* p) {
	LNode* q = p->next;
	p->data = q->data;
	p->next = q->next;

	if (L == p) {		//尾节点
		q = p;
		while (q->next != p) {
			q = q->next;
		}
		L = q;
	}
	//free(q);   不能这样写,因为指针之间的赋值是指向同一块区域,就比如L和q就是指向相同的区域
	return true;
}

6.判空

bool Empty(LinkList L) {
	if (L->next == L) {
		return true;
	}
	return false;
}

7.判尾

//判断是否为表尾节点
bool isTail(LinkList L, LNode* p) {
	if (p == L) return true;
	return false;
}

8.输出

void print(LinkList L) {
	LNode* s = L->next->next;
	while (s != L->next) {

		cout << s->data << " ";
		s = s->next;
	}
	cout << endl;
}

七、循环双链表

1. 初始化

typedef int ElemType;

typedef struct DNode {
	ElemType data;
	struct DNode* prior, * next;
}DNode, * DLinkList;

//初始化双链表
bool InitDLinkList(DLinkList& L) {
	L = (DNode*)malloc(sizeof(DNode));
	if (L == NULL) {
		return false;
	}
	L->prior = L;
	L->next = L;
	return true;
}

2. 查找

//按位查找:返回第i个结点
DNode* GetElem(DLinkList L, int i) {
	if (i < 0) return NULL;
	if (i == 0) return L;
	int j = 1;
	DNode* p = L->next;
	while (p != L && j < i) {
		p = p->next;
		j++;
	}
	if (p == L) return NULL;
	return p;
}

//按值查找:找到第一个数据域为e的结点
DNode* LocateElem(DLinkList L, ElemType e) {
	DNode* p = L;
	if (p == NULL) return NULL;
	p = p->next;
	while (p != L && p->data != e) {
		p = p->next;
	}
	if (p == L) return NULL;
	return p;
}

3. 长度

int Length(DLinkList L) {
	DNode* p = L;
	int len = 0;
	while (p->next != L) {
		len++;
		p = p->next;
	}
	return len;
}

4. 插入

//在p节点之后插入s节点
bool InsertNextDNode(DNode* p, DNode* s) {
	if (p == NULL || s == NULL) {
		return false;
	}
	s->next = p->next;
	p->next->prior = s;
	s->prior = p;
	p->next = s;
}

//在p节点后面插入值是e的节点
bool InsertNextDNode(DNode* p, ElemType e) {
	if (p == NULL) return false;
	DNode* q = (DNode*)malloc(sizeof(DNode));
	if (q == NULL) return false;
	q->data = e;
	q->prior = p;
	p->next->prior = q;
	q->next = p->next;
	p->next = q;
	return true;
}

//前插,在p节点前面插入节点s
bool InsertPriorDnode(DNode* p, DNode* s) {
	return InsertNextDNode(p->prior, s);
}

//按位插入,在第i个位置插入值为e的节点(位序i)
bool InsertDLinkList(DLinkList& L, int i, ElemType e) {
	if (i <= 0) return false;
	DNode* p = GetElem(L, i - 1);
	return InsertNextDNode(p, e);
}

//尾插法
DLinkList List_TailInsert(DLinkList& L) {
	InitDLinkList(L);
	DNode* p = L;
	ElemType x;
	while (cin >> x) {
		InsertNextDNode(p, x);
		p = p->next;
	}
	return L;
}

//头插法
DLinkList List_HeadInsert(DLinkList& L) {
	InitDLinkList(L);
	ElemType x;
	while (cin >> x) {
		InsertNextDNode(L, x);
	}
	return L;
}

5. 删除

//删除p节点的后继节点
bool DeleteNextNode(DNode* p) {
	if (p == NULL) return false;
	DNode* q = p->next;
	p->next = q->next;
	q->next->prior = p;
	free(q);
	return true;
}

//销毁双链表
bool DestoryList(DLinkList& L) {
	while (L->next != L) {
		DeleteNextNode(L);
	}
	free(L);
	L = NULL;
	return true;
}

//删除指定节点s
bool DeleteNode(DNode* s) {
	DNode* p;
	p = s->prior;
	p->next = s->next;
	s->next->prior = p;
	free(s);
	return true;
}

//删除位序i的节点,e是i节点的值
bool ListDelete(DLinkList& L, int i, ElemType& e) {
	if (i <= 0 || i > Length(L)) return false;
	DNode* s;
	s = GetElem(L, i);
	if (s == NULL) return false;
	e = s->data;
	return DeleteNode(s);
}

6.判空

//判断双链表是否为空
bool empty(DLinkList L) {
	if (L->next = L) {
		return true;
	}
	return false;
}

7.判尾

bool isTail(DLinkList L, DNode* p) {
	if (p->next == L) return true;
	return false;
}

8.输出

void print(DLinkList L) {
	DNode* p = L->next;
	while (p != L) {
		cout << p->data << " ";
		p = p->next;
	}
	cout << endl;
}

八、静态链表

1. 初始化

#define MaxSize 10
#define ElemType int

typedef struct {
	ElemType data;
	int next;
}SLinkList[MaxSize];


void InitSLinkList(SLinkList L) {
	for (int i = 0; i < MaxSize; i++) {
		L[i].next = -2;		//-2表时链表这个位置是空的
	}
	L[0].next = -1;
}

2. 查找

//得到第i个元素的下标
int Get_Index(SLinkList L, int i) {
	int j = 0;	//模拟指针
	int cnt = 0;		//计数
	while (j != -1 && cnt < i) {
		cnt++;
		j = L[j].next;
		//cout << j << " " << L[j].next << endl;
	}
	if (cnt != i) return -1;	//不存在
	return j;
}

//得到第一个是空的元素
int Get_First_Empty_Node(SLinkList L) {
	for (int i = 1; i < MaxSize; i++) {
		if (L[i].next == -2) return i;
	}
}

//	返回L的第i个元素
ElemType GetElem(SLinkList L, int i) {
	int j = Get_Index(L, i);
	return L[j].data;
}

3. 插入

//在第i个节点后面插入值是e的节点
bool InsertNextSNode(SLinkList L, int i, ElemType e) {
	int j = Get_Index(L, i);
	//cout << j << endl;
	int k = Get_First_Empty_Node(L);	//第一个空节点的位置

	L[k].next = L[j].next;
	L[j].next = k;
	L[k].data = e;
	return true;

}

//插入(默认开始是空的)
bool List_Insert(SLinkList L) {
	int tot = 1, pre = 0;
	ElemType x;
	while (cin >> x) {
		L[tot].data = x;
		L[tot].next = -1;
		L[pre].next = tot;
		pre = tot++;
	}
	return true;
}

4. 删除

//删除第i个节点 e是删除元素的值
bool DeleteNode(SLinkList L, int i, ElemType& e) {
	int j = Get_Index(L, i);
	//cout <<i<< "  " << j << endl;
	if (L[j].next == -1) {	//最后一个要特判
		//cout << "asdad" << endl;
		int k = Get_Index(L, i - 1);
		L[j].next = -2;
		e = L[j].data;
		L[k].next = -1;
		return true;
	}
	//相当于交换次序,跟王道之前的删除方法类似
	e = L[j].data;
	int tmp = L[j].next;
	L[j].data = L[L[j].next].data;
	L[j].next = L[L[j].next].next;
	L[tmp].next = -2;
	return true;
}

5.判空

//判断双链表是否为空
bool empty(SLinkList L) {
	if (L[0].next = -1) {
		return true;
	}
	return false;
}

6.输出

void print(SLinkList L) {
	int i = L[0].next;
	while (~i) {
		cout << L[i].data << " ";
		i = L[i].next;
	}
	cout << endl;
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

特立独行の猫

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值