链表的基本操作

#include <stdio.h>
#include <stdlib.h>
typedef int ElemType; 
#define Maxsize 50
#define InisSize 100
typedef struct SNode {  //定义单链表结点类型
	ElemType data;
	struct SNode * next;
}SNode, *SLinklist;
typedef struct List {   //管理循环单链表 
	SNode* first;  //指向第一个节点(头节点) 
	SNode* last;   //指向最后一个节点 
	int size;
}List;//管理链表头尾节点 

typedef struct DNode {  //定义双链表结点类型
	ElemType data;
	struct DNode* prior, * next;
}DNode,*DLinklist;
typedef struct DList {  // 管理循环双链表 
	DNode* first;
	DNode* last;
	int size;
}DList;

typedef struct LNode {//链式结构
	char ch; 
	ElemType data;
	struct LNode* next;/*/p/*/ 
}LNode,*LinkList;
typedef struct {
	int* data;   
	int MaxSize, length;
}SeqList;
//表的基操 
bool ListInsert(SeqList* L, int i, int e);      //顺序表插入 
bool ListDelete(SeqList* L, int i, ElemType* e);//顺序表删除 
int LocateElem(SeqList L, ElemType e);			//顺序表查找 
LinkList List_HeadInsert(LinkList L);			//采用头插法 建立单链表 
bool ListInsert_i(LinkList L,int i,ElemType e);//插入链表第i个位置 
LinkList List_TailInsert(LinkList L);			//采用尾插法 建立单链表 
LNode* GetElem(LinkList L, int i);				// 查找第i个节点并将该节点返回 
bool List_delete(LinkList L, int i);			//删除链表第i位置的节点 
int List_Length(LinkList L);					//获得链表的长度 
LinkList List_Reverse(LinkList L);				//单链表的逆置  (头插法/迭代) O(1) 
LinkList List_Reverse2(LinkList L);				//单链表的逆置   (递归) 
void ReverseDoubleList(DList L);             	//逆置一个含有两个以上节点的循环双链表。

//单循环链表 
void SLinkList_create(List *list);				//循环单链表的初始化 
void push_back(List* list, ElemType e);         //循环单链表尾插法 
void show_list(List* list);						//打印循环单链表数据
SNode* getNode(ElemType e);						//创建新结点 
void push_front(List* list, ElemType n);        //循环单链表头插法 
void pop_back(List* list);						//循环链表尾删法 
void pop_front(List* list);						//循环链表头删法 

//双循环链表 
void DLinkList_create(DList* list);				//双循环链表初始化 
DNode* getDNode(ElemType e);					//创建新节点 
void push_backD(DList* list, ElemType e);		//双循环链表尾插 
void push_frontD(DList* list, ElemType e);      //双循环链表头插 
void pop_backD(DList* list);					//双循环链表尾删 
void pop_frontD(DList* list);					//双循环链表头删 
void show_listD(DList* list);	//打印双链表数据 

//p17 ,01
void delx(SeqList* s,int x);
//02
void reverse(SeqList* s); 
//03
int delMin(SeqList* s);
//04有序,05无序    
void del_s_t(SeqList* l,int s,int t);        //删除介于s和t的所有元素 
//06  有无序均适合 
void del_repeat(SeqList* s); 
//07
SeqList mergeList(SeqList* s1,SeqList* s2); 
//08
void exchage(int array[],int n,int m,int arraySize);
void reverse(int array[],int left,int right,int arraySize);
//09 
void Binary_Search_List(SeqList* s,int key);
//10
void reverse(int R[],int from,int to);
void Converse(int R[],int n,int p); 
 



//038, 01 
void del_x(LinkList l,ElemType e); 
//02
void del_x1(LinkList l,ElemType e); 
//03
void print(LinkList l);
//04
void del_min(LinkList l); 
//05
void reverse(LinkList l);
//06
void Sort(LinkList l);
//07                                          删除介于min与max之间的数 
void del_min_max(LinkList l,int min,int max); 
//08
LinkList find_com_node(LinkList l1,LinkList l2);
int length(LinkList l);
//09 
void del_list(LinkList l); 
//10 
LinkList discrete_one_two(LinkList l);
//11 
LinkList discrete_one_two_2(LinkList l); 
//12 
void remove_repeat(LinkList l); 
//13 
LinkList mergeLinkList(LinkList l1,LinkList l2);
//14 
LinkList mergeA_B(LinkList l1,LinkList l2); 
//15 
void search_jiaoji(LinkList A,LinkList B);
//16 
int Is_childList(LinkList l1,LinkList l2);
//int KMP_Is_childList(LinkList l1,LinkList l2); 
//17 
int isSymmetry(DList* list);
//18
void merge_oneCycleList(List* list1,List* list2);
//19
void del_min_onecycleList(List* list); 
//21
SNode* isCycleList(List* list); 
//24
void func(LinkList l,int n); 
//25
void chang_list(LinkList l);


int Is_qian_N_duichen(LinkList head,int n);   //判断不带头结点的单链表前n个字符是否中心对称 
LNode* Fast_Find_Mid_Node(LinkList l); 			//快速找到未知长度链表的中间节点 
LinkList ji_ou_List(LinkList l);         //将奇数结点偶数结点排在一起,且偶数结点再奇数节点后 
LinkList remove_end_n(LinkList l,int n);   //删除链表倒数第n个结点 
LinkList MergeTowList(LinkList l1,LinkList l2);  //递归合并两个有序链表 
LNode* getIntersectionNode(LinkList l1,LinkList l2); //递归找到相交链表 

