此文为上一篇文章改为C++格式实现(多文件形式)

头文件

#pragma once
#include<iostream>
using namespace std;struct Node
{int iData;Node* pNext;
};class List
{private:Node* pHead;Node* pEnd; //pEnd指针是为了增加尾添加的效率,否则就要循环找尾int iCount = 0;
public:List();~List();
private:void FreeList();void FreeListNULL();
public:void AddToEnd(int iData);void AddToEndNopEnd(int iData);void Look();void AddToHead(int iData);Node* FindNodeByIndex(int iIndex);Node* FindNodeByData(int iData);void InsertNodeByIndex(int iIndex, int iData);void AddSomeNode(unsigned int iCount, unsigned int iData);void ChengeData(int iResData, int iDecData);void ChengeSomeData(int iResData, int iDecData);void ChengeSomeDataText(int iResData, int iDecData);void DeleteHead();void DeleteEnd();Node* DeleteOneDataByData(int iData);void DeleteAllDataByData(int iData);void DeleteDataByIndex(int iIndex);void SwapByData(int iData1, int iData2);void SwapByIndex(int iIndex1, int iIndex2);void SwapByChangePoint(int iIndex1, int iIndex2);void ReverseByData();void ReverseByPoint();int GetListNodeCount();
};

函数实现

