双链表的排序

// 排序-插入-查找.cpp : 定义控制台应用程序的入口点。
//


#include "stdafx.h"

///关键代码开始




/*
*程序功能:对双向链表操作,主要包括:插入结点、删除结点、查找结点等基本操作
*需要注意的是,链表中附加了一个结点root_p
*root_p是链表的根节点,root_p中的data字段存储的是当前链表中的总结点个数
*root_p->prev指向链表中第一个存放数据的结点,root_p->next指向链表中最后一个存放数据的结点;
*当链表为空时,root_p->prev和root_p->next都为NULL
*/


#include<stdio.h>
#include<stdlib.h>


struct node
{
struct node *prev;   /*指向前一个结点的指针*/
int data;
struct node *next;   /*指向后一个结点的指针*/
};


void srand(unsigned int seed);
extern int printf(const char *format,...);


int dll_insert(struct node *root_p, int value);  /*插入结点,插入成功返回1,否则返回0*/
int dll_delete(struct node *root_p, int value);  /*删除结点,插入成功返回1,否则返回0*/
int dll_member(struct node *root_p, int value);  /*查找结点,如果存在返回1,否则返回0*/
void dll_print(struct node *root_p);  /*打印链表*/






int dll_insert(struct node *root_p, int value)
{
struct node *save_p, *curr_p;
struct node *new_p;


save_p = NULL;
curr_p = root_p->prev;
while (curr_p != NULL && curr_p->data < value)
curr_p = curr_p->next;// 从小到大排序插入


if (curr_p != NULL && curr_p->data == value)
return 0;// 相等则返回,即不允许重复
if ((new_p = (struct node *)malloc(sizeof(struct node))) == NULL)
return 0;
new_p->data = value;


if (curr_p != NULL) 
save_p = curr_p->prev;// 找到前驱
else if (root_p->data != 0) 
save_p = root_p->next;// 找到前驱 , 前驱为最后一个元素!!! 走到此说明插入到末尾. 


new_p->next = curr_p; // 新节点lianru
new_p->prev = save_p;


if (save_p == NULL) 
root_p->prev = new_p;
else save_p->next = new_p;
if (curr_p == NULL) root_p->next = new_p;
else curr_p->prev = new_p;


root_p->data++;
return 1;
}


int dll_delete(struct node *root_p, int value)
{
struct node *save_p, *curr_p, *next_p;


curr_p = root_p->prev;
while (curr_p != NULL && curr_p->data<value)
curr_p = curr_p->next;


if (curr_p != NULL && curr_p->data == value)
{
save_p = curr_p->prev;
next_p = curr_p->next;
if (save_p != NULL) save_p->next = next_p;
else root_p->prev = next_p;
if (next_p != NULL) next_p->prev = save_p;
else root_p->next = save_p;
root_p->data--;
return 1;
}
else return 0;  /* 空链表 或者 没有找到要删除的内容*/
}


int dll_member(struct node *root_p, int value)
{
struct node *curr_p = root_p->prev;


while (curr_p != NULL && curr_p->data<value)
curr_p = curr_p->next;


if (curr_p != NULL && curr_p->data == value) return 1;
else return 0;
}


void dll_print(struct node *root_p)
{
struct node *curr_p = root_p->prev;
printf("total number of nodes = %d .\n", root_p->data);
while (curr_p != NULL)
{
printf("%d  ", curr_p->data);
curr_p = curr_p->next;
}


printf("\n");
}


///关键代码结束
int _tmain(int argc, _TCHAR* argv[])