int Is_Symmestery(LinkList l,int n); 
 
 
int Mergelistl1_l2(LinkList l1,LinkList l2,LinkList l3);

int main() {
	
//		LinkList l,l2,l1;
//		
//		l1 = List_TailInsert(l1);
//		l2 = List_TailInsert(l2);
//		KMP_Is_childList(l1,l2); 
//		int flag = Is_childList(l1,l2);
//		printf("%d",flag);
//		if(flag == 1){
//			printf("成功");	
//		}else if(flag == 0){
//			printf("失败"); 
//		}
//		search_jiaoji(l1,l2);
//		l =  mergeA_B(l1,l2); 
//		l = mergeLinkList(l1,l2);
//		remove_repeat(l);
//		l2 = discrete_one_two_2(l);
//		A = discrete_one_two(l); 
//		Sort(l);
//       del_min_max(l,3,5); 
//        del_list(l);
//		l = l->next;
//		del_x1(l,3);
//		print(l);
//		del_min(l);
//       reverse(l);
//				l = l->next;
//				l1 = l1->next;
//		while(l!=NULL){ //l起始结点为有效结点 
//			printf("%d ",l->data);
//			l = l->next;
//		}
//		putchar('\n');
//				l2 = l2->next;
//		while(l2!=NULL){ //l起始结点为有效结点 
//			printf("%d ",l2->data);
//			l2 = l2->next;
//		}
//		SeqList
//		DList list;
//		DLinkList_create(&list);
		for(int i = 0; i < 5; i++){
//			push_frontD(&list,0);
//			push_frontD(&list,3);
//			push_frontD(&list,3);
//			push_frontD(&list,2);
//			push_frontD(&list,0);
		}
//		if(isSymmetry(&list)){
//			printf("对称");
//		}else{
//			printf("不对称");
//		}
//		putchar('\n'); 
//		show_listD(&list);
//		putchar('\n');
//		pop_frontD(&list);
//		show_listD(&list);
//		
	
//	
//		List list1,list2;
//		SLinkList_create(&list1);
//		SLinkList_create(&list2);	
//		for(int i = 0; i < 5; i++){
			
//			push_back(&list1,1);
//			push_back(&list1,5);
//			push_back(&list1,4);
//			push_back(&list1,3);
//			push_back(&list1,8);	
//			push_back(&list2,i);	
//			}
//		merge_oneCycleList(&list1,&list2);
//		del_min_onecycleList(&list1);
//	     show_list(&list1); 
//	      show_list(&list2); 
//		
//
//	     printf("\n");
//	     pop_front(&list);
//	      pop_front(&list);
//		  show_list(&list); 
//		 
		 
		
//     DLinklist DL =  DLinkList_create();
//     if(DL){
//     	printf("创建成功"); 
//	 }else{
//	 	printf("创建失败");
//	 }

	LinkList L,L1,L2 = NULL;
	L = List_TailInsert(L);
//	L = L->next;
	L1 = List_TailInsert(L1);
//	L1 = L1->next;
//	L =  List_Reverse2(L);
//		L = ji_ou_List(L);
//    L = MergeTowList(L,L1);
     int num = Mergelistl1_l2(L,L1,L2);
     printf("%d",L2->next->data);
	L2 = L2->next;
//	int length = List_Length(L);
//	printf("%d\n",length); 
//	List_delete(L,3); 
//	if(ListInsert_i(L,3,100)){
//		printf("插入成功\n"); 
//	}else{
//		printf("插入失败\n");
//	}


//	LNode* l = GetElem(L,4); 
//	if(l){
//		printf("%d\n",l->data);
//	}
//	L = L->next;

	while(1){
		if(L2!=NULL){
		printf("%d ",L2->data);	
		L = L2->next;
		}
		if(L2 == NULL)break;
	}
	
	
//	SeqList s;
//	int e; 
//	s.data = (int*)malloc(sizeof(int) * 50);
//	bool b =ListInsert(&s, 1, 1);
//    ListInsert(&s, 2, 2);
//    ListInsert(&s, 3, 3);
//    ListInsert(&s, 4, 4);
//    ListInsert(&s, 5, 5);
//    ListInsert(&s, 6, 5);
//    ListInsert(&s, 7, 7);
//     Binary_Search_List(&s,7);
//	for(int i = 0; i < s.length; i++)printf("%d ",s.data[i]);
//    SeqList s2 = mergeList(&s,&s1); 
//     int data = LocateElem(s,4);
//	 if(data != 0){
//	 	printf("查找成功%d\n",data); 
//	 }else{
//	 	printf("查找失败%d\n",data);
//	 }
     ListDelete(&s,1,&e);
     printf("删除了%d\n",e);
//	 delx(&s,3);
//	del_repeat(&s);
//		
//		for(int i = 0; i < s2.length; i++)
//		printf("%d ",s2.data[i]);

	return 0;
}//链表的顺序存储    插入 
bool ListInsert(SeqList* L, int i, int e) {
	if (i<1 || i>L->length+1) { //超过范围 
		return false;
	}
	if (L->length == Maxsize) {   //链表已满 
		return false;
	}
	for (int j = L->length; j >= i; j--) {
		L->data[j] = L->data[j - 1];
	}
	L->data[i - 1] = e;  //插入第i个位置 
	L->length++;   //length初始为0; 
	return true;
}
//顺序表删除 
bool ListDelete(SeqList* L, int i, ElemType* e) {
	if (i < 1 || i>L->length) {
		return false;
	}
	if (L->length == 0)return false;
	*e = L->data[i - 1];
	for (int j = i-1; j < L->length; j++) {
		L->data[j] = L->data[j];
	}
	L->length--;
	return true;
}
int LocateElem(SeqList L, ElemType e) {
	for (int i = 0; i < L.length; i++) {
		if (L.data[i] == e)return i + 1;
	}
	return 0;
}
//采用头插法 建立单链表 
LinkList List_HeadInsert(LinkList L) {
	LNode* s; int x;
	L = (LinkList)malloc(sizeof(LNode)); //创建头节点 
	L->next = NULL;
	scanf("%d", &x);
	while (x != 0) {  //0表示输入结束 
		s = (LNode*)malloc(sizeof(LNode));
		s->data = x;
		s->next = L->next;  
		L->next = s;
		scanf("%d", &x);
	}
	return L;
}
//插入链表第i个位置 
bool ListInsert_i(LinkList L, int i, ElemType e) {
	LNode* s;
	LinkList l;
	int j = 1;
	l = L;
	while (l && j < i) {//查找第i个位置 
		j++;
		l = l->next;
	}
	if (!l || j > i)return false;//不存在第i个位置 

	s = (LNode*)malloc(sizeof(LNode));
	s->data = e;
	s->next = l->next;
	l->next = s;
	return true;
}
//采用尾插法建立单链表 
LinkList List_TailInsert(LinkList L) {
	int x;
	L = (LinkList)malloc(sizeof(LNode));
	LNode* s, * r = L;
	scanf("%d", &x);
	while (x != 0) {
		s = (LNode*)malloc(sizeof(LNode));
		s->data = x;
		r->next = s;
		r = s;
		scanf("%d", &x);
	}
	r->next = NULL;
	return L;
}
// 查找第i个节点并将该节点返回  
LNode* GetElem(LinkList L, int i) {
	if (i < 1)return NULL;
	int j = 1;
	LNode* p = L->next;	//找到第一个节点 
	while (p && j < i){
		p = p->next;
		j++;
	}
	return p;
}
//删除链表第i位置的节点 
bool List_delete(LinkList L, int i) {
	int j = 0;
	LNode* n = L, * N;
	while (n && j < i - 1) { //找到第i-1位置的节点 
		n = n->next;
		j++;
	}
	if (n == NULL || j != i - 1 || n->next == NULL) {
		return false;
	}else{
		N = n->next;
		n->next = N->next;
		free(N);
		return true;
	}
}
//获得链表的长度 
int List_Length(LinkList L) {
	int length = 0;
	LNode* N = L->next;//先指第一个有效的节点 
	while (N) {
		length++;
		N = N->next;
	}
	return length;
}
//单链表的逆置    (头插法)		O(1) 
LinkList List_Reverse(LinkList L) {
	LNode* L1 = L->next,*L2;  //L1记录原来链表有效节点位置,L2作为遍历节点 
	L->next = NULL;  //致L2后继位空作为头节点 
	while (L1) {
		L2 = L1->next; //标记L1指向后一个节点记为L2 
		L1->next = L->next;  //将L1后继改为L1头节点的下一个位置 
		L->next = L1;  //将L1作为表头 的下一个位置作为头 
		L1 = L2;   //L1改为原来位置的后继 
	}
	return L;  //返回新链表的头指针
}
//单链表的逆置    (递归) 注意开始调用从头节点后一个有效结点开始 
LinkList List_Reverse2(LinkList L) {
	if (L == NULL || L->next == NULL) {
		return L;
	}
	LinkList newhead = List_Reverse2(L->next); //递归找到最后一个节点 
	L->next->next = L;   //反转链表 
	L->next = NULL;
	return newhead;
}
void ReverseDoubleList(DList L){  //逆置双循环链表 
	DNode* begin = L.first;
	DNode* end = L.last;
	while(begin != end && begin->prior != end){
		ElemType temp = begin->data; //逆置双循环链表实际就将内部数据交换 
		begin->data = end->data;
		end->data = temp;
		begin = begin->next;
		end = end->prior; 
	} 
}
DLinklist DLinkList_create() {
	DNode* DL = (DLinklist)malloc(sizeof(DNode));
	if (DL == NULL) {
		printf("创建失败");
		return NULL;
	}
	DL->prior = DL;
	DL->next = DL;
	return DL;
}
//循环单链表的初始化 
void SLinkList_create(List *list) {
	SNode* L = (SNode*)malloc(sizeof(SNode));
	if (L != NULL){//初始化一个空的头节点 
		list->first = list->last = L;
		list->last->next = list->first;
		list->size = 0;
	}	
}
//循环单链表尾插法 
void push_back(List* list,ElemType e) {
	SNode* p = getNode(e);
	list->last->next = p;           //插入新结点 
	list->last = p;                 //更改管理结点指向尾接点  
	list->last->next = list->first;  //重新形成循环 
	list->size++;                  //有效结点数加一 
}
//打印循环单链表数据 
void show_list(List* list) {
	if(list->size == 0)return ;
	SNode* p = list->first->next;  //指向第一个有效数据 
	while (p != list->first) {     //不等于头节点一直输出 
		printf("%d ", p->data);
		p = p->next;
	}
}
//创建新结点 
SNode* getNode(ElemType e) {
	SNode* p = (SNode*)malloc(sizeof(SNode));
	if (p != NULL) {
		p->data = e;
		p->next = NULL;
		return p;
	}
	return NULL;
}
//循环单链表尾插法 
void push_front(List* list, ElemType e) {
	SNode* p = getNode(e);
	p->next = list->first->next;
	list->first->next = p;
	if (list->first == list->last) { //表示当添加第一个有效结点时更新管理结点尾结点 
		list->last = p;
	}
	list->size++;
}
//循环链表尾删法 
void pop_back(List* list) {
	if (list->size == 0) {
		return ;
	}
	SNode* p = list->first;
	while (p->next != list->last) {  //找到最后一个结点的前一个节点 
		p = p->next;
	}
	free(list->last);  //删除最后一个结点 
	list->last = p;    //重新指向最后一个结点 
	list->last->next = list->first;  //重新形成循环 
	list->size--;    //个数减一 
}
//循环链表头删法 
void pop_front(List* list) {
	if (list->size == 0) {
		return;
	}
	SNode* p = list->first->next;   //p指向第一个有效结点也就是要被删除的结点 
	list->first->next = p->next;
	free(p);
	if (list->size == 1) {   		//若被删除的结点前只有一个更改管理表头尾指针 
		list->first = list->last;
	}
	list->size--;
}
//双循环链表初始化 
void DLinkList_create(DList* list) {
	DNode* p = (DNode*)malloc(sizeof(DNode));
	if (p == NULL) {
		printf("创建失败");
		return;
	}
	list->first = list->last = p;       
	list->first->prior = list->last;   //形成双循环 
	list->last->next = list->first;
	list->size = 0;
}
//创建新结点 
DNode* getDNode(ElemType e){
	DNode* p = (DNode*)malloc(sizeof(DNode));
	if (p) {
		p->data = e;
		p->next = p->prior = NULL;
		return p;
	}
	return NULL;
}
//双循环链表尾插法 
void push_backD(DList* list, ElemType e){
	DNode* p = getDNode(e);
	p->next = list->last->next;   //插入结点与尾结点后继连接 形成尾结点 
	p->next->prior = p;
	p->prior = list->last;       //插入结点与上一个尾接点连接 
	list->last->next = p;
	list->last = p;              //更新尾结点 
	list->size++;
}
//打印双循环链表 
void show_listD(DList* list) {
	if(list->size == 0)return ;
	DNode* p = list->first->next;  //指向第一个有效数据 
	while (p != list->first){
		printf("%d ", p->data);
		p = p->next;
	}
}
//双循环链表头插 
void push_frontD(DList* list, ElemType e) {
	DNode* p = getDNode(e);
	p->next = list->first->next;
	p->next->prior = p;
	p->prior = list->first;
	list->first->next = p;
	if (list->first == list->last) {   //若插入时没有有效结点更改尾结点 
		list->last = p;
	}
	list->size++;
}
//双循环链表尾删 
void pop_backD(DList* list) {
	if (list->size == 0) {
		return;
	}
	DNode* p = list->last;
	list->last = p->prior;				//更改尾结点 
	p->next->prior = list->last;
	list->last->next = p->next;
	free(p);
	list->size--;
}
//双循环链表头删 
void pop_frontD(DList* list) {
	if (list->size == 0) {
		return;
	}
	DNode* p = list->first->next;  //指向第一个有效结点 
	p->next->prior = list->first;  //更改删除节点的指向 
	list->first->next = p->next;
	free(p);
	if (list->size == 1) {        //若删除时只有一个结点更改链表管理结点指向 
		list->first = list->last;
	}
	list->size--;
}


