链表翻转 递归与非递归写法

标签: 数据结构  数据结构  链表  指针  单链表

链表翻转 递归与非递归写法

链表类实现:

class node
{
public:
	node();
	int data;
	node* next;
	
	void insert(int dt);
	void display();	
};

node::node()
{
	this->next = NULL;
}

void node::insert(int dt)
{
	node* nd = new node();
	nd->data = dt;
	
	node* p = this;
	while(p->next)
	{
		p = p->next;
	}
	
	p->next = nd;
}

void node::display()
{
	node* p = this->next;
	
	while(p)
	{
		cout<<p->data<<" ";
		p = p->next;
	}
	cout<<endl;
}

递归翻转:

  • 要翻转第 i 个节点, 先翻转 i 之后的所有节点
  • 然后将 第 i+1 个节点的 后继指针next 指向 第 i个节点
  • 将 第 i 个节点的后继指针next 置空
    在这里插入图片描述
/*
链表翻转递归写法 
param p : 要翻转的链表的第一个元素的指针 
return  : 新表的第一个元素的指针 
*/
node* flip(node* p)
{
	// 如果p不是原表尾节点 
	if(p->next)
	{
		node* new_head = flip(p->next);	// 翻转p的所有后继节点,获得新表的第一个元素 
		p->next->next = p;				// p的后继的后继指向p 
		p->next = NULL;					// p的后继置空 
		
		return new_head;				// 返回新表第一个元素 
	}
	// 如果p是原表尾节点,返回 
	else
	{
		return p;
	}
}

非递归翻转

p1, p2做迭代指针

  • 记录p2的后继节点,用temp保存
  • p2的后继指针指向p1
  • p1 = p2, p2 = temp,后向迭代

在这里插入图片描述

/*
链表翻转迭代写法 
param p : 要翻转的链表的第一个元素的指针 
return  : 新表的第一个元素的指针 
*/
node* flip_(node* t)
{
	node* p1 = t;
	node* p2 = t->next;
	p1->next = NULL;	// 尾节点是p1, p1->next置空 
	
	while(p2)
	{
		
		node* temp = p2->next;	// 保存p2的下一个节点 
		p2->next = p1;			// 修改p2的next,指向P1 
		
		p1 = p2;				// p1, p2向后迭代 
		p2 = temp;
	}
	
	return p1;
}

主函数

int main()
{
	int n, i, x;
	cin>>n;
	
	node* t;
	
	for(i=0; i<n; i++)
	{
		cin>>x;
		t->insert(x);
	} 
	
	t->next = flip_(t->next);
	t->display();
	
	t->next = flip(t->next);
	t->display();
	
	return 0;
}

运行结果

在这里插入图片描述

完整代码

#include <iostream>

using namespace std;

class node
{
public:
	node();
	int data;
	node* next;
	
	void insert(int dt);
	void display();	
};

node::node()
{
	this->next = NULL;
}

void node::insert(int dt)
{
	node* nd = new node();
	nd->data = dt;
	
	node* p = this;
	while(p->next)
	{
		p = p->next;
	}
	
	p->next = nd;
}

void node::display()
{
	node* p = this->next;
	
	while(p)
	{
		cout<<p->data<<" ";
		p = p->next;
	}
	cout<<endl;
}

/*
链表翻转递归写法 
param p : 要翻转的链表的第一个元素的指针 
return  : 新表的第一个元素的指针 
*/
node* flip(node* p)
{
	// 如果p不是原表尾节点 
	if(p->next)
	{
		node* new_head = flip(p->next);	// 翻转p的所有后继节点,获得新表的第一个元素 
		p->next->next = p;				// p的后继的后继指向p 
		p->next = NULL;					// p的后继置空 
		
		return new_head;				// 返回新表第一个元素 
	}
	// 如果p是原表尾节点,返回 
	else
	{
		return p;
	}
}

/*
链表翻转迭代写法 
param p : 要翻转的链表的第一个元素的指针 
return  : 新表的第一个元素的指针 
*/
node* flip_(node* t)
{
	node* p1 = t;
	node* p2 = t->next;
	p1->next = NULL;	// 尾节点是p1, p1->next置空 
	
	while(p2)
	{
		
		node* temp = p2->next;	// 保存p2的下一个节点 
		p2->next = p1;			// 修改p2的next,指向P1 
		
		p1 = p2;				// p1, p2向后迭代 
		p2 = temp;
	}
	
	return p1;
}

int main()
{
	int n, i, x;
	cin>>n;
	
	node* t;
	
	for(i=0; i<n; i++)
	{
		cin>>x;
		t->insert(x);
	} 
	
	t->next = flip_(t->next);
	t->display();
	
	t->next = flip(t->next);
	t->display();
	
	return 0;
}
版权声明:本文为weixin_44176696原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/weixin_44176696/article/details/103957695