{
struct node *root_p;
int i;


/*root_p是链表的根节点,但是它并不存储链表的有效结点,
 root_p中的data存储的是当前链表中的总结点个数
 root_p->prev指向链表中第一个存放数据的结点,
 root_p->next指向链表中最后一个存放数据的结点
*/
root_p = (struct node *) malloc(sizeof(struct node));
root_p->prev = root_p->next = NULL;
root_p->data = 0;// 专门准备一个头节点


srand(5); //随机数
printf("insert...\n");
for (i = 0; i<3; i++) 
dll_insert(root_p, rand() % 100);
dll_print(root_p);


printf("\nmember...\n");
printf("10?exist : %d\n", dll_member(root_p, 10));
printf("65?exist : %d\n", dll_member(root_p, 65));
printf("75?exist : %d\n", dll_member(root_p, 75));
printf("9?exist : %d\n", dll_member(root_p, 9));
printf("70?exist : %d\n", dll_member(root_p, 70));
printf("100?exist : %d\n", dll_member(root_p, 100));


printf("\ndelete\n");
dll_delete(root_p, 10);
dll_delete(root_p, 65);
dll_delete(root_p, 75);
dll_delete(root_p, 9);
dll_delete(root_p, 70);
dll_delete(root_p, 100);
dll_print(root_p);


return 0;

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
当涉及到双向链表排序算法时,常见的方法有插入排序和归并排序。以下是使用C语言实现这两种算法的示例代码。 1. 插入排序(Insertion Sort): ```c #include <stdio.h> #include <stdlib.h> typedef struct Node { int data; struct Node* prev; struct Node* next; } Node; void insert(Node** head, int data) { Node* newNode = (Node*)malloc(sizeof(Node)); newNode->data = data; newNode->prev = NULL; newNode->next = NULL; if (*head == NULL) { *head = newNode; } else { Node* current = *head; while (current->next != NULL && current->next->data < data) { current = current->next; } if (current->next != NULL) { current->next->prev = newNode; } newNode->next = current->next; newNode->prev = current; current->next = newNode; } } void printList(Node* head) { Node* current = head; while (current != NULL) { printf("%d ", current->data); current = current->next; } printf("\n"); } void freeList(Node* head) { Node* current = head; while (current != NULL) { Node* temp = current->next; free(current); current = temp; } } int main() { Node* head = NULL; insert(&head, 5); insert(&head, 3); insert(&head, 8); insert(&head, 1); insert(&head, 6); printf("Before sorting: "); printList(head); // 插入排序 for (Node* i = head->next; i != NULL; i = i->next) { int key = i->data; Node* j = i->prev; while (j != NULL && j->data > key) { j->next->data = j->data; j = j->prev; } if (j == NULL) { head->data = key; } else { j->next->data = key; } } printf("After sorting: "); printList(head); freeList(head); return 0; } ``` 2. 归并排序(Merge Sort): ```c #include <stdio.h> #include <stdlib.h> typedef struct Node { int data; struct Node* prev; struct Node* next; } Node; Node* merge(Node* left, Node* right) { Node dummy; Node* tail = &dummy; while (left != NULL && right != NULL) { if (left->data <= right->data) { tail->next = left; left->prev = tail; left = left->next; } else { tail->next = right; right->prev = tail; right = right->next; } tail = tail->next; tail->prev = NULL; } if (left != NULL) { tail->next = left; left->prev = tail; } else { tail->next = right; right->prev = tail; } return dummy.next; } Node* mergeSort(Node* head) { if (head == NULL || head->next == NULL) { return head; } Node* slow = head; Node* fast = head->next; while (fast != NULL && fast->next != NULL) { slow = slow->next; fast = fast->next->next; } Node* right = slow->next; slow->next = NULL; Node* left = mergeSort(head); right = mergeSort(right); return merge(left, right); } void insert(Node** head, int data) { Node* newNode = (Node*)malloc(sizeof(Node)); newNode->data = data; newNode->prev = NULL; newNode->next = NULL; if (*head == NULL) { *head = newNode; } else { Node* current = *head; while (current->next != NULL) { current = current->next; } current->next = newNode; newNode->prev = current; } } void printList(Node* head) { Node* current = head; while (current != NULL) { printf("%d ", current->data); current = current->next; } printf("\n"); } void freeList(Node* head) { Node* current = head; while (current != NULL) { Node* temp = current->next; free(current); current = temp; } } int main() { Node* head = NULL; insert(&head, 5); insert(&head, 3); insert(&head, 8); insert(&head, 1); insert(&head, 6); printf("Before sorting: "); printList(head); // 归并排序 head = mergeSort(head); printf("After sorting: "); printList(head); freeList(head); return 0; } ``` 这两种算法都可以对双向链表进行排序,插入排序每次将一个元素插入到已排序的部分,而归并排序则将链表分割为较小的部分并进行合并。您可以根据需要选择适合您情况的算法。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值