int delMin(SeqList* s){//删除最小元素 
	if(s->length == 0)return -1;//表空不操作 
	int i = 0,min = 0;
	for(i = 1; i < s->length; i++){
		if(s->data[i]<s->data[min])min = i;
	}
	int Min = s->data[min];
	s->data[min] = s->data[s->length-1];
	s->length--;
	return Min;
}

//删除顺序表为x的数 
void delx(SeqList* s,int x){
	int k = 0, i = 0,sum = 0;
	while(i < s->length){
		if(s->data[i] == x)k++;
		else s->data[i-k] = s->data[i];
		i++;
	}
	s->length = s->length-k;
//	printf("%d\n",s->length);
} 

void reverse(SeqList* s){//逆置顺序表 
	int temp;
	for(int i = 0; i < s->length/2; i++){
		temp = s->data[i];
		s->data[i] = s->data[s->length-i-1];
		s->data[s->length-i-1] = temp;
	}
}
void del_s_t(SeqList* l,int s,int t){//删除给定值s-t之间所有元素 
	if(s >= t || l->length == 0)return;
	int k = 0;
	for(int i = 0; i < l->length; i++){
		if(l->data[i]>=s&&l->data[i]<=t){
			k++;
		} else{
		 l->data[i-k] = l->data[i];
		} 
	}
	l->length = l->length-k;
}
void del_repeat(SeqList* s){// 删除有序顺序表所有重复元素 
	int len = 1,j = 1,i = 0;
	while(j < s->length){
		for(i = 0; i < len; i++){
			if(s->data[i] == s->data[j])break; 
	}
	if(i == len){  //正常退出 
		s->data[len++] = s->data[j++]; //将j所指数据赋值到不重复的顺序表中(对原来值进行覆盖) 
	}else{
		j++; //有重复值,则该j就不赋了进行下次比较 
	}
    }
    s->length = len;//重新修改顺序表长度 
}
SeqList mergeList(SeqList* s1,SeqList* s2){//俩有序顺序表合并一个有序顺序表 
	SeqList s;
	s.data = (int*)malloc(sizeof(int) * (s1->length+s2->length));
	int i = 0, j = 0;
	while(i < s1->length && j < s2->length){
		if(s1->data[i] <= s2->data[j]){
			s.data[s.length++] = s1->data[i];
			i++;
		}else{
			s.data[s.length++] = s2->data[j];
			j++;
		}
	}
	while(i<s1->length){
		s.data[s.length++] = s1->data[i];
		i++;
	}
	while(j<s2->length){
		s.data[s.length++] = s2->data[j];
		j++;
	}
	return s;
}
void exchage(int array[],int m,int n,int arraySize){//数组中存入a1---am,b1---bn变为b1---bn,a1---am 
		reverse(array,0,n+m-1,arraySize);
		reverse(array,0,n-1,arraySize);
		reverse(array,n,n+m-1,arraySize);
}
void reverse(int array[],int left,int right,int arraySize){
		if(left >= right || right >= arraySize)return;
		int j = 0;
		for(int i = left; i <= (left+right)/2; i++){
			int temp = array[i];
			array[i] = array[right-j];
			array[right-j] = temp;
			j++;
		}
}
void Binary_Search_List(SeqList* s,int key){//找k,若存在与后继交换否则插入使表递增 
	int low = 0,height = s->length-1;
	int mid;	
	while(low <= height){
		mid = (low+height)/2;
		if(s->data[mid] == key){
			break;		
		}else if(s->data[mid] < key){
			low = mid+1;
		}else{
			height = mid-1;
		}
	}
	if(s->data[mid] == key && s->data[mid]!=s->data[s->length-1]){//若存在 且不是最后一个元素(没有后继) 
		int temp = s->data[mid];
		s->data[mid] = s->data[mid+1];
		s->data[mid+1] = temp;
	}
	if(low > height){  //最后排序结束时low = height+1,将未找到的值插入low所指的位置 
		int i;
		for(i = s->length; i > low;i--){
			s->data[i] = s->data[i-1];
		}
		s->data[i] = key;//插入该值 
		s->length++;
	}	
}