#include"dl.h"List::List()
{pHead = NULL;pEnd = NULL;iCount = 0;
}
List::~List()
{FreeListNULL();
}void List::ReverseByPoint()
{Node* pHead = this->pHead;//参数合法性检测if (NULL == pHead || NULL == pHead->pNext){return;}int iCount = GetListNodeCount();int i = 0, j = iCount - 1;for (; i < j; i++, j--){SwapByChangePoint(i, j);}
}
void List::ReverseByData()
{//参数合法性检测if (NULL == pHead || NULL == pHead->pNext){return;}int iCount = GetListNodeCount();int i = 0, j = iCount - 1;for (; i < j; i++, j--){SwapByIndex(i, j);}
}
int List::GetListNodeCount()
{Node* pHead = this->pHead;int iCount = 0;while (NULL != pHead){iCount++;pHead = pHead->pNext;}return iCount;
}
void List::SwapByChangePoint(int iIndex1, int iIndex2)
{Node* pHead = this->pHead;//参数合法性检测if (NULL == pHead || NULL == pHead->pNext || iIndex1 == iIndex2 || iIndex1 < 0 || iIndex2 < 0){return;}//确定大小关系int iMin = iIndex1;int iMax = iIndex2;if (iIndex1 > iIndex2){iMin = iIndex2;iMax = iIndex1;}//根据下标找节点Node* pMin = FindNodeByIndex(iMin);Node* pMax = FindNodeByIndex(iMax);//找不到就结束if (NULL == pMin || NULL == pMax){cout<<"查无此节点\n";return;}//头尾交换if (pMin == pHead && pMax == pEnd){if (pHead->pNext == pEnd)  //两个节点{pEnd->pNext = pHead;pHead->pNext = NULL;//交换指向pHead = pEnd;pEnd = pHead->pNext;}else //多个节点{//找到尾巴的前一个节点Node* pMaxPre = FindNodeByIndex(iMax - 1);//尾巴变头pEnd->pNext = pHead->pNext;//头变尾巴pMaxPre->pNext = pHead;//头下一个为NULLpHead->pNext = NULL;//交换指向pHead = pEnd;pEnd = pMaxPre->pNext;}}//头和中间交换else if (pMin == pHead && pMax != pEnd){//相邻if (pMin->pNext == pMax){pMin->pNext = pMax->pNext;pMax->pNext = pMin;pHead = pMax;}//不相邻else{//找pMax的前一个指针Node* pMaxPre = FindNodeByIndex(iMax - 1);//记录头的下一个节点 即链表第二个节点Node* pHeadNext = pMin->pNext;//头节点连在max的位置上pMin->pNext = pMax->pNext;pMaxPre->pNext = pMin;//pMax挪到头pMax->pNext = pHeadNext;//改变新的头pHead = pMax;}}//尾和中间交换else if (pMin != pHead && pMax == pEnd){if (pMin->pNext == pMax)  //相邻{//找到pMin的前一个Node* pMinPre = FindNodeByIndex(iMin - 1);//先把尾巴放中间pMinPre->pNext = pMax;pMax->pNext = pMin;//pMin next = NULLpMin->pNext = NULL;pEnd = pMin;}//不相邻else{//找到pMin的前一个Node* pMinPre = FindNodeByIndex(iMin - 1);//找pMax的前一个指针Node* pMaxPre = FindNodeByIndex(iMax - 1);//pmax放中间去pMinPre->pNext = pMax;pMax->pNext = pMin->pNext;//pMin放尾巴上去pMaxPre->pNext = pMin;pMin->pNext = NULL;pEnd = pMin;}}//中间两个相互交换else if (pMin != pHead && pMax != pEnd){//相邻if (pMin->pNext == pMax){//找到pMin的前一个节点Node* pMinPre = FindNodeByIndex(iMin - 1);Node* pMaxNext = pMax->pNext;//将pMax装在pMin 与pMinPre中间pMinPre->pNext = pMax;pMax->pNext = pMin;//把pMax拿下来pMin->pNext = pMaxNext;}//不相邻else{//找到pMin的前一个Node* pMinPre = FindNodeByIndex(iMin - 1);Node* pMinNext = pMin->pNext;//找pMax的前一个指针Node* pMaxPre = FindNodeByIndex(iMax - 1);Node* pMaxNext = pMax->pNext;//将pMin撞到pMax的位置pMaxPre->pNext = pMin;pMin->pNext = pMaxNext;//将pMax撞到pMin的位置pMinPre->pNext = pMax;pMax->pNext = pMinNext;}}
}
void List::SwapByIndex(int iIndex1, int iIndex2)
{if (NULL == pHead)return;//查找Node* pT1 = FindNodeByIndex(iIndex1);Node* pT2 = FindNodeByIndex(iIndex2);//都找到才能交换if (pT1 != NULL && pT2 != NULL){//交换成员//int temp = pT1->iData;//pT1->iData = pT2->iData;//pT2->iData = temp;Node p = *pT1;memcpy(pT1, pT2, 4);memcpy(pT2, &p, 4);}
}
void List::SwapByData(int iData1, int iData2)
{if (NULL == pHead)return;//查找Node* pT1 = FindNodeByData(iData1);Node* pT2 = FindNodeByData(iData2);//都找到才能交换if (pT1 != NULL && pT2 != NULL){//交换成员//Node p = *pT1;//*pT1 = *pT2;//*pT2 = p;//int temp = pT1->iData;//pT1->iData = pT2->iData;//pT2->iData = temp;Node p = *pT1;memcpy(pT1, pT2, 4);memcpy(pT2, &p, 4);}
}
void List::DeleteDataByIndex(int iIndex)
{Node* pHead = this->pHead;if (NULL == pHead)return;if (0 == iIndex)DeleteHead();else{//找前一个节点Node* pTemp = FindNodeByIndex(iIndex - 1);if (pTemp != NULL){if (pTemp->pNext == pEnd)DeleteEnd();//记录被删除的节点Node* pT = pTemp->pNext;//链接pTemp->pNext = pT->pNext;//释放delete pT;}else{cout << "查无此节点\n";}}
}
void List::DeleteAllDataByData(int iData)
{Node* pHead = this->pHead;if (NULL == pHead)return;Node* pTemp = DeleteOneDataByData(iData);while (pTemp != NULL){pTemp = DeleteOneDataByData(iData);}
}
Node* List::DeleteOneDataByData(int iData)
{Node* pHead = this->pHead;if (NULL == pHead)return NULL;if (pHead->iData == iData){DeleteHead();return pHead;}else if (pEnd->iData == iData){DeleteEnd();return pHead;}else{//循环找节点Node* pTemp = pHead;while (pTemp->pNext != NULL){if (pTemp->pNext->iData == iData)break;pTemp = pTemp->pNext;}//判断if (pTemp->pNext != NULL){Node* pT = pTemp->pNext; //记录pTemp->pNext = pT->pNext;delete  pT;return pHead;   //return pTemp->pNext  ----- pHead}else{cout << "查无此节点\n";return NULL;}}
}
void List::DeleteEnd()
{Node* pHead = this->pHead;//参数合法性检测if (NULL == pHead)return;if (pHead == pEnd || pHead->pNext == NULL)//只有一个节点{delete pHead;pHead = NULL;pEnd = NULL;}else{//找到结尾的前一个Node* pT = pHead;while (pT->pNext != pEnd){pT = pT->pNext;}delete pEnd;pEnd = pT;pEnd->pNext = NULL;}
}
void List::DeleteHead()
{Node* pHead = this->pHead;//参数合法性检测if (NULL == pHead)return;if (pHead == pEnd || pHead->pNext == NULL)//只有一个节点{delete pHead;pHead = NULL;pEnd = NULL;}else{Node* pT = pHead;pHead = pHead->pNext;delete pT;}
}
void List::ChengeSomeData(int iResData, int iDecData)
{Node* pHead = this->pHead;//参数合法性检测if (NULL == pHead){cout << "查无此节点\n";return;}while (pHead != NULL){if (pHead->iData == iResData)pHead->iData = iDecData;pHead = pHead->pNext;}
}
void List::ChengeSomeDataText(int iResData, int iDecData)
{//参数合法性检测if (NULL == pHead){cout << "查无此节点\n";return;}while (FindNodeByData(iResData) != NULL){ChengeData(iResData, iDecData);}
}
void List::ChengeData(int iResData, int iDecData)
{Node* pRec = FindNodeByData(iResData);if (NULL == pRec){cout << "查无此节点\n";}else{pRec->iData = iDecData;}
}
void List::AddSomeNode(unsigned int iCount, unsigned int iData)
{for (unsigned int i = 0; i < iCount; i++){AddToEnd(iData);}
}
void List::InsertNodeByIndex(int iIndex, int iData)
{//参数合法性检测if (iIndex < 0){cout << "下标输入有误,请重新输入\n";return;}//下标为0,直接头添加if (0 == iIndex){AddToHead(iData);}else{//找位置Node* pTemp = FindNodeByIndex(iIndex - 1);if (pTemp != NULL){//申请节点空间Node* pT = new(Node);if (pT != NULL){//节点成员赋值pT->iData = iData;pT->pNext = NULL;//链接 先连后断pT->pNext = pTemp->pNext;pTemp->pNext = pT;}}else{cout << "查无此节点";}}
}
Node* List::FindNodeByData(int iData)
{Node* pHead = this->pHead;//参数合法性检测if (NULL == pHead || iData < 0){cout << "链表为空/位置输入有误,无法查节点\n";return NULL;}//循环链表while (pHead != NULL){if (pHead->iData == iData)return pHead;pHead = pHead->pNext;}return NULL;
}
Node* List::FindNodeByIndex(int iIndex)
{Node* pHead = this->pHead;//参数合法性检测if (NULL == pHead || iIndex < 0){cout << "链表为空/位置输入有误,无法查节点\n";return NULL;}//循环链表int i = 0;while (pHead != NULL){if (i == iIndex)return pHead;i++;pHead = pHead->pNext;}cout << "位置输入过大,无法查节点\n";return NULL;
}
void List::AddToHead(int iData)
{//创建节点Node* pTemp = new(Node);if (NULL != pTemp){//节点成员赋值pTemp->iData = iData;pTemp->pNext = NULL;//连接链表if (NULL == pHead)//空链表{//*pHead = pTemp;pEnd = pTemp;}else{pTemp->pNext = pHead;//*pHead = pTemp;}pHead = pTemp;}
}
void List::Look()
{Node* pHead = this->pHead;while (pHead != NULL){cout << " " << (pHead->iData);pHead = pHead->pNext;}cout << endl;
}
void List::FreeList()
{Node* pTemp = pHead;while (pTemp != NULL){Node* pt = pTemp;pTemp = pTemp->pNext;delete pt;}pHead = NULL;pEnd = NULL;
}
void List::FreeListNULL()
{Node* pTemp = pHead;while (pTemp != NULL){Node* pt = pTemp;pTemp = pTemp->pNext;delete pt;}pHead = NULL;pEnd = NULL;
}
void List::AddToEndNopEnd(int iData)
{//创建节点Node* pTemp = new(Node);if (NULL != pTemp){//节点成员赋值pTemp->iData = iData;pTemp->pNext = NULL;//链接if (NULL == pHead){pHead = pTemp;}else{Node* pt = pHead;while (pt->pNext != NULL)      //找尾巴{pt = pt->pNext;}pt->pNext = pTemp;}}
}
void List::AddToEnd(int iData)
{//创建节点Node* pTemp = new(Node);if (NULL != pTemp){//节点成员赋值pTemp->iData = iData;pTemp->pNext = NULL;//连接链表if (NULL == pHead)//空链表{pHead = pTemp;//*pEnd = pTemp;}else{pEnd->pNext = pTemp;//*pEnd = pTemp;}pEnd = pTemp;}}

主函数

#include<iostream>
#include"dl.h"
using namespace std;int main()
{List ls;ls.AddToEnd(1);ls.AddToEnd(2);ls.AddToEndNopEnd(5);ls.AddToHead(3);//ls.FindNodeByIndex(2);//ls.FindNodeByData(2);ls.InsertNodeByIndex(2,3);ls.Look();return 0;
}

perfect~

【数据结构基础_有[*pHead]和[*pEnd]的单向链表_(C++实现)】相关推荐

  1. 链表有环是什么意思_互联网大厂offer收割之单向链表的概念及面试题大全

    链表是最基本的数据结构,面试官也常常用链表来考察面试者的基本能力,而且链表相关的操作相对而言比较简单,也适合考察写代码的能力.链表的操作也离不开指针,指针又很容易导致出错.综合多方面的原因,链表题目在 ...

  2. c语言文件读写_学生信息管理系统(C语言\单向链表\文件读写)

    最近在复习数据结构,早上刚复习完链表,就想到了学生信息管理系统这个经典的大作业,然后呢,花了一早上加一中午的功夫给重新实现了一遍,里面可能会有写的不好的地方,但也代表了我实现的一些想法,在这里我将分享 ...

  3. java简单单向链表_【新手自白书】简单单项链表的实现(JAVA)

    复习一下简单单项链表的实现. 在动手写链表之前,需要思考链表是如何组成的,一般来说,一个简单的单项链表主要是由节点构成,由于链表的特性,头节点是一个十分重要的成员,所以,链表必须的成员是节点Node, ...

  4. java简单单向链表_用java简单的实现单链表的基本操作

    packagecom.tyxh.link;//节点类 public classNode {protected Node next; //指针域 protected int data;//数据域 pub ...

  5. java 链表逆序代码_如何实现一个高效的单向链表逆序输出?(详解)

    需要考虑因素,高效应权衡多方面因素 数据量是否会很大 空间是否有限制 原始链表的结构是否可以更改 时间复杂度是否有限制 一个链表节点需要输出的元素有多个,例如链表中存的是自定义对象,有多个字段 题目. ...

  6. Algorithms_基础数据结构(04)_线性表之链表_单向循环链表约瑟夫环问题

    文章目录 大纲图 链表的经典面试题目 如何设计一个LRU缓存淘汰算法 约瑟夫问题 结构 分析 大纲图 链表的经典面试题目 如何设计一个LRU缓存淘汰算法 tip:单向链表 约瑟夫问题 N个人围成一圈, ...

  7. Algorithms_基础数据结构(03)_线性表之链表_双向链表

    文章目录 大纲图 双向链表 双向链表的基本结构 双向链表的基本操作 头插 尾插 中间部位插入 删除头部 删除尾部 删除中间位置的数据 查找 更新 Code 总结 大纲图 双向链表 Algorithms ...

  8. asp子窗口读取父窗口数据_算法与数据结构基础 - 数组(Array)

    数组基础 数组是最基础的数据结构,特点是O(1)时间读取任意下标元素,经常应用于排序(Sort).双指针(Two Pointers).二分查找(Binary Search).动态规划(DP)等算法.顺 ...

  9. 在列表前方插入一个数据_通俗易懂的Redis数据结构基础教程

    Redis有5个基本数据结构,string.list.hash.set和zset.它们是日常开发中使用频率非常高应用最为广泛的数据结构,把这5个数据结构都吃透了,你就掌握了Redis应用知识的一半了. ...

  10. 有十五个数按由大到小顺序存放在一个数组中_数据结构基础 (代码效率优化, 线性表, 栈, 队列, 数组,字符串,树和二叉树,哈希表)...

    作者:张人大 代码效率优化 复杂度 -- 一个关于输入数据量n的函数 时间复杂度 -- 昂贵 与代码的结构设计有着紧密关系 一个顺序结构的代码,时间复杂度是O(1), 即任务与算例个数 n 无关 空间 ...

最新文章

  1. Ubuntu 使用记录
  2. HNUSTOJ 1601:名字缩写
  3. 如何复制带格式的Notepad++文本?
  4. 华为荣耀20和x10比较_荣耀x10和荣耀20Pro哪个值得入手 荣耀x10和荣耀20Pro参数对比...
  5. 2017第35周日乱记
  6. inputn函数与input函数的区别
  7. NodeJS在CentOs7下安装
  8. 如何在Flutter上实现高性能的动态模板渲染
  9. MTK 驱动开发(29)---TP 驱动移植
  10. 《极客与团队》一说到底真正重要的还是代码本身
  11. markdown使用模板(供自己方便使用)
  12. 电脑版我的世界java_我的世界pc JAVA版
  13. 计算机未来发展展望3000字,关于我的计算机职业生涯规划3000字
  14. api文档 luci_Luci介绍
  15. Treeview 无限分类非递归终极解决方案VB
  16. 数组转这种格式 county_list:{ 110101: “东城区“, 110102: “西城区“, 110105: “朝阳区“, 110106: “丰台区“,
  17. 全家都是博士是一种什么样的体验?
  18. Win7安全模式启动卡在Classpnp.sys
  19. matlab解决最短路径问题
  20. shell学习之引号

热门文章

  1. NetCore游戏服务器GeekServer
  2. python中不同文件之间使用所谓的全局变量
  3. uni-app入门教程
  4. windows下choco 安装helm
  5. 简单使用pdf插件pdf.js
  6. vue中使用rrweb实现页面回放功能
  7. Mysql事务隔离级别和锁机制(间隙锁、临建锁)
  8. Innodb中的事务隔离级别和锁的关系
  9. 为什么中国的游戏没有做出像欧美那种自由度很高的RPG游戏?
  10. 专家不靠谱,秘笈才重要