【Weiss】【第03章】练习3.3:通过交换指针交换单/双链表元素
【练习3.3】
通过之调整指针(而不是数据)来交换两个相邻的元素,使用
a.单链表
b.双链表
Answer:
先放测试代码,折叠标题可以看到分别是哪种链表的测试。
实测可满足题意,但单链表和双链表的两段代码是分开实现的,所以需要分开测试。
如果要合在一起的话,需要改一下头文件包含以及命名空间。
单链表测试代码:
#include <iostream>
#include "linklist.cpp"
using namespace std;
using namespace linklist;
template class List<int>;
int main(void)
{
List<int> number; //原始链表
cout << "/*additem()*/" << endl;
number.additem();
number.additem();
number.additem();
number.additem();
number.additem();
number.additem();
number.additem();
number.traverse();
cout << "\n/*end*/\n\n" << endl; //测试交换顺序,头节点与中间节点各一
cout << "/*swappos()*/" << endl;
number.swappos(number.find());
number.swappos(number.find());
number.traverse();
cout << "/*end*/\n\n" << endl; system("pause");
}
双链表测试代码:
#include <iostream>
#include "double_linklist.cpp"
using namespace std;
using namespace doublelinklist;
template class DList<int>;
int main(void)
{
DList<int> number; //测试插入
cout << "/*additem()*/" << endl;
number.additem();
number.additem();
number.additem();
number.additem();
number.additem();
number.additem();
number.additem();
number.traverse();
cout << "\n/*end*/\n\n" << flush; //测试交换函数
cout << "/*swappos*/" << endl;
//测试头节点
number.swappos(number.find());
number.traverse();
cout << endl;
//测试邻接尾节点的中间节点
number.swappos(number.find());
number.traverse();
cout << endl;
//测试中间节点
number.swappos(number.find());
number.traverse();
cout << endl;
//测试尾节点
number.swappos(number.find());
cout << "/*end*/\n\n" << flush; system("pause");
}
通过交换指针交换节点直观上还是比较容易的,但是需要比较细致否则容易做错。
因为注释不太好解释,所以代码上就不放注释了,直接上图比较直观。
首先以单链表为例,pos是头节点的情形可以当做一种特殊情况,处理方法比一般情况要简单。
更一般地,通过迭代找到pos的前驱,在后面的实现代码里记为iter变量,然后几个指针的变化关系如下图。
最后的问号代表该处可能是一个节点,也可能是nullptr,但是对于单链表而言没有影响。
考虑双链表时,同样不考虑pos是头指针的情况(当然在代码里还是要表现的),有三点细微的不一致
①、不需从链表头迭代寻找pos的前驱iter,在没有修改前向指针的情况下,可以把单链表书写中的iter全部写成pos->prev
②、按单链表的方法,修改完后向指针后,需要调整前向指针
③、尾部的问号节点如果为空,则会对rear的位置产生影响;如果不为空,则需调整该问号节点的前向指针
简图如下:
最后是实现代码,将其分别复制进此前对应的例程中,函数的声明请自行补充。
单链表实现代码:
//练习3.3新增,交换相邻节点
template <typename T> bool List<T>::swappos(Node<T>* pos)
{
if (pos->next == nullptr)
{
cout << ("Illegal!") << endl;
return false;
}
if (pos == front)
{
front = front->next;
pos->next = front->next;
front->next = pos;
}
else
{
Node<T>* iter = front;
while (iter->next != pos)
iter = iter->next;
if (iter == nullptr)
{
cout << ("Illegal!") << endl;
return false;
}
else
{
iter->next = pos->next;
pos->next = pos->next->next;
iter->next->next = pos;
}
}
return true;
}
双链表实现代码:
//练习3.3新增,通过交换指针交换节点
//不检测pos位置是否确实在双链表中(否则速度比单链表更慢,失去意义)
template <typename T> bool DList<T>::swappos(Node<T>* pos)
{
if (pos->next == nullptr)
{
cout << "Illegal" << endl;
return false;
}
if (pos == front)
{
front = front->next;
front->prev = nullptr;
pos->next = front->next;
pos->prev = front;
front->next = pos;
}
else
{
//后向指针调整
pos->prev->next = pos->next;
pos->next = pos->next->next;
pos->prev->next->next = pos;
//前向指针调整
pos->prev->next->prev = pos->prev;
pos->prev = pos->prev->next; }
//判断尾指针是否为空
if (pos->next == nullptr)
rear = pos;
else
pos->next->prev = pos;
return true;
}
【Weiss】【第03章】练习3.3:通过交换指针交换单/双链表元素的更多相关文章
- 【Weiss】【第03章】练习3.21:单数组模拟双栈
[练习3.21] 编写仅用一个数组而实现两个栈的例程.除非数组的每一个单元都被使用,否则栈例程不能有溢出声明. Answer: 很简单,一个栈从数组头起,一个栈从数组尾起,分别保留左右栈头索引. 如l ...
- 【Weiss】【第03章】练习3.4、3.5:有序链表求交、并
[练习3.4] 给定两个已排序的表L1和L2,只使用基本的表操作编写计算L1∩L2的过程. [练习3.5] 给定两个已排序的表L1和L2,只使用基本的表操作编写计算L1∪L2的过程. 思路比较简单,测 ...
- 第03章 AOP前奏
第03章 AOP前奏 提出问题 ●情景:数学计算器 ●要求 ①执行加减乘除运算 ②日志:在程序执行期间追踪正在发生的活动 ③验证:希望计算器只能处理正数的运算 ●常规实现 ●问题 ○代码混乱:越来越多 ...
- 第03章_基本的SELECT语句
第03章_基本的SELECT语句 1. SQL概述 1.1 SQL背景知识 1946 年,世界上第一台电脑诞生,如今,借由这台电脑发展起来的互联网已经自成江湖.在这几十年里,无数的技术.产业在这片江湖 ...
- suse 12 二进制部署 Kubernetets 1.19.7 - 第03章 - 部署flannel插件
文章目录 1.3.部署flannel网络 1.3.0.下载flannel二进制文件 1.3.1.创建flannel证书和私钥 1.3.2.生成flannel证书和私钥 1.3.3.将pod网段写入et ...
- 【Weiss】【第03章】增补附注
基本上每章到增补附注这里就算是结束了. 根据设想,每章的这一篇基本上会注明这一章哪些题没有做,原因是什么,如果以后打算做了也会在这里补充. 还有就是最后会把有此前诸多习题的代码和原数据结构放整理后,以 ...
- 【Weiss】【第03章】练习3.25:数组模拟队列
[练习3.25] 编写实现队列的例程,使用 a.链表 b.数组 Answer: 在这章一开头就已经写了个链表的队列例程了,所以实际上只要做b小题就可以. 数组模拟队列和链表的两点小不同是: ①.数组空 ...
- 【Weiss】【第03章】练习3.16:删除相同元素
[练习3.16] 假设我们有一个基于数组的表A[0,1...N-1],并且我们想删除所有相同的元素. LastPosition初始值为N-1,但应该随着相同元素被删除而变得越来越小. 考虑图3-61中 ...
- 【Weiss】【第03章】练习3.26:双端队列
[练习3.26] 双端队列(deque)是由一些项的表组成的数据结构,对该数据结构可以进行下列操作: Push(X,D):将项X插入到双端队列D的前端. Pop(D):从双端队列D中删除前端项并返回. ...
随机推荐
- RabbitMQ(1)——基础入门
本文章写在了CSDN :https://blog.csdn.net/qq_30348181/article/details/87911398
- jenkins发布项目到远程主机上,配置linux使用SSH免密码登录
一.首先要配置两台linux如何使用SSH免密码登录,这样脚本执行scp命令以及远程执行脚本都不需要输入密码: A为本地主机(即用于控制其他主机的机器,jenkins服务器) ; B为远程主机(即被控 ...
- Ionic3 Demo
本文为原创文章,转载请标明出处 最近又开源了一个小 Demo,基于 Ionic 3.9.2.注册登录功能使用的是 WildDog 野狗通信云,大家可以放心的注册登录玩.电影相关数据来源自"某 ...
- HexoC++第04课 构造析构.md
C++第04课 构造析构.mdhtml {overflow-x: initial !important;}#write, body { height: auto; } #write, #write h ...
- LeetCode 刷题记录(6-10题)
6 Z 字形变换(题目链接) class Solution: def convert(self, s, numRows): """ :type s: str :type ...
- 移动 H5 首屏秒开优化方案探讨
转载bang大神文章,原文<移动 H5 首屏秒开优化方案探讨>,此文仅仅用做自学与分享! 随着移动设备性能不断增强,web 页面的性能体验逐渐变得可以接受,又因为 web 开发模式的诸多好 ...
- Android 绘制中国地图
最近的版本有这样一个需求: 有 3 个要素: 中国地图 高亮省区 中心显示数字 面对这样一个需求,该如何实现呢? 高德地图 因为项目是基于高德地图来做的,所以很自然而然的想到了高德.但是当查阅高德地图 ...
- Snap们崛起告诉我们:这个世界太需要悄悄话
北京时间3月3日凌晨,"阅后即焚"应用Snapchat母公司Snap在纽约证券交易所上市.开盘价24美元,比其初定的17美元IPO价格高出近41.2%,按照24美元的股价计算, ...
- springmvc两种配置方法
基于配置文件xml方式, 配置springmvc步骤: 1.在pom文件中引入jar包: <!--导入springmvc的jar包--> <dependency> <gr ...
- 吐槽苹果开放接口のappleid登陆
这里吐槽一下苹果的开发文档,一切源于前段时间,公司的产品app(某知名资讯app)要接入苹果登陆(ios13发布以来,apple就流氓要求新上线的app,如果有第三方登陆的话,必须要接入appleid ...