void del_x(LinkList l,ElemType e){//删除不带头结点所有值为x结点 
		if(l == NULL)return;
		if(l->data == e){ //防止断链,将删除的结点改为删除其后面一个结点 
		    LNode* p = l->next;
		    l->data = p->data;
		    l->next = p->next;
		    free(p);
		    del_x(l,e); //再从l递归防止l也为要删除的结点 
		}else{
		    del_x(l->next,e);	
		}
}
void del_x1(LinkList l,ElemType e){//带头结点栓除所有x结点 
	 LNode* p;
	 	l = l->next;
	 while(l){
	 	if(l->data == e){
	 		p = l->next;
		    l->data = p->data;
		    l->next = p->next;
		    free(p);
		 }else l  = l->next;
	 }
}
void print(LinkList l){//从尾到头反向输出每个节点 
	l = l->next;
	if(l == NULL){
		return;
	}
	if(l != NULL){
		print(l);
		printf("%d ",l->data);
	}

}
void del_min(LinkList l){//带头结点链表删除最小节点 
	LNode* min = l->next,*p;
	l = min->next;
	while(l!=NULL){
		if(min->data>l->data)min = l;
		l = l->next;
	}
	p = min->next;
	min->data = p->data;
	min->next = p->next;
	free(p);
}
void reverse(LinkList l){//单链表就地逆置空间复杂度O(1) 
	LNode *p1 = l->next,*p3;
	l->next = NULL;  //最后l依然是头结点 
	while(p1){
		p3 = p1->next; //保存后继 
		p1->next = l->next;  //p1结点连在头结点后 
		l->next= p1;  //重新定位头 
		p1 = p3;
	}
}
//构造单结点链表以此从原来链表找一个合适结点插入进来 
void Sort(LinkList l){
	LNode* p = l->next,*pre;
	LNode* r = p->next;
	p->next = NULL;  //构造只含有一个数据节点的有序表 
	p = r;    //指向第二个有效结点 
	while(p!=NULL){
		r = p->next;  //保存后继结点 
		pre = l;
		while(pre->next != NULL && pre->next->data < p->data)pre = pre->next;
		p->next = pre->next;
		pre->next = p;
		p = r;
	} 
}
void del_min_max(LinkList l,int min,int max){//删除介于Min和max之间的元素 
	LNode* p = l->next;
	while(p != NULL){
		if(p->data >= min && p->data <= max){
			LNode* temp = p->next;
			p->data = temp->data;
			p->next = temp->next;
			free(temp);
		}else{
			p = p->next;
		}
	}
}
/*分析
  一但发现公共结点则从该结点到尾一定全是公共结点(因为结点只有一个后继) 
   则公共结点的长度相同, 则考虑若不同长度的链表
   通过先遍历长的达到最后长度和短的一样再共同遍历、
   找到共同结点 

*/
LinkList find_com_node(LinkList l1,LinkList l2){
	 int len1,len2,cha; //1表长度,2表长度,两表之差 
	 LinkList longList,shortList;  //长链表 短链表 
	 len1 = length(l1);
	 len2 = length(l2);
	 if(len1 > len2){
	 	longList = l1->next;
		 shortList = l2->next;
		 cha = (len1-len2);
	 }else{
	 	longList = l2->next;
		 shortList = l1->next;
		 cha = (len2-len1);
	 }
	 while(cha--){
	 	longList = longList->next; //循环找到从该链表与短链表到尾长度相同的结点 
	 }
	 while(longList){
	 	if(longList != shortList){
	 		longList = longList->next;
	 		shortList = shortList->next;
		 }else return longList; //找到第一个相同的结点从这以后全相同 
	 }
	 return NULL;
}
LNode* getIntersectionNode(LinkList l1,LinkList l2){//递归找到相交链表  
	LNode* head1 = l1,*head2 = l2;
	while(l1 != l2){//最后两指针分别遍历对面,长的指针重新遍历到短的指针时,短的指针所指当前链表与长指针一样长 
		l1 = l1?l1->next:head2;
		l2 = l2?l2->next:head1;
	}
	return l1;//l2;
} 
int length(LinkList l){
	int length = 0;
	l = l->next;
	while(l){
		length++;
		l = l->next;
	}
	return length;
}
void del_list(LinkList l){//但头结点链表,递增输出单链表各节点 
	LNode* head = l,*pre = l,*min = l->next;
	while(head->next){
		while(head->next){//遍历找出最小结点 
			if(head->next->data < min->data){
				min = head->next;
				pre = head;
			}
			head = head->next;
		}//输出并释放空间,再次重新从头开始找第二小结点 
		printf("%d ",min->data);
		pre->next = min->next;
		free(min);		
		min = l->next;
		head = l;
		pre = l;
	}
	free(head);
}
//将l奇结点断链存到l1中 ,剩下偶节点还在L中 
LinkList discrete_one_two(LinkList l){
	LinkList l1 = (LinkList)malloc(sizeof(LNode));//l1存储奇结点 
	LNode *p = l->next,*q,*r,*pre;
	int count = 1;
	r = l1;//l1尾结点 
	r->next = NULL;
	pre = l;
	while(p){
		q = p->next;
		if(count%2 == 1){		//尾插 
			p->next = NULL;//断链,获得单个节点 
			r->next = p;
			r = p;
			pre->next = q; //保持原来链表联通 ,并更新结点 
			p = q;	
		}else{
			pre = p;   //更新节点 
			p = q;
		}						
		count++;	
	}
	return l1;
}
//原来表尾插法,l2头插法 
LinkList discrete_one_two_2(LinkList l){//将a1,b1,a2,b2..拆分为a1-an,  bn-b1 
	LinkList l2 = (LinkList)malloc(sizeof(LNode));
	LNode* p = l->next,*r,*temp;
	r = l;
	l2->next = NULL;	
	while(p != NULL){	
		r->next = p;
		r = p;
		p = p->next;
		if(p != NULL){//第二个结点非空插入l2 
			LNode* q = p->next;//保留后继 
			p->next = l2->next;
			l2->next = p;
			p = q;
		}
//		printf("fsd");
	}
	r->next = NULL;//尾结点next置为空 
	return l2;	
}
void remove_repeat(LinkList l){//递增有序线性表去除相同元素 
	LNode* p = l->next,*q;
	while(p->next){//判定条件不能改为p,防止下一行出现指针异常 
		q = p->next;
		if(q->data == p->data){
			p->next = q->next;			
		}else{
			p = p->next;
		}
	}
}
//利用l1来当存储链表 
LinkList mergeLinkList(LinkList l1,LinkList l2){//l1,l2递增有序合并为递减有序 
    LNode* n1 = l1->next,*n2 = l2->next,*p;
	l1->next = NULL;
	while(n1 && n2){
		if(n1->data <= n2->data){
			p = n1->next;
			n1->next = l1->next;
			l1->next = n1;
			n1 = p;
		}else{
			p = n2->next;
			n2->next = l1->next;
			l1->next = n2;
			n2 = p;
		}
	}
	//通常只会有一个表非空,则判断只处理n2 
	if(n1){
		n2 = n1;
	}
	while(n2){
		p = n2->next;
		n2->next = l1->next;
		l1->next = n2;
		n2 = p;
	}
	return l1;
}
int Mergelistl1_l2(LinkList l1,LinkList l2,LinkList l3){//l1,l2是单调递减合并这俩链表为l3单调递增且没有重复结点 
	LNode* la = l1->next,*lb = l2->next,*lc;
	int count = 0;
	l3 = (LinkList)malloc(sizeof(struct LNode));
	l3->next = NULL;
	while(la && lb){
		count++;
		lc = (LNode*)malloc(sizeof(struct LNode));
		if(la->data > lb->data){		
			lc->data = la->data;
			la = la->next;
		}else if(la->data < lb->data){
			lc->data = lb->data;
			lb = lb->next;
		}else{
			lc->data = lb->data;
			lb = lb->next;
			la = la->next;
		}
		lc->next = l3->next;
		l3->next = lc;
	} 
	if(la)lb = la;
	while(lb){
		count++;
		lc = (LNode*)malloc(sizeof(struct LNode));
		lc->data = lb->data;
		lb = lb->next;
		lc->next = l3->next;
		l3->next = lc;
	}
	return count;
}
LinkList mergeA_B(LinkList l1,LinkList l2){//用l1,l2公共元素产生c链表 
	LinkList l = (LinkList)malloc(sizeof(LNode));
	LNode* r = l;
	r->next = NULL;
	while(l1->next && l2->next){
		if(l1->next->data == l2->next->data){
			LNode* n = (LNode*)malloc(sizeof(LNode));
			n->next = NULL;
			n->data = l1->next->data;
			r->next = n;
			r = n;
			l1 = l1->next;
			l2 = l2->next;
		}else if(l1->next->data < l2->next->data){//数值小的结点后移重新进行比较 
			l1 = l1->next;
		}else if(l1->next->data > l2->next->data){
			l2 = l2->next;
		}
	}
	return l;
}
void search_jiaoji(LinkList A,LinkList B){//A,B递增有序,求A,B交集 
	LNode* p = A->next,*q = B->next,*temp,*r;
	A->next = NULL; 
	r = A;
	while(p && q){
		if(p->data == q->data){
			temp = p->next;
			r->next = p;
			r = p;
			p->next = NULL;
			p = temp;
			q = q->next;
		}else if(p->data < q->data){
			p = p->next;
		}else if(p->data > q->data){
			q = q->next;
		}
	}
}
int Is_childList(LinkList l1,LinkList l2){//判断l2是否是l1子序列 
	 LNode* temp = l1->next,*p,*q;
	 p = l1->next;
	 q = l2->next;
	 while(p && q){
	 	if(p->data == q->data){
	 		p = p->next;
	 		q = q->next;
		 }else{
		 	q = l2->next;
		 	p = temp->next;//比较l1后一个结点 
		 	temp = p->next;
		 }
	 }
	 if(q == NULL)return 1;
	 else return 0;
}
int isSymmetry(DList* list){//带头结点的循环双链表是否对称 
	DNode* n1 = list->first->next,*n2 = list->last; //n1第一个有效结点,n2最后一个有效结点 
	while(n1 != n2 && n2->next != n1){//一定要是n2->next != n1,不能写反 
		if(n1->data == n2->data){
			n1 = n1->next;
			n2 = n2->prior;
		}else return 0;
	}
	return 1;
}
void merge_oneCycleList(List* list1,List* list2){//两循环单链表,将list2连接在list1后仍然循环 
	list1->last->next = list2->first->next;
	list2->last->next = list1->first;
}
void del_min_onecycleList(List* list){//反复找循环单链表最小结点并删除 
	SNode* pre = list->first,*min = pre->next,*p = pre;
	while(list->first->next != list->first){//表非空 
		while(p->next != list->first){//查遍一次循环 
			if(min->data > p->next->data){//寻找最小值 
				min = p->next;
				pre = p;
			}
			p = p->next;		
		}
		pre->next = min->next;
		printf("%d ",min->data);
		free(min);
		pre = list->first;//更新结点 
		min = pre->next;
		p = min;
	}
	free(list->first);
}
SNode* isCycleList(List* list){// 判断单链表是否有环 
	SNode* fast = list->first,*slow = list->first;
	while(fast != NULL && fast->next != NULL){
		slow = slow->next;				//慢结点一次一步 
		fast = fast->next->next;		//快结点一次两步 
		if(slow == fast)break;
	}
	if(fast == NULL || fast->next == NULL)return NULL; //表示没有循环 
		/*
		a为头结点到循环入口节点距离 
		r为环长 
		x为循环入口节点到相遇之间距离 
		n为相遇时快结点在循环中绕的圈数
		2(a+x) = a+n*r+x ==> a = n*r-x,当n == 1求循环入口 
	*/
	SNode* p1 = list->first,*p2 = slow;		//分别表示头结点  循环中相遇结点 
	while(p1 != p2){
		p1 = p1->next;
		p2 = p2->next;
	}
	return p1;  //循环入口 结点 
}
int Is_Symmestery(LinkList l,int n){//判断带头结点的链表是否中心对称 
	LNode* stack[100];
	l = l->next;
	int i = n/2,top = -1;
	while(i>0){
		stack[++top] = l;//前半段链表入队 
		l = l->next;
		i--;
	}
	if(n % 2)l = l->next;//l指向后半段链表 
	while(l){
		if(stack[top]->data == l->data){//一一出栈雨后把那段比较 
			top--;
			l = l->next;
		}else break; 
	}
	if(top != -1)return 0;//非空说明不对称 
	return 1;
}
int Is_qian_N_duichen(SLinklist head,int n){  //不带头结点链表判断前n个结点是否中心对称 
	SNode* l = head;
	int i = n/2;
	while(i>0){
		head = head->next;
		i--;
	}
	if(n%2==1)head = head->next;
	i = n/2;
	while(i>0){
		if(l == head){
			l = l->next;
			head = head->next;
		}else{
			return 1;//不对称 
		}
		i--;
	}
	return 0; 
}
int dc(LinkList  head,int n){//判断带头结点的链表前n个节点是否中心对称 
 	LinkList  p;
 	char s[10];
 	int i=1;
 	int j;
 	p=head->next;
 	for(i=1;i<=n/2;i++){
 		s[i]=p->data;//前n/2各数据存入数组中 
 		p=p->next;
 	}
 	j=i-1;
 	if(n%2==1){
 		p=p->next;//p指向后n/2开头 
 	}
 	for(i=j;i>0;i--){
 		if(p->data==s[i]){
 			p=p->next;
 		}else break;
 	}
 	if(i!=0){
		 return 0;
 	}else{
 		return 1;
 	}
 }
