C语言【微项目14】—带头结点单链表逆置问题[在原链表上逆转/置](采用指针数组-顺序化思想实现)【2021-12-26】

C语言【微项目14】—带头结点单链表逆置问题[在原链表上逆转/置](采用指针数组-顺序化思想实现)【2021-12-26】


【TDTX】
【C99】
【编译与运行环境】64位Windows操作系统,TDM-gcc 4.9.2 64bit编译。
【问题描述】有一个 带头结点的单链表,需要将它的 指向关系逆转(逆置)
【思路】 1. 本文解决思路比较独特!单链表由于“单”的特性,因此很难从后继位置获得其直接前驱的指针。
               2.同时,在学习数据结构时知道单链表插入方便、顺序化的数组查找方便。
               3.因而,把单链表顺序化使其兼具数组的特性,即可方便的获取链表任意结点的指针。
               4.顺序化方法很简单。 建立一个长度为链表有效数据结点个数的指针数组,数组的每个元素保存结点的地址即可!
               5.而单链表的 逆转(逆置)只需要通过该指针数组操作即可,可很方便容易的改变结点之间的指向关系!

一、ReverseSLinkList.c

#include <stdio.h>
#include <stdlib.h>
typedef struct ListNode
{
	int data;
	struct ListNode* next;
}ListNode;

int init_LinkList(ListNode** H)
{
	//产生一个头结点,数据域不放数据 
	(*H) = (ListNode*)malloc(sizeof(ListNode));
	if((*H) == NULL)
	{
		return 0;
	}
	(*H)->data = -1;
	(*H)->next = NULL;
	return 1;
}
int TailInsert_LinkList(ListNode* h)
{
	ListNode* p = h;
	ListNode* q = NULL;
	int t;
	while(1)
	{
		int n = 0;
		puts("输入结点值:(f结束)");
		n = scanf("%d",&t);
		if(n != 1)
		{
			break;
		}
		q = (ListNode*)malloc(sizeof(ListNode));
		if(q == NULL)
		{
			return 0;
		}
		q->data = t;
		q->next = p->next;
		p->next = q;	
		p = q;
	}
	return 1;
}
void traverse_LinkList(ListNode* h)
{
	ListNode* p = h->next;
	while(p != NULL)
	{
		printf("%d ",p->data);	
		p = p->next;
	}
}
void reverse_LinkList(ListNode* h)
{
	int num = 0;
	
	ListNode* p = h->next;
	while(p != NULL)
	{
		//printf("%d ",p->data);
		num++;	
		p = p->next;
	}
	//printf("num=%d\n",num);
	ListNode* a[num];//C99
	
	p = h->next;
	int k = 0;
	
	while(p != NULL)
	{
		a[k++] = p;
		p = p->next;
	}
	/****************关键代码*****************/
	for(int i = num - 1;i >= 0;i--)
	{
		if(i == 0)
		{
			a[i]->next = NULL;//原首元结点的next指向NULL
		}
		else
		{
			a[i]->next = a[i-1];//逆转操作
		}
	}
	h->next = a[num-1];//头结点的next指向完成逆转后的首元结点
	/****************关键代码*****************/
	return;
}
int main()
{
	ListNode* L;
	init_LinkList(&L);
	TailInsert_LinkList(L);
	traverse_LinkList(L);
	puts("\n开始逆转单链表!");
	reverse_LinkList(L);
	traverse_LinkList(L);

	return 0;
}

二、思路图示

在这里插入图片描述
在这里插入图片描述

三、 运行结果示例

在这里插入图片描述


------------------------------------------------------第十四次发项目类文章有点激动啊!-----------------------------------------------------
-----------------------------------------------------【C语言—微项目—自编练习】----------------------------------------------------------
----------------------------------------------------------------【TDTX】--------------------------------------------------------------------------

  • 5
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 7
    评论
下面是用C语言实现头结点单链表就地逆置的成员函数的代码: ```c #include <stdio.h> #include <stdlib.h> // 定义单链表的结点结构体 typedef struct ListNode { int data; struct ListNode* next; } ListNode; // 初始头结点单链表 ListNode* initList() { ListNode* head = (ListNode*)malloc(sizeof(ListNode)); head->next = NULL; return head; } // 尾插法建立单链表 void createList(ListNode* head) { int data; ListNode* tail = head; printf("请输入链表中的元素(以-1结束):"); while (1) { scanf("%d", &data); if (data == -1) { break; } ListNode* newNode = (ListNode*)malloc(sizeof(ListNode)); newNode->data = data; newNode->next = NULL; tail->next = newNode; tail = newNode; } } // 打印头结点单链表 void printList(ListNode* head) { ListNode* p = head->next; while (p != NULL) { printf("%d ", p->data); p = p->next; } printf("\n"); } // 就地逆置头结点单链表 void reverseList(ListNode* head) { ListNode* p = head->next; ListNode* q = p->next; p->next = NULL; // 将第一个结点的指针域赋值为NULL while (q != NULL) { ListNode* r = q->next; q->next = p; p = q; q = r; } head->next = p; // 将头结点的指针域指向链表的最后一个结点 } int main() { ListNode* head = initList(); createList(head); printf("链表:"); printList(head); reverseList(head); printf("逆置后的链表:"); printList(head); return 0; } ``` 运行结果: ``` 请输入链表中的元素(以-1结束):1 2 3 4 5 -1 链表:1 2 3 4 5 逆置后的链表:5 4 3 2 1 ```
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值