LNode* Fast_Find_Mid_Node(LinkList l){	//快速找到未知长度链表的中间节点 
      LNode* l1 = l;	//利用快慢结点,快结点一次两步,慢的一步,当快的到末尾慢的到中间 
	  while(l1->next != NULL){
	  	if(l1->next->next != NULL){
	  		l = l->next;
	  		l1 = l1->next->next;
		  }else{
		  	l1 = l1->next;
		  }
	  }
	  return l;
} 
LinkList ji_ou_List(LinkList l){//将奇数结点偶数结点排在一起,且偶数结点再奇数节点后 
	if(l == NULL || l->next == NULL || l->next->next == NULL){
		return l;
	} 
	LNode* front = l,*l1 = l->next,*l3 = l1;//front标记头结点,l3标记偶列表头结点 
	while(l1 && l1->next){
		l->next= l->next->next;
		l1->next = l1->next->next;
		l = l->next;
		l1 = l1->next;
	}
	l->next = l3;//偶链表连在奇链表后 
	return front;
} 
LinkList remove_end_n(LinkList l,int n){//删除链表倒数第n个结点 
	LNode* fast = l,*low = fast;
	int i = 0;
	while(i < n){
		fast = fast->next;
		if(fast == NULL)return l->next;//fast为最后一个结点删除头结点即可 
		i++;
	} 
	while(fast->next){
		low = low->next;
		fast = fast->next;
	}
	low->next = low->next->next;//low->next即为倒数第n个结点 
	return l;
} 
LinkList MergeTowList(LinkList l1,LinkList l2){//递归合并两个有序链表
	if(l1 == NULL)return l2;//将非空结点返回 
	if(l2 == NULL)return l1;
	if(l1->data <= l2->data){
		l1->next = MergeTowList(l1->next,l2);
	}else{
		l2->next = MergeTowList(l1,l2->next);
	}
	
}
void func(LinkList l,int n){//删除保存链表中第一次出现的结点删除其他绝对值与之相等的结点,数据大小小于n 
	LinkList r;
	int temp;
	int *p = (int *)malloc(sizeof(int) * (n+1));
	for(int i = 0; i < n+1; i++){
		*(p+i) = 0;//标记 
	}
	while(l->next != NULL){
		temp = l->next->data > 0 ? l->next->data : -l->next->data;
		if(*(p+temp) == 0){
			*(p+temp) = 1;
			l = l->next;
		}else{
			r = l->next;
			l->next = r->next;
			free(r);
		}
	}
	free(p);
}
void chang_list(LinkList l){//将s1,s2,s3.....sn,改为s1,sn,s2,sn-1...... ,将后半段结点逆置然后一次合并前半段和后半段 
	LNode* q,*p,*r,*s;//l为头结点 
	q = p = l;
	while(q->next != NULL)//当q指向尾时p指向中间结点 
	{
		p = p->next;
		q = q->next;
		if(q->next != NULL)q = q->next;
	}
	q = p->next;//p指向中间节点,q指向后半段首结点 
	p->next = NULL;//对后半段结点逆置 
	while(q != NULL){
		r = q->next;
		q->next = p->next;
		p->next = q;
		q = r;
	}
    s = l->next;//前半段第一个结点
	q = p->next;//后半段结点第一个结点 
	p->next = NULL;
	while(q != NULL){
		r = q->next;//保存后半段结点的后继 
		q->next = s->next;//后半段插入前半段 
		s->next = q;
		s = q->next;//指向前半段后继 
		q = r;//更新后半段结点 
	} 
}
void reverse(int R[],int from,int to){// 对调 
	int i,temp;
	for(i = 0; i < (to-from+1)/2; i++){
		temp = R[from+i];
		R[from+i] = R[to-i];
		R[to-i] = temp;
	}
}
void Converse(int R[],int n,int p){//将数组左移p个及将ab转换为ba 
	reverse(R,0,p-1);
	reverse(R,p,n-1);
	reverse(R,0,n-1);
}
void fun(LinkList l,LinkList l1,LinkList l2,LinkList l3){//将l中大写字母,数字,其他字符分别放在3链表 
 		LNode* p; 
 		l1 = (LinkList)malloc(sizeof(LinkList));
 		l2 = (LinkList)malloc(sizeof(LinkList));
 		l3 = (LinkList)malloc(sizeof(LinkList));
 		l = l->next;
 		while(l){
 			if(l->ch >= 'A' && l->ch <= 'Z'){
 				p->ch = l->ch;
 				l1->next = p;
 				l1 = p;
			 }else if(l->ch >= '0' && l->ch <= '9'){
			 	p->ch = l->ch;
			 	l2->next = p;
			 	l2 = p;
			 }else{
			 	p->ch = l->ch;
			 	l3->next = p;
				l3 = p;
			 }
		 }
		 l1->next = l2->next = l3->next = NULL;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值