当前位置:   article > 正文

双向链表C++,C#,Java版,这些程序大多已经过测试,一直在用。

双向链表C++,C#,Java版,这些程序大多已经过测试,一直在用。

先C++版吧,我最先用的是C#,后来是Java,后来改用C++版的,因为现在一直在用C++,单链

表一直没写上去,因为我很少用,用的是双链表。

执行代码例子1:

int main()
{
     
    _DList<_string>  sl = { "123","a1","b4","1998","wc" };

    _pcn(sl);

    sl.Sort_Selection();

    _pcn(sl);

}

输出:

执行代码例子2:


void test()
{
    _DList<_string>  sl = { "123","a1","b4","1998","wc" };

    std::cout << "使用内存:" << _Memory::mem_used() << "\n";

    sl.Sort_Selection();

    std::cout << "使用内存:" << _Memory::mem_used() << "\n";
}

int main()
{
    std::cout << "使用内存:" << _Memory::mem_used() << "\n";
     

    test();

    std::cout << "使用内存:" << _Memory::mem_used() << "\n";
}

1. C++版

_List.h

  1. /*******************************************************************************************
  2. 文件名 : list.h
  3. 作者 : 李锋
  4. 功能 : 链表
  5. 创建时间 : 2016年07月31日
  6. 最后一次修改时间 : 2021年10月23日
  7. /// 链表是一种用来存储数据集合的数据结构。链表具有如下属性
  8. ///(1)元素通过指针依次相连
  9. ///(2)最后一个元素的指针为空(null)。
  10. ///(3)在程序的执行过程中,链表的长度可以自由伸缩。
  11. ///(4)链表的长度可以要求的任意长度(除非系统内存耗尽)。
  12. ///(5)它不会浪费内存空间(但会需要额外的内存空间存储指针)。
  13. 记住: Virtual C++ Bug: 模板继承用到父类成员访问时,要用 this->
  14. ********************************************************************************************/
  15. #ifndef __LIST_H_
  16. #define __LIST_H_
  17. #include "_Macro.h"
  18. #include "_Memory.h"
  19. #include "_ByteArray.h"
  20. #include "_Pair.h"
  21. _LF_BEGIN_
  22. /// <summary>
  23. /// 排序顺序
  24. /// </summary>
  25. enum class _SortOrder
  26. {
  27. s_Minmax = 0, //从小到大
  28. s_Maxmin = 1, //从大到小
  29. s_null = 2 //无排序顺序
  30. };
  31. /// <summary>
  32. /// 单链表节点
  33. /// </summary>
  34. /// <typeparam name="T"></typeparam>
  35. /// 创建时间 2021年10月23日 最后一次修改时间 : 2021年10月23日
  36. template<class T>
  37. class _SListNode
  38. {
  39. public:
  40. /// <summary>
  41. /// 节点数据
  42. /// </summary>
  43. T Data;
  44. /// <summary>
  45. /// 下一个节点
  46. /// </summary>
  47. _SListNode<T>* Next;
  48. /// <summary>
  49. /// 构造函数
  50. /// </summary>
  51. /// <param name="aData"></param>
  52. _SListNode(T aData)
  53. {
  54. Data = aData;
  55. }
  56. };
  57. /// <summary>
  58. /// C#语句:public class _DListNode<T>
  59. /// </summary>
  60. /// <typeparam name="T">默认数据</typeparam>
  61. template<class T>
  62. class _DListNode
  63. {
  64. public:
  65. /// <summary>
  66. /// 节点数据
  67. /// </summary>
  68. T Data;
  69. /// <summary>
  70. /// 前一个节点
  71. /// </summary>
  72. _DListNode<T>* Prev;
  73. /// <summary>
  74. /// 下一个节点
  75. /// </summary>
  76. _DListNode<T>* Next;
  77. /// <summary>
  78. /// 构造函数
  79. /// </summary>
  80. /// <param name="aData">默认数据</param>
  81. _DListNode(const T& aData)
  82. {
  83. Data = aData;
  84. Prev = null;
  85. Next = null;
  86. }
  87. _DListNode()
  88. {
  89. Prev = null;
  90. Next = null;
  91. Data = T();
  92. }
  93. };
  94. /// <summary>
  95. /// 单链表:
  96. /// 通常我们说的链表指的是单链表(singly linked list)。单链表包括一组结点,每个结
  97. /// 点有一个 next 指针域,用来存储指向(逻辑上)下一个元素对应结点的指针。最后一个结点的
  98. /// next指针域的值为null,这预示着已经到达链表的尾部。
  99. ///
  100. /// </summary>
  101. /// <typeparam name="T"></typeparam>
  102. template<class T>
  103. class _SList : public _Object
  104. {
  105. private:
  106. /// <summary>
  107. /// 第一个结点
  108. /// </summary>
  109. _SListNode<T>* _First;
  110. /// <summary>
  111. /// 结点数
  112. /// </summary>
  113. int _Count;
  114. public:
  115. inline const int& Count() { return _Count; }
  116. inline const _SListNode<T>* First() { return _First; }
  117. };
  118. //------------------------------------------LDIterator
  119. //参考网址: https://blog.csdn.net/qq_28398301/article/details/106321525 C++用for遍历自定义类
  120. /// <summary>
  121. ///
  122. /// </summary>
  123. /// <typeparam name="T"></typeparam>
  124. template<class T>
  125. class _DListNodeIterator
  126. {
  127. private:
  128. _DListNode<T>* _pNode;
  129. public:
  130. /// <summary>
  131. /// 构造函数,传值迭代器管理的值
  132. /// </summary>
  133. /// <param name="pNode"></param>
  134. inline _DListNodeIterator(_DListNode<T>* pNode) { _pNode = pNode; }
  135. /// <summary>
  136. /// 比较实现
  137. /// </summary>
  138. /// <param name="that"></param>
  139. /// <returns></returns>
  140. bool operator != (const _DListNodeIterator& that) { return _pNode != that._pNode; }
  141. /// <summary>
  142. /// 自增实现
  143. /// </summary>
  144. /// <returns></returns>
  145. inline _DListNodeIterator& operator ++ () { _pNode = _pNode->Next; return *this; }
  146. /// <summary>
  147. /// 解引用,取值
  148. /// </summary>
  149. /// <typeparam name="T"></typeparam>
  150. T& operator * () { return _pNode->Data; }
  151. //LDIterator(const LDIterator&) = delete;
  152. //LDIterator& operator=(const LDIterator&) = delete;
  153. //~LDIterator() = default;
  154. };
  155. /// <summary>
  156. /// 双向链表, 数据 T 要求能够比较大小,否则编译会出错。
  157. /// </summary>
  158. /// <typeparam name="T"></typeparam>
  159. template<class T>
  160. class _DList : public _Object
  161. {
  162. protected:
  163. _DListNode<T>* _First; //第一个节点
  164. _DListNode<T>* _Last; //最后一个节点
  165. int _Count; //节点个数
  166. int _MaxBuffer; //双链表最大可以存储的元素个数
  167. _SortOrder _so; //排序顺序
  168. protected:
  169. /// <summary>
  170. /// 初台化数据
  171. /// </summary>
  172. /// <returns></returns>
  173. inline void InitData()
  174. {
  175. _Count = 0; _First = null; _Last = null; _MaxBuffer = 100000;
  176. _so = _SortOrder::s_null;
  177. }
  178. public: //---------------------------------------------------------------------------属性
  179. __declspec(property(get = GetSortOrder, put = SetSortOrder) ) _SortOrder SortOrder;
  180. const _SortOrder& GetSortOrder() const { return _so; }
  181. virtual void SetSortOrder(const _SortOrder so) { _so = so; }
  182. __declspec(property(get = GetCount)) const int Count;
  183. inline int GetCount() const { return _Count; }
  184. public:
  185. //------------------------------------------------------------构造与析构
  186. /// <summary>
  187. /// 默认构造函数
  188. /// </summary>
  189. /// <returns></returns>
  190. inline _DList()
  191. {
  192. InitData();
  193. }
  194. inline _DList(const _DList& dl)
  195. {
  196. //_cout << _t("inline _DList<T>::_DList(const _DList& dl)\n");
  197. InitData();
  198. _DListNode<T>* dn = dl.First();
  199. while (dn != null)
  200. {
  201. Add(dn->Data);
  202. dn = dn->Next;
  203. }
  204. }
  205. inline _DList(const T& item)
  206. {
  207. InitData();
  208. Add(item);
  209. }
  210. /// <summary>
  211. /// 列表初始化 dList<int> idl = {1,2,3,4};
  212. /// </summary>
  213. /// <typeparam name="T"></typeparam>
  214. /// <param name="tList"></param>
  215. inline _DList(std::initializer_list<T> tList)
  216. {
  217. InitData();
  218. for (T t : tList) { Add(t); }
  219. }
  220. /// <summary>
  221. /// 析构函数
  222. /// </summary>
  223. inline virtual ~_DList()
  224. {
  225. //_cout << _t("inline _DList<T>::~_DList()\n");
  226. ClearData();
  227. }
  228. //------------------------------------------------------------属性
  229. /// <summary>
  230. /// 双链表最大可以存储的元素个数
  231. /// </summary>
  232. int MaxBuffer()const { return _MaxBuffer; }
  233. /// <summary>
  234. ///设定双链表最大可以存储的元素个数
  235. /// </summary>
  236. /// <param name="nCaptionty"></param>
  237. inline void MaxBuffer(int nCaptionty) { _MaxBuffer = nCaptionty; }
  238. inline int CSharp_Count() const { return _Count; }
  239. inline _DListNode<T>* First()const { return _First; }
  240. inline _DListNode<T>* Last()const { return _Last; }
  241. inline _DListNodeIterator<T> begin()const { return _DListNodeIterator<T>(_First); }
  242. /// <summary>
  243. ///
  244. /// </summary>
  245. /// <returns></returns>
  246. inline _DListNodeIterator<T> end()const
  247. {
  248. //迭代器使用的语句
  249. //for (_DListNodeIterator<int> f = dl.begin(); f != dl.end(); f++) { }
  250. return _DListNodeIterator<T>(null);
  251. }
  252. //-----------------------------------------------------------运算符重载
  253. /// <summary>
  254. /// 重载的下标操作符 []
  255. /// </summary>
  256. T& operator[](const int& nIndex) const { return IndexOfNode(nIndex)->Data; }
  257. /// <summary>
  258. /// 重载的下标操作符 =
  259. /// </summary>
  260. /// 创建时间: ????-??-?? 最后一次修改时间:2024-04-19
  261. inline _DList<T>& operator = (const _DList<T>& other)
  262. {
  263. if (this != &other)
  264. {
  265. ClearData();
  266. Add(other);
  267. }
  268. return *this;
  269. }
  270. /// <summary>
  271. /// 类型转换
  272. /// </summary>
  273. inline operator _string() const{ return ToString(); }
  274. /// <summary>
  275. /// 类型转换
  276. /// </summary>
  277. inline operator _stdstr() const { return ToString().Data; }
  278. //---------------------------------------------------------虚函数重写
  279. /// <summary>
  280. /// 是否存在 item
  281. /// </summary>
  282. inline virtual bool Contains(const T& item){ return BinarySearch(item) != -1; }
  283. /// <summary>
  284. /// 交换两个节点的数据
  285. /// </summary>
  286. /// <typeparam name="T"></typeparam>
  287. /// <param name="iIndex1"></param>
  288. /// <param name="iIndex2"></param>
  289. /// <returns></returns>
  290. inline bool SwapNodeData(const int& iIndex1, const int& iIndex2)
  291. {
  292. _DListNode<T>* pNode1, * pNode2;
  293. pNode1 = IndexOfNode(iIndex1);
  294. pNode2 = IndexOfNode(iIndex2);
  295. if (!(pNode1 != null && pNode2 != null))
  296. {
  297. return false;
  298. }
  299. T ptmp = pNode1->Data;
  300. pNode1->Data = pNode2->Data;
  301. pNode2->Data = ptmp;
  302. return true;
  303. }
  304. /// <summary>
  305. /// 选择排序(Selection sort)是一种简单直观的排序算法。它的工作原理是:第一次从待排序的数据元素中选出最小
  306. /// 或最大)的一个元素,存放在序列的起始位置,然后再从剩余的未排序元素中寻找到最小(大)元素,然后放到已排序
  307. /// 的序列的末尾。以此类推,直到全部待排序的数据元素的个数为零。选择排序是不稳定的排序方法。
  308. /// </summary>
  309. /// <typeparam name="T"></typeparam>
  310. /// <param name="sortord"></param>
  311. /// 创建时间: ???-??-?? 最后一次修改时间:???-??-?? 已测试
  312. inline virtual void Sort_Selection(const _SortOrder& sortord = _SortOrder::s_Minmax)
  313. {
  314. if (_Count == 0 || _Count == 1) return;
  315. _DListNode<T>* min = _First, * tmp = _First->Next;
  316. if (sortord == _SortOrder::s_Minmax) //从小到大
  317. {
  318. while (min->Next != null)
  319. {
  320. while (tmp != null)
  321. {
  322. if (tmp->Data < min->Data) //交换数据
  323. {
  324. T pt = tmp->Data;
  325. tmp->Data = min->Data;
  326. min->Data = pt;
  327. }
  328. tmp = tmp->Next;
  329. }
  330. min = min->Next;
  331. tmp = min->Next;
  332. }
  333. }
  334. else
  335. {
  336. while (min->Next != null)
  337. {
  338. while (tmp != null)
  339. {
  340. if (tmp->Data > min->Data)
  341. {
  342. T pt = tmp->Data;
  343. tmp->Data = min->Data;
  344. min->Data = pt;
  345. }
  346. tmp = tmp->Next;
  347. }
  348. min = min->Next;
  349. tmp = min->Next;
  350. }
  351. }
  352. this->_so = sortord; //已排序
  353. }
  354. /// <summary>
  355. /// 返回索引的节点
  356. /// </summary>
  357. inline virtual _DListNode<T>* IndexOfNode(const int& iPos)const
  358. {
  359. if (iPos < 0 || iPos >= _Count) //错误索引:
  360. {
  361. return NULL;
  362. }
  363. unsigned int nindex = 0;
  364. if (iPos > _Count / 2)
  365. {
  366. _DListNode<T>* pNode = _Last;
  367. while (pNode != null)
  368. {
  369. if (nindex++ == _Count - iPos - 1) { return pNode; }
  370. pNode = pNode->Prev;
  371. }
  372. }
  373. else
  374. {
  375. _DListNode<T>* pNode = _First;
  376. while (pNode != null)
  377. {
  378. if (nindex++ == iPos)
  379. {
  380. return pNode;
  381. }
  382. pNode = pNode->Next;
  383. }
  384. }
  385. return null;
  386. }
  387. /// <summary>
  388. /// 把索引为nIndex的节点移到最后
  389. /// </summary>
  390. /// <typeparam name="T"></typeparam>
  391. /// <param name="iIndex"></param>
  392. /// <returns></returns>
  393. inline virtual bool MoveLast(const int& iIndex)
  394. {
  395. _DListNode<T>* pNode = IndexOfNode(iIndex);
  396. if (pNode != null)
  397. {
  398. if (pNode == _Last)
  399. return true;
  400. if (pNode == _First) //此时最少两个节点
  401. {
  402. _First = _First->Next;
  403. _First->Prev = null;
  404. _Last->Next = pNode;
  405. pNode->Prev = _Last;
  406. _Last = pNode;
  407. }
  408. else
  409. {
  410. pNode->Prev->Next = pNode->Next;
  411. pNode->Next->Prev = pNode->Prev;
  412. _Last->Next = pNode;
  413. pNode->Prev = _Last;
  414. _Last = pNode;
  415. }
  416. return true;
  417. }
  418. return false;
  419. }
  420. /// <summary>
  421. /// 把节点移到最后
  422. /// </summary>
  423. /// 创建时间: 2022-02-18 最后一次修改时间:2022-02-18
  424. inline virtual bool MoveLast(_DListNode<T>* dnCurrent)
  425. {
  426. if (dnCurrent == null) return false;
  427. this->_so = _SortOrder::s_null;
  428. if (_Count == 0)
  429. {
  430. return false;
  431. }
  432. else if (_Count == 1)
  433. {
  434. return true;
  435. }
  436. else if (_Count == 2)
  437. {
  438. if (dnCurrent == _First) //交换_First 与 _Last 数据
  439. {
  440. T tmp = _First->Data;
  441. _First->Data = _Last->Data;
  442. _Last->Data = tmp;
  443. }
  444. return true;
  445. }
  446. else
  447. {
  448. if (dnCurrent == _First)
  449. {
  450. _First = _First->Next;
  451. _First->Prev = null;
  452. _Last->Next = dnCurrent;
  453. dnCurrent->Next = null;
  454. dnCurrent->Prev = _Last;
  455. _Last = dnCurrent;
  456. }
  457. else if (dnCurrent != _Last)
  458. {
  459. dnCurrent->Prev->Next = dnCurrent->Next;
  460. dnCurrent->Next->Prev = dnCurrent->Prev;
  461. _Last->Next = dnCurrent;
  462. dnCurrent->Next = null;
  463. dnCurrent->Prev = _Last;
  464. _Last = dnCurrent;
  465. }
  466. return true;
  467. }
  468. }
  469. /// <summary>
  470. /// 把索引为nIndex的节点移到最前
  471. /// </summary>
  472. /// <param name="iIndex"></param>
  473. inline virtual bool MoveFirst(const int& iIndex)
  474. {
  475. _DListNode<T>* pNode = IndexOfNode(iIndex);
  476. if (pNode != null)
  477. {
  478. if (pNode == _First)
  479. return true;
  480. if (pNode == _Last) //此时最少两个节点
  481. {
  482. _Last->Prev->Next = null;
  483. _Last = _Last->Prev;
  484. pNode->Prev = null;
  485. pNode->Next = _First;
  486. _First->Prev = pNode;
  487. _First = pNode;
  488. }
  489. else
  490. {
  491. pNode->Prev->Next = pNode->Next;
  492. pNode->Next->Prev = pNode->Prev;
  493. pNode->Next = _First;
  494. _First->Prev = pNode;
  495. pNode->Prev = null;
  496. _First = pNode;
  497. }
  498. return true;
  499. }
  500. return false;
  501. }
  502. /// <summary>
  503. /// 将指定集合的元素添加到末尾
  504. /// </summary>
  505. /// <typeparam name="T"></typeparam>
  506. /// <param name="item"></param>
  507. /// <returns></returns>
  508. inline virtual bool Add(const T& item)
  509. {
  510. if (_Count == 0)
  511. {
  512. //_First = new _DListNode<T>(item);
  513. _First = _Memory::New< _DListNode<T> >(1);
  514. _First->Data = item;
  515. _First->Next = null;
  516. _First->Prev = null;
  517. _Last = _First;
  518. }
  519. else
  520. {
  521. _DListNode<T>* pNew = _Memory::New< _DListNode<T> >(1);
  522. pNew->Data = item;
  523. pNew->Next = null;
  524. pNew->Prev = _Last;
  525. _Last->Next = pNew;
  526. _Last = pNew;
  527. }
  528. ++_Count;
  529. this->_so = _SortOrder::s_null; //要重新排序
  530. return true;
  531. }
  532. /// <summary>
  533. /// 添加一个链表
  534. /// </summary>
  535. inline void Add(const _DList<T>& dList)
  536. {
  537. assert(&dList != null);
  538. _DListNode<T>* pNode = dList._First;
  539. while (pNode != null)
  540. {
  541. Add(pNode->Data);
  542. pNode = pNode->Next;
  543. }
  544. }
  545. protected:
  546. /// <summary>
  547. /// 在结点pListItem前面插入一个结点,成功,返回新的结点,否则返回null
  548. /// </summary>
  549. /// <typeparam name="T"></typeparam>
  550. /// <param name="pListItem"></param>
  551. /// <param name="rData"></param>
  552. /// <returns></returns>
  553. inline virtual _DListNode<T>* InserNodeFront(_DListNode<T>* pListItem, const T& rData)
  554. {
  555. assert(pListItem != null);
  556. _DListNode<T>* pNode = _Memory::New<_DListNode<T>>(1);
  557. pNode->Data = rData;
  558. //pNode
  559. pNode->Next = pListItem;
  560. pNode->Prev = pListItem->Prev;
  561. //--pListItem->Prev
  562. if (pListItem->Prev != null)
  563. {
  564. pListItem->Prev->Next = pNode;
  565. }
  566. else
  567. {
  568. _First = pNode;
  569. }
  570. //pListItem
  571. pListItem->Prev = pNode;
  572. ++_Count;
  573. return pNode;
  574. }
  575. /// <summary>
  576. /// 在结点pListItem后面插入一个结点,成功,返回新的结点,否则返回0;
  577. /// </summary>
  578. /// <typeparam name="T"></typeparam>
  579. /// <param name="pListItem"></param>
  580. /// <param name="rData"></param>
  581. /// <returns></returns>
  582. inline virtual _DListNode<T>* InserNodeBack(_DListNode<T>* pListItem, const T& rData)
  583. {
  584. if (pListItem == null) return null;
  585. _DListNode<T>* pNode = _Memory::New<_DListNode<T>>(1);
  586. pNode->Data = rData;
  587. //pNode
  588. pNode->Prev = pListItem;
  589. pNode->Next = pListItem->Next;
  590. //pListItem->Next
  591. if (pListItem->Next != null)
  592. {
  593. pListItem->Next->Prev = pNode;
  594. }
  595. else
  596. {
  597. _Last = pNode;
  598. }
  599. //--pListItem
  600. pListItem->Next = pNode;
  601. ++_Count;
  602. return pNode;
  603. }
  604. //------------------------------------------------------------操作
  605. public:
  606. /// <summary>
  607. /// 如果已排好序,它会按二分法查找,否则它会普通查找。
  608. /// </summary>
  609. /// <param name="item"></param>
  610. /// <returns></returns>
  611. /// 创建时间: ????-??-?? 最后一次修改时间:????_??_?? 已测试
  612. inline int BinarySearch(const T& item)const {
  613. switch (this->_so)
  614. {
  615. case _SortOrder::s_Maxmin:
  616. {
  617. if (_Count == 0)
  618. {
  619. return -1;
  620. }
  621. if (_Count == 1)
  622. {
  623. //return (_First.Data as IComparable).CompareTo(item) == 0 ? 0 : -1; //C#
  624. return _First->Data == item ? 0 : -1;
  625. }
  626. if (_Count == 2)
  627. {
  628. //if ((_First.Data as IComparable).CompareTo(item) == 0) return 0;
  629. //if ((_First.Next.Data as IComparable).CompareTo(item) == 0) return 1;
  630. if (_First->Data == item) return 0;
  631. if (_First->Next->Data == item) return 1;
  632. return -1;
  633. }
  634. int nPos = (int)_Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  635. int nLeft = 0; //左边远素
  636. int nRight = (int)_Count - 1; //右边远素
  637. _DListNode<T>* pNode;
  638. while (nRight >= 0 && nLeft >= 0)
  639. {
  640. pNode = IndexOfNode(nPos);
  641. //int iCom = (item as IComparable).CompareTo(ld.Data);
  642. if (item > pNode->Data)
  643. {
  644. if (nRight == nLeft || nPos == nLeft)
  645. {
  646. return -1;
  647. }
  648. nRight = nPos - 1;
  649. }
  650. else if (item < pNode->Data)
  651. {
  652. if (nRight == nLeft || nPos == nRight)
  653. {
  654. return -1;
  655. }
  656. nLeft = nPos + 1;
  657. }
  658. else
  659. {
  660. return nPos;
  661. }
  662. nPos = nLeft + (nRight - nLeft + 1) / 2;
  663. }
  664. break;
  665. }
  666. case _SortOrder::s_Minmax:
  667. {
  668. if (_Count == 0)
  669. {
  670. return -1;
  671. }
  672. if (_Count == 1)
  673. {
  674. //return (_First.Data as IComparable).CompareTo(item) == 0 ? 0 : -1;
  675. return _First->Data == item ? 0 : -1;
  676. }
  677. if (_Count == 2)
  678. {
  679. //if ((_First.Data as IComparable).CompareTo(item) == 0) return 0;
  680. //if ((_First.Next.Data as IComparable).CompareTo(item) == 0) return 1;
  681. if (_First->Data == item) return 0;
  682. if (_First->Next->Data == item) return 1;
  683. return -1;
  684. }
  685. int nPos = (int)_Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  686. int nLeft = 0; //左边远素
  687. int nRight = (int)_Count - 1; //右边远素
  688. _DListNode<T>* pNode = null;
  689. while (nRight >= 0 && nLeft >= 0)
  690. {
  691. pNode = IndexOfNode(nPos);
  692. //int iCom = (item as IComparable).CompareTo(ld.Data);
  693. if (item < pNode->Data)
  694. {
  695. if (nRight == nLeft || nPos == nLeft)
  696. {
  697. return -1;
  698. }
  699. nRight = nPos - 1;
  700. }
  701. else if (item > pNode->Data)
  702. {
  703. if (nRight == nLeft || nPos == nRight)
  704. {
  705. return -1;
  706. }
  707. nLeft = nPos + 1;
  708. }
  709. else
  710. {
  711. return nPos;
  712. }
  713. nPos = nLeft + (nRight - nLeft + 1) / 2;
  714. }
  715. break;
  716. }
  717. case _SortOrder::s_null:
  718. {
  719. _DListNode<T>* pNode = _First;
  720. int iCount = 0;
  721. while (pNode != null)
  722. {
  723. if (pNode->Data == item)
  724. {
  725. return iCount;
  726. }
  727. pNode = pNode->Next;
  728. ++iCount;
  729. }
  730. break;
  731. }
  732. default:
  733. {
  734. return -1;
  735. }
  736. }
  737. return -1;
  738. }
  739. /// <summary>
  740. /// 清除节点,并释放内存
  741. /// </summary>
  742. /// <typeparam name="T"></typeparam>
  743. /// 创建时间: ????-??-?? 最后一次修改时间:2022-12-24 (已测试)
  744. inline void ClearData() override { ClearMemory(); }
  745. /// <summary>
  746. /// 清除节点,并释放内存
  747. /// </summary>
  748. inline void ClearMemory() override
  749. {
  750. _Count = 0;
  751. _DListNode<T>* dn = _First;
  752. while (dn != null)
  753. {
  754. if (dn->Prev != null)
  755. _Memory::Delete< _DListNode<T> >(dn->Prev, 1);
  756. dn = dn->Next;
  757. }
  758. if (_Last != null)
  759. _Memory::Delete< _DListNode<T> >(_Last, 1);
  760. _First = null;
  761. _Last = null;
  762. this->_so = _SortOrder::s_null;
  763. }
  764. /// <summary>
  765. /// 复制一个链表,清除原来链表的数据
  766. /// </summary>
  767. /// <typeparam name="T"></typeparam>
  768. /// <param name="ld"></param>
  769. inline void CopyFrom(const _DList<T>& ld)
  770. {
  771. if (this != &ld)
  772. {
  773. ClearData();
  774. _DListNode<T>* pNode = ld._First;
  775. while (pNode != null)
  776. {
  777. Add(pNode->Data);
  778. pNode = pNode->Next;
  779. }
  780. }
  781. }
  782. /// <summary>
  783. /// 移除指定索引处的元素
  784. /// </summary>
  785. /// <typeparam name="T">类型</typeparam>
  786. /// <param name="iIndex">要移除的元素的从零开始的索引。</param>
  787. /// <returns>成功返回true,否则返回false</returns>
  788. /// 创建时间:????-??-?? 最后一次修改时间:2023-04-08
  789. inline bool RemoveAt(const int& iIndex)
  790. {
  791. if (iIndex < 0 || iIndex >= _Count) return false;
  792. _DListNode<T>* pNode = _First;
  793. int iCount = 0;
  794. while (pNode != null)
  795. {
  796. if (iCount == iIndex)
  797. {
  798. if (pNode == _First)
  799. {
  800. if (_First->Next == null) //只有一个
  801. {
  802. ClearData();
  803. return true;
  804. }
  805. else
  806. {
  807. _First = _First->Next;
  808. _First->Prev = null;
  809. --_Count;
  810. _Memory::Delete< _DListNode<T> >(pNode, 1);
  811. return true;
  812. }
  813. }
  814. else if (pNode == _Last)
  815. {
  816. if (_Last->Prev == null)
  817. {
  818. ClearData();
  819. return true;
  820. }
  821. else
  822. {
  823. _Last = _Last->Prev;
  824. _Last->Next = null;
  825. --_Count;
  826. _Memory::Delete< _DListNode<T>>(pNode, 1);
  827. return true;
  828. }
  829. }
  830. else
  831. {
  832. pNode->Prev->Next = pNode->Next;
  833. pNode->Next->Prev = pNode->Prev;
  834. --_Count;
  835. _Memory::Delete< _DListNode<T>>(pNode, 1);
  836. return true;
  837. }
  838. }
  839. pNode = pNode->Next;
  840. ++iCount;
  841. }
  842. return false;
  843. }
  844. /// <summary>
  845. /// 查找一项数据
  846. /// </summary>
  847. inline _DListNode<T>* FindNodeItem(const T& item)const
  848. {
  849. switch (this->_so)
  850. {
  851. case _SortOrder::s_Maxmin:
  852. {
  853. if (_Count == 0)
  854. {
  855. return null;
  856. }
  857. if (_Count == 1)
  858. {
  859. //return (_First.Data as IComparable).CompareTo(item) == 0 ? _First : null;
  860. return _First->Data == item ? _First : null;
  861. }
  862. if (_Count == 2)
  863. {
  864. //if ((_First.Data as IComparable).CompareTo(item) == 0) return _First;
  865. //if ((_First.Next.Data as IComparable).CompareTo(item) == 0) return _First.Next;
  866. if (_First->Data == item) return _First;
  867. if (_First->Next->Data == item) return _First->Next;
  868. return null;
  869. }
  870. int nPos = (int)(_Count / 2); //nPos在中间,所以无素一定要大于等于3才行
  871. int nLeft = 0; //左边远素
  872. int nRight = (int)(_Count - 1); //右边远素
  873. _DListNode<T>* pNode = null;
  874. while (nRight >= 0 && nLeft >= 0)
  875. {
  876. pNode = IndexOfNode(nPos);
  877. //int iCom = (item as IComparable).CompareTo(ld.Data);
  878. if (item > pNode->Data)
  879. {
  880. if (nRight == nLeft || nPos == nLeft)
  881. {
  882. return null;
  883. }
  884. nRight = nPos - 1;
  885. }
  886. else if (item < pNode->Data)
  887. {
  888. if (nRight == nLeft || nPos == nRight)
  889. {
  890. return null;
  891. }
  892. nLeft = nPos + 1;
  893. }
  894. else
  895. {
  896. return pNode;
  897. }
  898. nPos = nLeft + (nRight - nLeft + 1) / 2;
  899. }
  900. break;
  901. }
  902. case _SortOrder::s_Minmax:
  903. {
  904. if (_Count == 0)
  905. {
  906. return null;
  907. }
  908. if (_Count == 1)
  909. {
  910. //return (_First.Data as IComparable).CompareTo(item) == 0 ? _First : null;
  911. return _First->Data == item ? _First : null;
  912. }
  913. if (_Count == 2)
  914. {
  915. //if ((_First.Data as IComparable).CompareTo(item) == 0) return _First;
  916. //if ((_First.Next.Data as IComparable).CompareTo(item) == 0) return _First.Next;
  917. if (_First->Data == item) return _First;
  918. if (_First->Next->Data == item) return _First->Next;
  919. return null;
  920. }
  921. int nPos = (int)(_Count / 2); //nPos在中间,所以无素一定要大于等于3才行
  922. int nLeft = 0; //左边远素
  923. int nRight = (int)(_Count - 1); //右边远素
  924. _DListNode<T>* pNode = null;
  925. while (nRight >= 0 && nLeft >= 0)
  926. {
  927. pNode = IndexOfNode(nPos);
  928. //int iCom = (item as IComparable).CompareTo(ld.Data);
  929. if (item < pNode->Data)
  930. {
  931. if (nRight == nLeft || nPos == nLeft)
  932. {
  933. return null;
  934. }
  935. nRight = nPos - 1;
  936. }
  937. else if (item > pNode->Data)
  938. {
  939. if (nRight == nLeft || nPos == nRight)
  940. {
  941. return null;
  942. }
  943. nLeft = nPos + 1;
  944. }
  945. else
  946. {
  947. return pNode;
  948. }
  949. nPos = nLeft + (nRight - nLeft + 1) / 2;
  950. }
  951. break;
  952. }
  953. case _SortOrder::s_null:
  954. {
  955. _DListNode<T>* pNode = _First;
  956. while (pNode != null)
  957. {
  958. //总结:Equals比较的永远是变量的内容是否相同,而= =比较的则是引用地址是否相同(前提:此种类型内部没有对Equals 或= = 进行重写操作,
  959. //否则输出可能会有不同)。string 类型是个特例,因为他的内部对这两个都进行了重写。
  960. if (item == pNode->Data)
  961. {
  962. return pNode;
  963. }
  964. /*
  965. if (pNode.Data.Equals(item))
  966. {
  967. return pNode;
  968. }
  969. */
  970. pNode = pNode->Next;
  971. }
  972. break;
  973. }
  974. default:
  975. {
  976. return null;
  977. }
  978. }
  979. return null;
  980. }
  981. /// <summary>
  982. /// 删除链表中的数据
  983. /// </summary>
  984. /// <typeparam name="T"></typeparam>
  985. /// <param name="pData"></param>
  986. /// <returns></returns>
  987. inline bool RemoveItem(const T& pData)
  988. {
  989. if (this->_so == _SortOrder::s_null)
  990. {
  991. _DListNode<T>* pNode = _First;
  992. while (pNode != null)
  993. {
  994. if (pNode->Data == pData) //找到一项
  995. {
  996. if (pNode == _First) //删除的是第一个节点
  997. {
  998. if (_First->Next != null)
  999. {
  1000. _First->Next->Prev = null;
  1001. _First = _First->Next;
  1002. }
  1003. else
  1004. {
  1005. _First = null;
  1006. _Last = null;
  1007. }
  1008. }
  1009. else if (pNode == _Last) //删除的是最后一个节点
  1010. {
  1011. if (_Last->Prev != null)
  1012. {
  1013. _Last->Prev->Next = null;
  1014. _Last = _Last->Prev;
  1015. }
  1016. else
  1017. {
  1018. _Last = null;
  1019. _Last = null;
  1020. }
  1021. }
  1022. else //删除的是中间的一个节点
  1023. {
  1024. pNode->Next->Prev = pNode->Prev;
  1025. pNode->Prev->Next = pNode->Next;
  1026. }
  1027. --_Count;
  1028. return true;
  1029. }
  1030. pNode = pNode->Next;
  1031. }
  1032. return false;
  1033. }
  1034. else
  1035. {
  1036. return RemoveAt(BinarySearch(pData));
  1037. }
  1038. }
  1039. /// <summary>
  1040. /// 删除最后一个节点
  1041. /// </summary>
  1042. /// 创建时间:2020-09-12 最后一次修改时间: 2023-01-18
  1043. inline bool DeleteLast()
  1044. {
  1045. auto pDelete = Last();
  1046. if (_Count <= 0)
  1047. {
  1048. return false;
  1049. }
  1050. else if (_Count == 1)
  1051. {
  1052. _First = null;
  1053. _Last = null;
  1054. _Count = 0;
  1055. }
  1056. else if (_Count == 2)
  1057. {
  1058. _Last = _First;
  1059. _Last->Prev = null;
  1060. _Last->Next = null;
  1061. _First->Next = null;
  1062. _First->Prev = null;
  1063. --_Count;
  1064. }
  1065. else
  1066. {
  1067. _Last->Prev->Next = null;
  1068. _Last = _Last->Prev;
  1069. --_Count;
  1070. }
  1071. _Memory::Delete<_DListNode<T>>(pDelete, 1);
  1072. return true;
  1073. }
  1074. /// <summary>
  1075. /// 添加一个元素,并把它放在首位,其它元素后移,如果后面的元素删除,总无素个数不变,如果元素个数为零,则添加一个无素。
  1076. /// </summary>
  1077. /// <param name="Item"></param>
  1078. /// <param name="bRemoveLast"></param>
  1079. /// 创建时间: 2022-04-19 最后一次修改时间:2022-04-19
  1080. inline void HistoryAdd(const T& Item, bool bRemoveLast)
  1081. {
  1082. if (_Count == 0) {
  1083. Add(Item);
  1084. }
  1085. else if (_Count == 1) {
  1086. if (bRemoveLast) {
  1087. _First->Data = Item;
  1088. }
  1089. else {
  1090. //把无素放在最前
  1091. _DListNode<T>* dnNew = _Memory::New<_DListNode<T>>(1);
  1092. dnNew->Data = Item;
  1093. _First->Prev = dnNew;
  1094. dnNew->Next = _First;
  1095. _First = dnNew;
  1096. ++_Count;
  1097. }
  1098. }
  1099. else {
  1100. if (bRemoveLast) {
  1101. _DListNode<T>* dnDelete = _Last;
  1102. //删除最后一个元素
  1103. _Last = _Last->Prev;
  1104. _Last->Next = null;
  1105. _DListNode<T>* dnNew = _Memory::New<_DListNode<T>>(1);
  1106. dnNew->Data = Item;
  1107. _First->Prev = dnNew;
  1108. dnNew->Next = _First;
  1109. dnNew->Prev = null;
  1110. _First = dnNew;
  1111. _Memory::Delete< _DListNode<T>>(dnDelete, 1);
  1112. }
  1113. else {
  1114. //把无素放在最前
  1115. _DListNode<T>* dnNew = _Memory::New<_DListNode<T>>(1);
  1116. dnNew->Data = Item;
  1117. _First->Prev = dnNew;
  1118. dnNew->Next = _First;
  1119. dnNew->Prev = null;
  1120. _First = dnNew;
  1121. ++_Count;
  1122. }
  1123. }
  1124. }
  1125. /// <summary>
  1126. /// 出栈(先进后出),删除最后一个元素,
  1127. /// </summary>
  1128. /// 创建时间: 2022-04-19 最后一次修改时间:2023-04-06
  1129. inline T StackPop()
  1130. {
  1131. assert(_Count > 0);
  1132. T tResult = _Last->Data;
  1133. this->RemoveAt(_Count - 1);
  1134. return tResult;
  1135. }
  1136. //----------------------------------------------------------------------------------------------------Python List方法
  1137. /// <summary>
  1138. /// 将元素tItem添加到列表末尾。
  1139. /// </summary>
  1140. /// 创建时间: 2023-04-08 最后一次修改时间:2023-04-08
  1141. inline void Python_append(const T& tItem)
  1142. {
  1143. Add(tItem);
  1144. }
  1145. /// <summary>
  1146. /// 在位置nIndex后面插入一个元素tItem
  1147. /// </summary>
  1148. inline void Python_insert(const int nIndex, const T& tItem)
  1149. {
  1150. InserNodeBack(IndexOfNode(nIndex), tItem);
  1151. }
  1152. /// <summary>
  1153. /// 在最前面插入一项
  1154. /// </summary>
  1155. /// <param name="tItem"></param>
  1156. /// 创建时间: 2024-04-16 最后一次修改时间:2024-04-16
  1157. inline void Inseart_front(const T& tItem)
  1158. {
  1159. _DListNode<T>* pNode = _Memory::New<_DListNode<T>>(1);
  1160. pNode->Data = tItem;
  1161. if (_First != null)
  1162. {
  1163. _First->Prev = pNode;
  1164. pNode->Next = _First;
  1165. pNode->Prev = null;
  1166. _First = pNode;
  1167. }
  1168. else
  1169. {
  1170. pNode->Next = null;
  1171. pNode->Prev = null;
  1172. _First = pNode;
  1173. _Last = pNode;
  1174. }
  1175. ++_Count;
  1176. }
  1177. /// <summary>
  1178. /// 删除索引位置为nIndex的元素,并返回删除的元素值的拷贝,如果索引值nIndex = -1,则默认删除为最后一个元素。
  1179. /// </summary>
  1180. /// <param name="nIndex"></param>
  1181. /// <returns></returns>
  1182. /// 创建时间: 2023-04-08 最后一次修改时间:2023-04-09
  1183. inline T Python_pop(const int nIndex = -1)
  1184. {
  1185. if (nIndex == -1)
  1186. {
  1187. return StackPop();
  1188. }
  1189. else
  1190. {
  1191. auto dn = this->IndexOfNode(nIndex);
  1192. T tmp = T();
  1193. if (dn != null)
  1194. {
  1195. tmp = dn->Data;
  1196. DeleteNode(dn);
  1197. }
  1198. return tmp;
  1199. }
  1200. }
  1201. /// <summary>
  1202. /// 删除值为tItem的一项。
  1203. /// 注意,方法remove()只删除第一个指定的值。如果要删除的值可能在列表中出现多次,
  1204. /// 就需要使用循环来确保每个值都删除。
  1205. /// </summary>
  1206. inline bool Python_remove(const T& tItem)
  1207. {
  1208. int n = _Count;
  1209. DeleteNode(FindNodeItem(tItem));
  1210. return n == _Count;
  1211. }
  1212. protected:
  1213. /// <summary>
  1214. /// 删除链表中的节点
  1215. /// </summary>
  1216. /// <typeparam name="T"></typeparam>
  1217. /// <param name="pListItem"></param>
  1218. /// <returns></returns>
  1219. //inline bool DeleteNode(const _DListNode<T>* pNodeDelete)
  1220. //{
  1221. // if (_Count == 0 || pNodeDelete == null)
  1222. // {
  1223. // return false;
  1224. // }
  1225. // _DListNode<T>* pNode = _First.Next;
  1226. // while (pNode != null)
  1227. // {
  1228. // if (pNode == pNodeDelete) //找到了
  1229. // {
  1230. // //pListItem->Prev
  1231. // if (pNodeDelete->Prev != null)
  1232. // {
  1233. // pNodeDelete->Prev->Next = pNodeDelete->Next;
  1234. // }
  1235. // else //删除的是第一个节点
  1236. // {
  1237. // _First = pNodeDelete.Next;
  1238. // }
  1239. // //pListItem->Next
  1240. // if (pNodeDelete->Next != null)
  1241. // {
  1242. // pNodeDelete->Next->Prev = pNodeDelete->Prev;
  1243. // }
  1244. // else //删除的是最后一个节点
  1245. // {
  1246. // _Last = pNodeDelete->Prev;
  1247. // }
  1248. // break;
  1249. // }
  1250. // pNode = pNode->Next;
  1251. // }
  1252. // if (pNode != null)
  1253. // {
  1254. // --_Count;
  1255. // _Memory::Delete< _DListNode<T> >(pNode,1); //C#不用清除内存
  1256. // return true;
  1257. // }
  1258. // return false;
  1259. //}
  1260. /// <summary>
  1261. /// 删除链表中的某一节点,注意,这个节点一定要是在链表中的。
  1262. /// </summary>
  1263. /// 创建时间: 2023-04-09 最后一次修改时间:2023-04-09
  1264. inline void DeleteNode(_DListNode<T>* pNodeDelete)
  1265. {
  1266. if (_Count == 0 || pNodeDelete == null) return;
  1267. if (_Count == 1)
  1268. {
  1269. ClearMemory();
  1270. }
  1271. else
  1272. {
  1273. if (pNodeDelete == _First) //删除的是第一个节点
  1274. {
  1275. _First = _First->Next;
  1276. _First->Prev = null;
  1277. }
  1278. else if (pNodeDelete == _Last)
  1279. {
  1280. _Last = _Last->Prev;
  1281. _Last->Next = null;
  1282. }
  1283. else
  1284. {
  1285. pNodeDelete->Prev->Next = pNodeDelete->Next;
  1286. pNodeDelete->Next->Prev = pNodeDelete->Prev;
  1287. }
  1288. --_Count;
  1289. _Memory::Delete< _DListNode<T> >(pNodeDelete, 1);
  1290. }
  1291. }
  1292. public:
  1293. //---------------------------------------------------------- C++
  1294. inline void Push_back(const T& TypeObject) { Add(TypeObject); }
  1295. public: //------------------------------------------------------------------重写
  1296. /// <summary>
  1297. /// 转换为字符串
  1298. /// </summary>
  1299. /// <returns></returns>
  1300. /// 创建时间: 2023-05-16 最后一次修改时间:2024-01-14
  1301. inline virtual _string ToSplitString(const _string& sSplitString) const override
  1302. {
  1303. //不可以这样: const _DList<_Object>* dp = (_DList<_Object> *)pList;
  1304. //就算 T 类型数据是从 _Object中继承也不可以。
  1305. _string sResult;
  1306. sResult.Add(_t("{"));
  1307. _string sp = sSplitString.Length == 0 ? _string(_t(",")) : sSplitString;
  1308. //是否继承处_Object
  1309. if (std::is_base_of<_Object, T>::value)
  1310. {
  1311. _Object* po;
  1312. if (_Count == 1)
  1313. {
  1314. po = (_Object*)(&_First->Data);
  1315. sResult.Add((_string)(*po));
  1316. }
  1317. _DListNode<T>* dn = this->_First;
  1318. while (dn != _Last)
  1319. {
  1320. po = (_Object*)(&dn->Data);
  1321. sResult.Add((_string)(*po));
  1322. sResult.Add(sp);
  1323. dn = dn->Next;
  1324. }
  1325. po = (_Object*)(&_Last->Data);
  1326. sResult.Add((_string)(*po));
  1327. }
  1328. else
  1329. {
  1330. if (typeid(T) == typeid(int))
  1331. {
  1332. _DListNode<T>* dn = this->_First;
  1333. while (dn != _Last)
  1334. {
  1335. int* pInt = (int*)&(dn->Data);
  1336. sResult.Add(_string::Java_valueOf(*pInt));
  1337. sResult.Add(sp);
  1338. dn = dn->Next;
  1339. }
  1340. if (this->Count > 0)
  1341. sResult.Add(_string::Java_valueOf(*((int*)(&(_Last->Data)))));
  1342. }
  1343. else if(typeid(T) == typeid(size_t))
  1344. {
  1345. _DListNode<T>* dn = this->_First;
  1346. while (dn != _Last)
  1347. {
  1348. size_t* pInt = (size_t*)&(dn->Data);
  1349. sResult.Add(_string::Java_valueOf(*pInt));
  1350. sResult.Add(sp);
  1351. dn = dn->Next;
  1352. }
  1353. if (this->Count > 0)
  1354. sResult.Add(_string::Java_valueOf(*((size_t*)(&(_Last->Data)))));
  1355. }
  1356. else if (typeid(T) == typeid(double))
  1357. {
  1358. if (_Count == 0) return sResult;
  1359. double* pd;
  1360. if (_Count == 1)
  1361. {
  1362. pd = (double*)(&(_First->Data));
  1363. sResult.Add(_Convert::DoubleToString(*pd));
  1364. }
  1365. _DListNode<T>* dn = this->_First;
  1366. while (dn != _Last)
  1367. {
  1368. pd = (double*)&(dn->Data);
  1369. sResult.Add(_Convert::DoubleToString(*pd));
  1370. sResult.Add(sp);
  1371. dn = dn->Next;
  1372. }
  1373. pd = (double*)&(_Last->Data);
  1374. sResult.Add(_Convert::DoubleToString(*pd));
  1375. }
  1376. else if (typeid(T) == typeid(_string))
  1377. {
  1378. _string* ps;
  1379. _DListNode<T>* dn = this->_First;
  1380. while (dn != _Last)
  1381. {
  1382. ps = (_string*)(&dn->Data);
  1383. sResult.Add(_t("\""));
  1384. sResult.Add(*ps);
  1385. sResult.Add(_t("\""));
  1386. sResult.Add(sp);
  1387. dn = dn->Next;
  1388. }
  1389. if (_Count > 0)
  1390. {
  1391. ps = (_string*)(&_Last->Data);
  1392. sResult.Add(_t("\""));
  1393. sResult.Add(*ps);
  1394. sResult.Add(_t("\""));
  1395. }
  1396. }
  1397. else if (typeid(T) == typeid(_StrA))
  1398. {
  1399. _StrA* ps;
  1400. if (_Count <= 0)
  1401. {
  1402. }
  1403. else if (_Count == 1)
  1404. {
  1405. ps = (_StrA*)(&_First->Data);
  1406. sResult.Add(_t("\""));
  1407. sResult.Add(*ps);
  1408. sResult.Add(_t("\""));
  1409. }
  1410. else
  1411. {
  1412. _DListNode<T>* dn = this->_First;
  1413. while (dn != _Last)
  1414. {
  1415. ps = (_StrA*)(&dn->Data);
  1416. sResult.Add(_t("\""));
  1417. sResult.Add(*ps);
  1418. sResult.Add(_t("\""));
  1419. sResult.Add(_t(','));
  1420. dn = dn->Next;
  1421. }
  1422. ps = (_StrA*)(&_Last->Data);
  1423. sResult.Add(_t("\""));
  1424. sResult.Add(*ps);
  1425. sResult.Add(_t("\""));
  1426. }
  1427. }
  1428. else //所有继承自 _Object 类的数据类型都可以
  1429. {
  1430. sResult.Add(_t("_LDList::ToSplitString重写,数据类型为:"));
  1431. sResult.Add(_string(typeid(T).name()));
  1432. }
  1433. }
  1434. sResult.Add(_t("}\n"));
  1435. return sResult;
  1436. }
  1437. inline _string ToString()const
  1438. {
  1439. return ToSplitString(_t(""));
  1440. }
  1441. }; //--------------------------------------------------------------------------DList
  1442. //-----------------------------------------------------------------------SortedDList
  1443. /// <summary>
  1444. /// C#语句:public class SortList<T> : _DList<T>
  1445. /// </summary>
  1446. /// <typeparam name="T"></typeparam>
  1447. template<class T>
  1448. class SortedDList : public _DList<T>
  1449. {
  1450. };
  1451. //----------------------------------------------------------------------StringList
  1452. template<class T>
  1453. class _StrList : public _DList<T>
  1454. {
  1455. public:
  1456. //------------------------------------------------------------------构造与析构
  1457. _StrList() : _DList<T>() {};
  1458. _StrList(const _StrList<T>& sl) : _DList<T>(sl) {};
  1459. explicit _StrList(const _char* pStr, const _char* pSplit, bool bIgnoreEmptyString = false)
  1460. {
  1461. this->InitData();
  1462. SplitForSeparator(pStr, pSplit, bIgnoreEmptyString);
  1463. }
  1464. /// <summary>
  1465. /// 要加上 explicit阻止自动转换, 否则执行语名会自动调用这个构造函数 _StrList ls = { L"AA",L"BB"};
  1466. /// </summary>
  1467. /// <param name="sText"></param>
  1468. /// <param name="sSplit"></param>
  1469. /// <param name="bIgnoreEmptyString"></param>
  1470. explicit _StrList(const T& sText, const T& sSplit, bool bIgnoreEmptyString = false)
  1471. {
  1472. //assert(sText != null && sSplit != null);
  1473. //SplitForSeparator(sText.Data, sSplit.Data, bIgnoreEmptyString);
  1474. if (sText.Length == 0) { return; }
  1475. if (sSplit.Length == 0) { Add(sText); return; }
  1476. int iStart = 0;
  1477. int iIndex = sText.IndexOf(sSplit, iStart);
  1478. if (iIndex == -1)
  1479. {
  1480. Add(sText);
  1481. return;
  1482. }
  1483. while (iIndex != -1 && iStart + 1 <= sText.Length)
  1484. {
  1485. if (iIndex != iStart)
  1486. Add(sText.SubStr(iStart, iIndex - iStart));
  1487. else
  1488. {
  1489. if (!bIgnoreEmptyString) Add(T());
  1490. }
  1491. iStart = iIndex + sSplit.Length;
  1492. iIndex = sText.IndexOf(sSplit, iStart);
  1493. if (iIndex == -1 && sText.Length != iStart)
  1494. Add(sText.SubStr(iStart, sText.Length - iStart)); //拷贝最后一个
  1495. }
  1496. }
  1497. _StrList(std::initializer_list<T> aList)
  1498. {
  1499. for (T s : aList)
  1500. {
  1501. Add(s);
  1502. }
  1503. }
  1504. public:
  1505. //------------------------------------------------------------------操作
  1506. void writeToFile(const T& sFullPathName)
  1507. {
  1508. }
  1509. bool readToFile(const T& sFullPathName)
  1510. {
  1511. return false;
  1512. }
  1513. bool readToUnicodeFile(const T& sFileName, const T& sSplit)
  1514. {
  1515. return false;
  1516. }
  1517. /// <summary>
  1518. /// 获取所有字符串的总共长度
  1519. /// </summary>
  1520. /// <returns></returns>
  1521. /// 创建时间: 2022-11-05 最后一次修改时间: 2022-11-05
  1522. int GetStringLength() const
  1523. {
  1524. int iSum = 0;
  1525. auto dn = this->_First;
  1526. while (dn != null) {
  1527. iSum += (int)dn->Data.Length;
  1528. dn = dn->Next;
  1529. }
  1530. return iSum;
  1531. }
  1532. T connectForSeparator(const T& sConnector)const
  1533. {
  1534. if (this->_Count == 0) return _t("");
  1535. if (this->_Count == 1) return this->_First->Data;
  1536. T tmp(_t(""), GetStringLength() + sConnector.Length * this->_Count + 100);
  1537. _DListNode<T>* ldNode = this->_First;
  1538. while (ldNode != this->_Last)
  1539. {
  1540. tmp += ldNode->Data;
  1541. tmp += sConnector;
  1542. ldNode = ldNode->Next;
  1543. }
  1544. tmp += this->_Last->Data; //加入最后一项
  1545. return tmp;
  1546. }
  1547. T connectForSeparator(const _char& cConnector) const
  1548. {
  1549. return connectForSeparator(&cConnector);
  1550. }
  1551. /// <summary>
  1552. /// 返回分隔后的字符串列表
  1553. /// </summary>
  1554. /// <param name="pStr">原文本</param>
  1555. /// <param name="pSplit">分隔字符串</param>
  1556. /// <param name="bIgnoreEmptyString">是否忽略空字符串</param>
  1557. /// <returns>返回一个字符串列表</returns>
  1558. /// 创建时间: 2022-10-04 最后一修改时间:2022-10-05 已测试
  1559. _StrList<T>& SplitForSeparator(const _char* pStr, const _char* pSplit, bool bIgnoreEmptyString)
  1560. {
  1561. if (pStr == null || pSplit == null)
  1562. {
  1563. _cout << "在中_StrList::SplitForSeparator中" << L"pStr == null || pSplit == null" << "\n";
  1564. throw "pStr == null || pSplit == null";
  1565. }
  1566. this->ClearData();
  1567. if (pStr[0] == 0 || pSplit[0] == 0)
  1568. {
  1569. Add(_t(""), 0, 0);
  1570. return *this;
  1571. }
  1572. int i = 0;
  1573. int j = 0;
  1574. int nStart = 0, nEnd = 0;
  1575. while (pStr[i] != 0) {
  1576. // _cout << _t("pStr[i] = ") << pStr[i] << _t("\n"); //此句出错,无任何提示
  1577. bool bFind = true;
  1578. j = 0;
  1579. while (pSplit[j] != 0) {
  1580. if (pStr[i + j] != pSplit[j]) {
  1581. bFind = false;
  1582. break;
  1583. }
  1584. ++j;
  1585. }
  1586. if (bFind) {
  1587. nEnd = i - 1; //此处如果 nEnd 是 int ,则 nEnd = i - 1 => nEnd = 18446744073709551615 => 溢出错误
  1588. if (bIgnoreEmptyString) {
  1589. if (nStart <= nEnd) {
  1590. Add(pStr, nStart, nEnd); //这里应nStart <= nEnd,而不是 nStart < nEnd,因为当 nStart = nEnd 还是有一个字符的
  1591. }
  1592. }
  1593. else {
  1594. Add(pStr, nStart, nEnd);
  1595. }
  1596. nStart = i + j;
  1597. i = nStart - 1;
  1598. }
  1599. ++i;
  1600. }
  1601. //拷贝右边最后一项
  1602. if (bIgnoreEmptyString) {
  1603. if (nStart <= i - 1) {
  1604. Add(pStr, nStart, (int)i - 1);
  1605. }
  1606. }
  1607. else {
  1608. Add(pStr, nStart, (int)i - 1);
  1609. }
  1610. return *this;
  1611. }
  1612. //int SplitForSeparator(const T& sText, const _char& cSplit);
  1613. int IndexOf(const T& s)
  1614. {
  1615. int nIndex = 0;
  1616. auto dn = this->_First;
  1617. while (dn)
  1618. {
  1619. if (dn->Data == s) { return nIndex; }
  1620. ++nIndex;
  1621. dn = dn->Next;
  1622. }
  1623. return -1;
  1624. }
  1625. int GetMaxSpaceLength(int nTabCount = 9, int nChineseCharactersCount = 3)const
  1626. {
  1627. int nMax = 0;
  1628. auto dn = this->_First;
  1629. while (dn)
  1630. {
  1631. int n = gs.s_length_space(dn->Data.Data, nTabCount, nChineseCharactersCount);
  1632. if (n > nMax) nMax = n;
  1633. dn = dn->Next;
  1634. }
  1635. return nMax;
  1636. }
  1637. /// <summary>
  1638. /// 用tab键使每行等长
  1639. /// </summary>
  1640. /// <param name="nTabCount"></param>
  1641. /// <returns></returns>
  1642. /// 创建时间: 2022-10-30 最后一次修改时间: 2022-10-30
  1643. T equilongTabLine(int nTabCount = 9)
  1644. {
  1645. this->RemoveHeadTab();
  1646. int iMax = GetMaxSpaceLength(nTabCount);
  1647. for (T& s : *this) {
  1648. int nSapceLength = gs.s_length_space(s.Data);
  1649. int n = (iMax - nSapceLength) / 9;
  1650. if (iMax - nSapceLength - n * 9 >= 5)
  1651. ++n;
  1652. else
  1653. --n;
  1654. for (int j = 0; j < n; j++)
  1655. {
  1656. s.Add(_t("\t"));
  1657. }
  1658. }
  1659. return connectForSeparator(_t('\n')) + _t('\n');
  1660. }
  1661. /// <summary>
  1662. /// 计算所有行,如果每行都有开始处都有 \t ,则每行除去 \t , 除去个数以最少 \t 行为准。
  1663. /// 例:
  1664. /// \t\t abc
  1665. /// \t bcd
  1666. /// \t\t\t dd
  1667. /// 运行函数后变成
  1668. /// \t abc
  1669. /// bcd
  1670. /// \t\t dd
  1671. /// </summary>
  1672. /// 创建时间: 2022-11-05 最后一次修改时间: 2022-11-05
  1673. void RemoveHeadTab()
  1674. {
  1675. int iMin = 100000000;
  1676. for (T& s : *this) {
  1677. if (s.Length > 0)
  1678. {
  1679. int iCount = gs.s_headTabCount(s.Data);
  1680. if (iCount < iMin) { iMin = iCount; }
  1681. //log::d("iCount=" + iCount.ToString(), s);
  1682. }
  1683. }
  1684. //log::d("iMin=" + iMin.ToString());
  1685. if (iMin > 0)
  1686. {
  1687. for (T& s : *this) {
  1688. s = s.SubStr(iMin, s.Length - iMin);
  1689. }
  1690. }
  1691. }
  1692. //-----------------------------------------------------------------------虚函数
  1693. virtual bool Add(const T& item) override
  1694. {
  1695. //_cout << item << "\n";
  1696. return _DList<T>::Add(item);
  1697. }
  1698. void Add(const _StrList<T>& ls) //覆盖 父类重载函数 virtual bool Add(const T& item);
  1699. {
  1700. _DListNode<T>* pNode = ls._First;
  1701. while (pNode != null)
  1702. {
  1703. Add(pNode->Data);
  1704. pNode = pNode->Next;
  1705. }
  1706. }
  1707. bool Add(const T& str, int nStartPos, int nEndPos)
  1708. {
  1709. if (str.Length == 0 || nEndPos - nStartPos < 0)
  1710. {
  1711. Add(T());
  1712. }
  1713. else {
  1714. int nLength = nEndPos - nStartPos + 1;
  1715. /*
  1716. _Mem<_char> m(nLength + 1);
  1717. for (int i = 0; i < nLength; ++i)
  1718. {
  1719. m.Data[i] = pStr[nStartPos + i];
  1720. }
  1721. m.Data[nLength] = 0;
  1722. */
  1723. Add(str.SubStr(nStartPos, nLength));
  1724. }
  1725. return false;
  1726. }
  1727. _string ToSplitString(const _string& sSplitString) const override
  1728. {
  1729. /*
  1730. * auto dn = this->_First;
  1731. T sResult;
  1732. while (dn != this->_Last)
  1733. {
  1734. sResult.std_append(dn->Data);
  1735. sResult.std_append(sConnector);
  1736. dn = dn->Next;
  1737. }
  1738. if (this->_Last != null)
  1739. {
  1740. sResult.std_append(dn->Data);
  1741. }
  1742. char c = '\n';
  1743. sResult.std_append(c );
  1744. return sResult;
  1745. */
  1746. return _DList<T>::ToSplitString(sSplitString);
  1747. }
  1748. };
  1749. /// <summary>
  1750. /// 不重复的字符串列表
  1751. /// </summary>
  1752. /// <typeparam name="T"></typeparam>
  1753. /// 创建时间: 2023-05-11 最后一次修改时间:2023-05-11
  1754. template<class T>
  1755. class _UStrList : public _StrList<T>
  1756. {
  1757. public:
  1758. /// <summary>
  1759. /// 加入一个串,如果这个串存在,则把这项移到最后。
  1760. /// </summary>
  1761. /// <param name="item"></param>
  1762. /// 创建时间: ????-??-?? 最后一次修改时间:2023-05-11 (已测试)
  1763. bool Add(const T& item)override
  1764. {
  1765. bool bFind = false;
  1766. _DListNode<T>* dnTemp = this->_First;
  1767. while (dnTemp != null)
  1768. {
  1769. if (dnTemp->Data == item)
  1770. {
  1771. this->MoveLast(dnTemp);
  1772. return false;
  1773. }
  1774. dnTemp = dnTemp->Next;
  1775. }
  1776. _StrList<T>::Add(item);
  1777. return true;
  1778. }
  1779. };
  1780. /// <summary>
  1781. /// 值都是唯一的字符串列表, Case Insensitive(不区分大小写)
  1782. /// </summary>
  1783. template<class T>
  1784. class _UStrListCI : public _StrList<T>
  1785. {
  1786. public:
  1787. /// <summary>
  1788. /// 加入一个串,如果这个串存在,则把这项移到最后。
  1789. /// </summary>
  1790. /// <param name="item"></param>
  1791. /// 创建时间: ????-??-?? 最后一次修改时间:2022-02-18
  1792. bool Add(const T& item)override
  1793. {
  1794. bool bFind = false;
  1795. _DListNode<T>* dnTemp = this->_First;
  1796. while (dnTemp != null)
  1797. {
  1798. if (dnTemp->Data.CSharp_ToLower() == item.CSharp_ToLower())
  1799. {
  1800. this->MoveLast(dnTemp);
  1801. return false;
  1802. }
  1803. dnTemp = dnTemp->Next;
  1804. }
  1805. _StrList<T>::Add(item);
  1806. return true;
  1807. }
  1808. /*
  1809. /// <summary>
  1810. /// 返回前面一个值
  1811. /// </summary>
  1812. /// <param name="tCurrValue"></param>
  1813. /// <returns></returns>
  1814. T& GetForward(T& sCurr)
  1815. {
  1816. int iIndex = BinarySearch(sCurr);
  1817. if (iIndex != -1)
  1818. {
  1819. if (iIndex + 1 < _Count)
  1820. return this[iIndex + 1];
  1821. }
  1822. return null;
  1823. }
  1824. /// <summary>
  1825. /// 返回后面的一个值
  1826. /// </summary>
  1827. /// <param name="sCurr"></param>
  1828. /// <returns></returns>
  1829. T& GetBack(T& sCurr)
  1830. {
  1831. int iIndex = BinarySearch(sCurr);
  1832. if (iIndex != -1)
  1833. {
  1834. if (iIndex - 1 < _Count && iIndex - 1 >= 0)
  1835. return this[iIndex - 1];
  1836. }
  1837. return null;
  1838. }
  1839. */
  1840. };
  1841. /// <summary>
  1842. /// 已排序好的字符串列表
  1843. /// </summary>
  1844. template<class T>
  1845. class _SStrList : public _StrList<T>
  1846. {
  1847. public:
  1848. _SStrList(const _SortOrder so = _SortOrder::s_Minmax)
  1849. {
  1850. this->_so = so;
  1851. if (this->_so == _SortOrder::s_null)
  1852. {
  1853. throw _t("排序不能为空!");
  1854. }
  1855. }
  1856. //-------------------------------------------------------------------------------重写
  1857. /// <summary>
  1858. /// 快速添加字符串,差不多用了8个小时(两天),才写成。
  1859. /// </summary>
  1860. /// <param name="s"></param>
  1861. /// <returns></returns>
  1862. bool Add(const T& item) override
  1863. {
  1864. if (this->_Count < 3)
  1865. {
  1866. bool bInsert = false;
  1867. _DListNode<T>* ld = this->_First;
  1868. while (ld != null)
  1869. {
  1870. if (this->_so == _SortOrder::s_Maxmin)
  1871. {
  1872. if (item >= ld->Data)
  1873. {
  1874. _StrList<T>::InserNodeFront(ld, item); bInsert = true;
  1875. break;
  1876. }
  1877. }
  1878. else
  1879. {
  1880. if (item <= ld->Data)
  1881. {
  1882. _StrList<T>::InserNodeFront(ld, item); bInsert = true; break;
  1883. }
  1884. }
  1885. ld = ld->Next;
  1886. }
  1887. if (!bInsert) _StrList<T>::Add(item);
  1888. return true;
  1889. }
  1890. int nPos = this->_Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  1891. int nLeft = 0; //左边远素
  1892. int nRight = this->_Count - 1; //右边远素
  1893. if (this->_so == _SortOrder::s_Maxmin)
  1894. {
  1895. _DListNode<T>* ld = null;
  1896. while (nRight >= 0 && nLeft >= 0)
  1897. {
  1898. ld = this->IndexOfNode(nPos);
  1899. if (item >= ld->Data)
  1900. {
  1901. if (nRight == nLeft || nPos == nLeft)
  1902. {
  1903. this->InserNodeFront(ld, item);
  1904. return true;
  1905. }
  1906. nRight = nPos - 1;
  1907. }
  1908. else
  1909. {
  1910. if (nRight == nLeft || nPos == nRight)
  1911. {
  1912. this->InserNodeBack(ld, item);
  1913. return true;
  1914. }
  1915. nLeft = nPos + 1;
  1916. }
  1917. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1918. }
  1919. }
  1920. else
  1921. {
  1922. _DListNode<T>* ld = null;
  1923. while (nRight >= 0 && nLeft >= 0)
  1924. {
  1925. ld = this->IndexOfNode(nPos);
  1926. if (item <= ld->Data)
  1927. {
  1928. if (nRight == nLeft || nPos == nLeft)
  1929. {
  1930. this->InserNodeFront(ld, item);
  1931. return true;
  1932. }
  1933. nRight = nPos - 1;
  1934. }
  1935. else
  1936. {
  1937. if (nRight == nLeft || nPos == nRight)
  1938. {
  1939. this->InserNodeBack(ld, item);
  1940. return true;
  1941. }
  1942. nLeft = nPos + 1;
  1943. }
  1944. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1945. }
  1946. }
  1947. return true;
  1948. }
  1949. /// <summary>
  1950. /// 确定某元素是否在列表中
  1951. /// </summary>
  1952. /// <param name="item">查找的对象。对于引用类型,该值可以为 null。</param>
  1953. /// <returns>如果在列表中找到 item,则为 true,否则为 false。</returns>
  1954. bool Contains(const T& item) override
  1955. {
  1956. if (this->_Count == 0) return false;
  1957. if (this->_Count == 1) return this->_First->Data == item;
  1958. if (this->_Count == 2) return this->_First->Data == item || this->_First->Next->Data == item;
  1959. int nPos = (int)this->_Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  1960. int nLeft = 0; //左边远素
  1961. int nRight = (int)this->_Count - 1; //右边远素
  1962. _DListNode<T>* ld = null;
  1963. if (this->_so == _SortOrder::s_Maxmin)
  1964. {
  1965. while (nRight >= 0 && nLeft >= 0)
  1966. {
  1967. ld = this->IndexOfNode(nPos);
  1968. int iCom = item.CompareTo(ld->Data);
  1969. if (iCom > 0)
  1970. {
  1971. if (nRight == nLeft || nPos == nLeft)
  1972. {
  1973. return false;
  1974. }
  1975. nRight = nPos - 1;
  1976. }
  1977. else if (iCom < 0)
  1978. {
  1979. if (nRight == nLeft || nPos == nRight)
  1980. {
  1981. return false;
  1982. }
  1983. nLeft = nPos + 1;
  1984. }
  1985. else
  1986. {
  1987. return true;
  1988. }
  1989. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1990. }
  1991. }
  1992. else
  1993. {
  1994. while (nRight >= 0 && nLeft >= 0)
  1995. {
  1996. ld = this->IndexOfNode(nPos);
  1997. int iCom = item.CompareTo(ld->Data);
  1998. if (iCom < 0)
  1999. {
  2000. if (nRight == nLeft || nPos == nLeft)
  2001. {
  2002. return false;
  2003. }
  2004. nRight = nPos - 1;
  2005. }
  2006. else if (iCom > 0)
  2007. {
  2008. if (nRight == nLeft || nPos == nRight)
  2009. {
  2010. return false;
  2011. }
  2012. nLeft = nPos + 1;
  2013. }
  2014. else
  2015. {
  2016. return true;
  2017. }
  2018. nPos = nLeft + (nRight - nLeft + 1) / 2;
  2019. }
  2020. }
  2021. return false;
  2022. }
  2023. };
  2024. /// <summary>
  2025. /// 值都是唯一的字符串列表,且已排好序,区分大小写
  2026. /// </summary>
  2027. template<class T>
  2028. class _SUStrList : public _SStrList<T>
  2029. {
  2030. public:
  2031. bool Add(const T& item)override
  2032. {
  2033. if (this->Contains(item))
  2034. return false;
  2035. return _SStrList<T>::Add(item);
  2036. }
  2037. _SUStrList(_SortOrder so = _SortOrder::s_Minmax) : _SStrList<T>(so)
  2038. {
  2039. }
  2040. };
  2041. /// <summary>
  2042. /// UStringListCI_值都是唯一,且已排序的字符串列表,不区分大小写
  2043. /// </summary>
  2044. template<class T>
  2045. class _SUStrListUI : public _SUStrList<T>
  2046. {
  2047. public:
  2048. _SUStrListUI(_SortOrder st) : _SUStrList<T>(st)
  2049. {
  2050. }
  2051. /// <summary>
  2052. /// 确定某元素是否在列表中
  2053. /// </summary>
  2054. /// <param name="item">查找的对象。对于引用类型,该值可以为 null。</param>
  2055. /// <returns>如果在列表中找到 item,则为 true,否则为 false。</returns>
  2056. bool Contains(const T& item) override
  2057. {
  2058. if (this->_Count == 0) return false;
  2059. if (this->_Count == 1) return this->_First->Data.ToLower().CompareTo(item.ToLower()) == 0;
  2060. if (this->_Count == 2) return this->_First->Data.ToLower().CompareTo(item.ToLower()) == 0 || this->_First->Next->Data.ToLower().CompareTo(item.ToLower()) == 0;
  2061. int nPos = (int)this->_Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  2062. int nLeft = 0; //左边远素
  2063. int nRight = (int)this->_Count - 1; //右边远素
  2064. _DListNode<T>* ld = null;
  2065. if (this->_so == _SortOrder::s_Maxmin)
  2066. {
  2067. while (nRight >= 0 && nLeft >= 0)
  2068. {
  2069. ld = this->IndexOfNode(nPos);
  2070. int iCom = item.ToLower().CompareTo(ld->Data.ToLower());
  2071. if (iCom > 0)
  2072. {
  2073. if (nRight == nLeft || nPos == nLeft)
  2074. {
  2075. return false;
  2076. }
  2077. nRight = nPos - 1;
  2078. }
  2079. else if (iCom < 0)
  2080. {
  2081. if (nRight == nLeft || nPos == nRight)
  2082. {
  2083. return false;
  2084. }
  2085. nLeft = nPos + 1;
  2086. }
  2087. else
  2088. {
  2089. return true;
  2090. }
  2091. nPos = nLeft + (nRight - nLeft + 1) / 2;
  2092. }
  2093. }
  2094. else
  2095. {
  2096. while (nRight >= 0 && nLeft >= 0)
  2097. {
  2098. ld = this->IndexOfNode(nPos);
  2099. int iCom = item.ToLower().CompareTo(ld->Data.ToLower());
  2100. if (iCom < 0)
  2101. {
  2102. if (nRight == nLeft || nPos == nLeft)
  2103. {
  2104. return false;
  2105. }
  2106. nRight = nPos - 1;
  2107. }
  2108. else if (iCom > 0)
  2109. {
  2110. if (nRight == nLeft || nPos == nRight)
  2111. {
  2112. return false;
  2113. }
  2114. nLeft = nPos + 1;
  2115. }
  2116. else
  2117. {
  2118. return true;
  2119. }
  2120. nPos = nLeft + (nRight - nLeft + 1) / 2;
  2121. }
  2122. }
  2123. return false;
  2124. }
  2125. };
  2126. _LF_END_
  2127. #endif

2. C#版

  1. /*****************************************************************************
  2. 创建时间 : 2006年12月19日
  3. 文件名 : List_.cs
  4. 作者 : 李锋
  5. Email : ruizhilf@139.com
  6. 联系电话 : 13828778863,25722732
  7. ----------------------最后一次修改时间:2022年10月10日
  8. *******************************************************************************/
  9. using System;
  10. using System.Collections.Generic;
  11. using System.Collections;
  12. using System.Text.RegularExpressions;
  13. using System.IO;
  14. using System.Diagnostics;
  15. namespace lf
  16. {
  17. #region DListNote_(双向链表的节点)
  18. /// <summary>
  19. /// 双向链表的节点
  20. /// </summary>
  21. /// <typeparam name="T"></typeparam>
  22. public class DListNote_<T>
  23. {
  24. /// <summary>
  25. /// 节点数据
  26. /// </summary>
  27. public T Data;
  28. /// <summary>
  29. /// 前一个节点
  30. /// </summary>
  31. public DListNote_<T> Prev;
  32. /// <summary>
  33. /// 下一个节点
  34. /// </summary>
  35. public DListNote_<T> Next;
  36. public DListNote_(T aData)
  37. {
  38. Data = aData;
  39. Prev = null;
  40. Next = null;
  41. }
  42. }
  43. #endregion
  44. #region Sortord_( 排序方式)
  45. /// <summary>
  46. /// 排序顺序
  47. /// </summary>
  48. public enum Sortord_
  49. {
  50. s_min_max, //从小到大
  51. s_max_min, //从大到小
  52. s_null //无排序顺序
  53. }
  54. #endregion
  55. #region //====================================================== DList_(双向链表)
  56. /// <summary>
  57. /// 双向链表
  58. /// </summary>
  59. /// <typeparam name="T"></typeparam>
  60. public class DList_<T> : IEnumerable
  61. {
  62. protected DListNote_<T> _First; //第一个节点
  63. protected DListNote_<T> _Last; //最后一个节点
  64. protected int _Count; //节点个数
  65. protected Sortord_ _sortord; //排序顺序
  66. //------------------------------------------------------------------------------------------属性
  67. /// <summary>
  68. /// 实际包含的元素数
  69. /// </summary>
  70. public int Count
  71. {
  72. get
  73. {
  74. return _Count;
  75. }
  76. }
  77. /// <summary>
  78. /// 获取或设置指定索引处的元素
  79. /// </summary>
  80. /// <param name="index">要获得或设置的元素从零开始的索引</param>
  81. /// <returns>指定索引处的元素</returns>
  82. public virtual T this[int index]
  83. {
  84. get
  85. {
  86. return IndexOfNote(index).Data;
  87. }
  88. set
  89. {
  90. IndexOfNote(index).Data = value;
  91. }
  92. }
  93. //---------------------------------------------------------------------------------构造与析构
  94. //---------------------------------------------------------------------------------运算符重载
  95. /// <summary>
  96. ///
  97. /// </summary>
  98. /// <param name="dLeft"></param>
  99. /// <param name="dlRight"></param>
  100. /// <returns></returns>
  101. /// 创建时间: 2021-11-07 最后一次修改时间:2021-11-07
  102. public static DList_<T> operator +(DList_<T> dLeft, DList_<T> dlRight)
  103. {
  104. /*
  105. DList_<T> dlResult = new DList_<T> ();
  106. dlResult.Add(dLeft);
  107. dlResult.Add(dlRight);
  108. return dlResult;
  109. */
  110. return new DList_<T> { dLeft, dlRight };
  111. }
  112. //---------------------------------------------------------------------------------功能函数
  113. /// <summary>
  114. /// 将指定集合的元素添加到末尾
  115. /// </summary>
  116. /// <param name="item">要添加到的末尾处的对象。对于引用类型,该值可以为 null</param>
  117. /// <returns>如成功,返回真,否则返回假</returns>
  118. public virtual void Add(T item)
  119. {
  120. if (_Count == 0)
  121. {
  122. _First = new DListNote_<T>(item);
  123. _First.Next = null;
  124. _First.Prev = null;
  125. _Last = _First;
  126. }
  127. else
  128. {
  129. DListNote_<T> pNew = new DListNote_<T>(item);
  130. pNew.Next = null;
  131. pNew.Prev = _Last;
  132. _Last.Next = pNew;
  133. _Last = pNew;
  134. }
  135. ++_Count;
  136. _sortord = Sortord_.s_null; //要重新排序
  137. }
  138. /// <summary>
  139. ///
  140. /// </summary>
  141. /// <param name="nIndex"></param>
  142. /// <param name="item"></param>
  143. /// <returns></returns>
  144. /// 创建时间: 2022-08-11 最后一次修改时间:2022-08-12
  145. public virtual void Insert(int nIndex, T item)
  146. {
  147. if ((uint)nIndex > (uint)_Count)
  148. {
  149. throw new Exception("DList_.Insert 插入位置错误!");
  150. }
  151. if (nIndex == 0)
  152. {
  153. if(_First != null)
  154. {
  155. DListNote_<T> dnNew = new DListNote_<T>(item);
  156. _First.Prev = dnNew;
  157. dnNew.Next = _First;
  158. _First = dnNew;
  159. ++_Count;
  160. _sortord = Sortord_.s_null;
  161. }
  162. else
  163. {
  164. Add(item);
  165. }
  166. }
  167. else if(nIndex == _Count)
  168. {
  169. Add(item);
  170. }
  171. else
  172. {
  173. DListNote_<T> dnNew = new DListNote_<T>(item);
  174. DListNote_<T> dnNext = IndexOfNote(nIndex);
  175. DListNote_<T> dnPrev = dnNext.Prev;
  176. dnNew.Next = dnNext;
  177. dnNew.Prev = dnPrev;
  178. dnNext.Prev = dnNew;
  179. dnPrev.Next = dnNew;
  180. ++_Count;
  181. _sortord = Sortord_.s_null;
  182. }
  183. }
  184. public void Add(DList_<T> dList)
  185. {
  186. if (dList == null)
  187. {
  188. throw new System.Exception("DList_<T>.Add中参数dList==null");
  189. }
  190. DListNote_<T> ld = dList._First;
  191. while (ld != null)
  192. {
  193. Add(ld.Data);
  194. ld = ld.Next;
  195. }
  196. }
  197. public override string ToString()
  198. {
  199. string sResult = "";
  200. DListNote_<T> dnNote = _First;
  201. while (dnNote != null)
  202. {
  203. sResult += dnNote.Data.ToString();
  204. sResult += "\n";
  205. dnNote = dnNote.Next;
  206. }
  207. return sResult;
  208. }
  209. public string ToString(string sSplit)
  210. {
  211. string sResult = "";
  212. DListNote_<T> dnNote = _First;
  213. while (dnNote != null)
  214. {
  215. sResult += dnNote.Data.ToString();
  216. if(dnNote != Last)
  217. sResult += sSplit;
  218. dnNote = dnNote.Next;
  219. }
  220. return sResult;
  221. }
  222. /// <summary>
  223. /// 使用指定的比较器在整个已排序的 中搜索元素,并返回该元素从零开始的索引
  224. /// </summary>
  225. /// <param name="item">要定位的对象。对于引用类型,该值可以为 null。</param>
  226. /// <returns>如果找到 item,则为已排序的 的从零开始的索引;否则为-1; </returns>
  227. public int BinarySearch(T item)
  228. {
  229. switch (_sortord)
  230. {
  231. case Sortord_.s_max_min:
  232. {
  233. if (Count == 0)
  234. {
  235. return -1;
  236. }
  237. if (Count == 1)
  238. {
  239. return (_First.Data as IComparable).CompareTo(item) == 0 ? 0 : -1;
  240. }
  241. if (Count == 2)
  242. {
  243. if( (_First.Data as IComparable).CompareTo(item) == 0) return 0;
  244. if ((_First.Next.Data as IComparable).CompareTo(item) == 0) return 1;
  245. return -1;
  246. }
  247. int nPos = (int)Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  248. int nLeft = 0; //左边远素
  249. int nRight = (int)Count - 1; //右边远素
  250. DListNote_<T> ld;
  251. while (nRight >= 0 && nLeft >= 0)
  252. {
  253. ld = IndexOfNote(nPos);
  254. int iCom = (item as IComparable).CompareTo(ld.Data);
  255. if (iCom > 0)
  256. {
  257. if (nRight == nLeft || nPos == nLeft)
  258. {
  259. return -1;
  260. }
  261. nRight = nPos - 1;
  262. }
  263. else if (iCom < 0)
  264. {
  265. if (nRight == nLeft || nPos == nRight)
  266. {
  267. return -1;
  268. }
  269. nLeft = nPos + 1;
  270. }
  271. else
  272. {
  273. return nPos;
  274. }
  275. nPos = nLeft + (nRight - nLeft + 1) / 2;
  276. }
  277. break;
  278. }
  279. case Sortord_.s_min_max:
  280. {
  281. if (Count == 0)
  282. {
  283. return -1;
  284. }
  285. if (Count == 1)
  286. {
  287. return (_First.Data as IComparable).CompareTo(item) == 0 ? 0 : -1;
  288. }
  289. if (Count == 2)
  290. {
  291. if ((_First.Data as IComparable).CompareTo(item) == 0) return 0;
  292. if ((_First.Next.Data as IComparable).CompareTo(item) == 0) return 1;
  293. return -1;
  294. }
  295. int nPos = (int)Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  296. int nLeft = 0; //左边远素
  297. int nRight = (int)Count - 1; //右边远素
  298. DListNote_<T> ld = null;
  299. while (nRight >= 0 && nLeft >= 0)
  300. {
  301. ld = IndexOfNote(nPos);
  302. int iCom = (item as IComparable).CompareTo(ld.Data);
  303. if (iCom < 0)
  304. {
  305. if (nRight == nLeft || nPos == nLeft)
  306. {
  307. return -1;
  308. }
  309. nRight = nPos - 1;
  310. }
  311. else if (iCom > 0)
  312. {
  313. if (nRight == nLeft || nPos == nRight)
  314. {
  315. return -1;
  316. }
  317. nLeft = nPos + 1;
  318. }
  319. else
  320. {
  321. return nPos;
  322. }
  323. nPos = nLeft + (nRight - nLeft + 1) / 2;
  324. }
  325. break;
  326. }
  327. case Sortord_.s_null:
  328. {
  329. DListNote_<T> pNote = _First;
  330. int iCount = 0;
  331. while (pNote != null)
  332. {
  333. if (pNote.Data.Equals(item))
  334. {
  335. return iCount;
  336. }
  337. pNote = pNote.Next;
  338. ++iCount;
  339. }
  340. break;
  341. }
  342. default:
  343. {
  344. return -1;
  345. }
  346. }
  347. return -1;
  348. }
  349. /**
  350. * 功能:清空所有元素的所有数据,并清空链表
  351. * 创建时间:????/??/??
  352. * 最后一次修改时间:2022-07-02
  353. */
  354. public void Clear()
  355. {
  356. _Count = 0;
  357. DListNote_<T> pTemp1 = _First;
  358. while (pTemp1 != null)
  359. {
  360. DListNote_<T> pTemp2 = pTemp1.Next;
  361. pTemp1.Data = default(T);
  362. pTemp1.Next = null;
  363. pTemp1.Prev = null;
  364. pTemp1 = pTemp2;
  365. }
  366. _First = null;
  367. _Last = null;
  368. }
  369. /// <summary>
  370. /// 确定某元素是否在列表中
  371. /// </summary>
  372. /// <param name="item">查找的对象。对于引用类型,该值可以为 null。</param>
  373. /// <returns>如果在列表中找到 item,则为 true,否则为 false。</returns>
  374. public virtual bool Contains(T item)
  375. {
  376. return BinarySearch(item) != -1;
  377. }
  378. /// <summary>
  379. /// 复制一个链表,清除原来链表的数据
  380. /// </summary>
  381. /// <param name="ld"></param>
  382. public void CopyFrom(DList_<T> ld)
  383. {
  384. if (!this.Equals(ld))
  385. {
  386. Clear();
  387. DListNote_<T> ldItem = ld._First;
  388. while (ldItem != null)
  389. {
  390. Add(ldItem.Data);
  391. ldItem = ldItem.Next;
  392. }
  393. }
  394. }
  395. /*
  396. public int IndexOf(T item)
  397. {
  398. return -1;
  399. }
  400. public int IndexOf(T item, int index)
  401. {
  402. return -1;
  403. }
  404. public void Insert(int index, T item)
  405. {
  406. }
  407. public int LastIndexOf(T item)
  408. {
  409. return -1;
  410. }
  411. public int LastIndexOf(T item, int index, int Count)
  412. {
  413. return -1;
  414. }
  415. */
  416. /// <summary>
  417. /// 移除指定索引处的元素
  418. /// </summary>
  419. /// <param name="iIndex">要移除的元素的从零开始的索引。</param>
  420. /// <returns>成功返回true,否则返回false</returns>
  421. public bool RemoveAt(int iIndex)
  422. {
  423. if (iIndex < 0 || iIndex + 1 > _Count) { return false; }
  424. DListNote_<T> pNode = _First;
  425. int iCount = 0;
  426. while (pNode != null)
  427. {
  428. if (iCount == iIndex)
  429. {
  430. if (pNode == _First)
  431. {
  432. if (_First.Next == null) //只有一个
  433. {
  434. Clear();
  435. return true;
  436. }
  437. else
  438. {
  439. _First = _First.Next;
  440. _First.Prev = null;
  441. --_Count;
  442. return true;
  443. }
  444. }
  445. else if (pNode == _Last)
  446. {
  447. if (_Last.Prev == null)
  448. {
  449. Clear();
  450. return true;
  451. }
  452. else
  453. {
  454. _Last = _Last.Prev;
  455. _Last.Next = null;
  456. --_Count;
  457. return true;
  458. }
  459. }
  460. else
  461. {
  462. pNode.Prev.Next = pNode.Next;
  463. pNode.Next.Prev = pNode.Prev;
  464. pNode = null;
  465. --_Count;
  466. return true;
  467. }
  468. }
  469. pNode = pNode.Next;
  470. ++iCount;
  471. }
  472. return false;
  473. }
  474. /// <summary>
  475. /// 反向排列链表
  476. /// </summary>
  477. /// 创建时间: 2022-04-20 最后一次修改时间:2022-04-20
  478. public virtual void Reverse()
  479. {
  480. DListNote_<T> dnTemp = First;
  481. while(dnTemp != null)
  482. {
  483. LMath.Swap(ref dnTemp.Next, ref dnTemp.Prev);
  484. dnTemp = dnTemp.Prev;
  485. }
  486. LMath.Swap(ref _First, ref _Last);
  487. }
  488. /// <summary>
  489. /// 添加一个元素,并把它放在首位,其它元素后移,如棵后面的元素删除,总无素个数不变,如果无素个数为零,则添加一个无素。
  490. /// </summary>
  491. /// <param name="Item"></param>
  492. /// <param name="bRemoveLast"></param>
  493. /// 创建时间: 2022-04-19 最后一次修改时间:2022-04-19
  494. public void StackPush(T Item, bool bRemoveLast = false){
  495. if (_Count == 0){
  496. Add(Item);
  497. }
  498. else if (_Count == 1){
  499. if (bRemoveLast){
  500. _First.Data = Item;
  501. }
  502. else{
  503. //把无素放在最前
  504. DListNote_<T> dnNew = new DListNote_<T>(Item);
  505. _First.Prev = dnNew;
  506. dnNew.Next = _First;
  507. _First = dnNew;
  508. ++_Count;
  509. }
  510. }
  511. else{
  512. if (bRemoveLast){
  513. //删除最后一个元素
  514. _Last = _Last.Prev;
  515. _Last.Next = null;
  516. //把无素放在最前
  517. DListNote_<T> dnNew = new DListNote_<T>(Item);
  518. _First.Prev = dnNew;
  519. dnNew.Next = _First;
  520. dnNew.Prev = null;
  521. _First = dnNew;
  522. }
  523. else {
  524. //把无素放在最前
  525. DListNote_<T> dnNew = new DListNote_<T>(Item);
  526. _First.Prev = dnNew;
  527. dnNew.Next = _First;
  528. dnNew.Prev = null;
  529. _First = dnNew;
  530. ++_Count;
  531. }
  532. }
  533. }
  534. /// <summary>
  535. /// 删除第一个元素,出栈
  536. /// </summary>
  537. /// 创建时间: 2022-04-19 最后一次修改时间:2022-04-19
  538. public void StackPop(){ RemoveAt(0); }
  539. /// <summary>
  540. /// 转换成数组
  541. /// </summary>
  542. /// <returns></returns>
  543. public T[] ToArray()
  544. {
  545. T[] aResult = new T[Count];
  546. int n = 0;
  547. DListNote_<T> pNoteTemp = _First;
  548. while (pNoteTemp != null)
  549. {
  550. aResult[n++] = pNoteTemp.Data;
  551. pNoteTemp = pNoteTemp.Next;
  552. }
  553. return aResult;
  554. }
  555. /// <summary>
  556. /// 交换两个节点的数据
  557. /// </summary>
  558. /// <param name="nIndex1"></param>
  559. /// <param name="nIndex2"></param>
  560. /// <returns></returns>
  561. protected virtual bool swapNoteData(int iIndex1, int iIndex2)
  562. {
  563. DListNote_<T> pNote1, pNote2;
  564. pNote1 = IndexOfNote(iIndex1);
  565. pNote2 = IndexOfNote(iIndex2);
  566. if (!(pNote1 != null && pNote2 != null))
  567. {
  568. return false;
  569. }
  570. T ptmp = pNote1.Data;
  571. pNote1.Data = pNote2.Data;
  572. pNote2.Data = ptmp;
  573. return true;
  574. }
  575. /// <summary>
  576. /// 选择排序可以说是最简单的一种排序方法:
  577. /// 1.找到数组中最小的那个元素
  578. /// 2.将最小的这个元素和数组中第一个元素交换位置
  579. /// 3.在剩下的元素中找到最小的的元素,与数组第二个元素交换位置
  580. /// 重复以上步骤,即可以得到有序数组。
  581. /// </summary>
  582. public virtual void sort_selection(Sortord_ sortord)
  583. {
  584. if (_Count == 0 || _Count == 1) return;
  585. //is关键字用于检查对象是否与给定类型兼容。注意了,这里is并不是“是”的意思,而是“兼容”。
  586. if (!(_First.Data is IComparable)) // 判断是否具有IComparable接口,以确定是否存在CompareTo()方法
  587. {
  588. throw new Exception("没有IComparable接口");
  589. }
  590. DListNote_<T> min = _First, tmp = _First.Next;
  591. if (sortord == Sortord_.s_min_max)
  592. {
  593. while (min.Next != null)
  594. {
  595. while (tmp != null)
  596. {
  597. if ((tmp.Data as IComparable).CompareTo(min.Data) < 0) //交换位置
  598. {
  599. T pt = tmp.Data;
  600. tmp.Data = min.Data;
  601. min.Data = pt;
  602. }
  603. tmp = tmp.Next;
  604. }
  605. min = min.Next;
  606. tmp = min.Next;
  607. }
  608. }
  609. else
  610. {
  611. while (min.Next != null)
  612. {
  613. while (tmp != null)
  614. {
  615. if ((tmp.Data as IComparable).CompareTo(min.Data) > 0)
  616. {
  617. T pt = tmp.Data;
  618. tmp.Data = min.Data;
  619. min.Data = pt;
  620. }
  621. tmp = tmp.Next;
  622. }
  623. min = min.Next;
  624. tmp = min.Next;
  625. }
  626. }
  627. _sortord = sortord; //已排序
  628. }
  629. /// <summary>
  630. /// 返回索引的节点,从零开始
  631. /// </summary>
  632. /// <param name="nPos"></param>
  633. /// <returns></returns>
  634. public virtual DListNote_<T> IndexOfNote(int iPos)
  635. {
  636. if (iPos >= _Count || iPos < 0) throw new System.Exception("DListNote_<T>.IndexOfNote 错误索引: " + iPos.ToString() + "!");
  637. uint nindex = 0;
  638. if (iPos > _Count / 2)
  639. {
  640. DListNote_<T> pNote = _Last;
  641. while (pNote != null)
  642. {
  643. if (nindex++ == _Count - iPos - 1){ return pNote;}
  644. pNote = pNote.Prev;
  645. }
  646. }
  647. else
  648. {
  649. DListNote_<T> pNote = _First;
  650. while (pNote != null)
  651. {
  652. if (nindex++ == iPos)
  653. {
  654. return pNote;
  655. }
  656. pNote = pNote.Next;
  657. }
  658. }
  659. return null;
  660. }
  661. /// <summary>
  662. /// 在结点pListItem前面插入一个结点,成功,返回新的结点,否则返回0
  663. /// </summary>
  664. /// <param name="pListItem"></param>
  665. /// <param name="pData"></param>
  666. /// <returns></returns>
  667. protected virtual DListNote_<T> InserNoteFront(DListNote_<T> pListItem, T pData)
  668. {
  669. if (pListItem == null)
  670. {
  671. throw new System.Exception("函数提示:pListItem = null");
  672. }
  673. DListNote_<T> pNote = new DListNote_<T>(pData);
  674. //pNote
  675. pNote.Next = pListItem;
  676. pNote.Prev = pListItem.Prev;
  677. //--pListItem->Prev
  678. if (pListItem.Prev != null)
  679. {
  680. pListItem.Prev.Next = pNote;
  681. }
  682. else
  683. {
  684. _First = pNote;
  685. }
  686. //pListItem
  687. pListItem.Prev = pNote;
  688. ++_Count;
  689. return pNote;
  690. }
  691. /// <summary>
  692. /// 在结点pListItem后面插入一个结点,成功,返回新的结点,否则返回0;
  693. /// </summary>
  694. /// <param name="pListItem"></param>
  695. /// <param name="pData"></param>
  696. /// <returns></returns>
  697. protected virtual DListNote_<T> InserNoteBack(DListNote_<T> pListItem, T pData)
  698. {
  699. if (pListItem == null) return null;
  700. DListNote_<T> pNote = new DListNote_<T>(pData);
  701. //pNote
  702. pNote.Prev = pListItem;
  703. pNote.Next = pListItem.Next;
  704. //pListItem->Next
  705. if (pListItem.Next != null)
  706. {
  707. pListItem.Next.Prev = pNote;
  708. }
  709. else
  710. {
  711. _Last = pNote;
  712. }
  713. //--pListItem
  714. pListItem.Next = pNote;
  715. ++_Count;
  716. return pNote;
  717. }
  718. /// <summary>
  719. /// 找查一个项,而不是节点,返回的这个节点相当于指针。
  720. /// </summary>
  721. /// <param name="pData">项值</param>
  722. /// <returns></returns>
  723. public DListNote_<T> FindNoteItem(T item)
  724. {
  725. switch (_sortord)
  726. {
  727. case Sortord_.s_max_min:
  728. {
  729. if (Count == 0)
  730. {
  731. return null;
  732. }
  733. if (Count == 1)
  734. {
  735. return (_First.Data as IComparable).CompareTo(item) == 0 ? _First : null;
  736. }
  737. if (Count == 2)
  738. {
  739. if ((_First.Data as IComparable).CompareTo(item) == 0) return _First;
  740. if ((_First.Next.Data as IComparable).CompareTo(item) == 0) return _First.Next;
  741. return null;
  742. }
  743. int nPos = (int)Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  744. int nLeft = 0; //左边远素
  745. int nRight = (int)Count - 1; //右边远素
  746. DListNote_<T> ld = null;
  747. while (nRight >= 0 && nLeft >= 0)
  748. {
  749. ld = IndexOfNote(nPos);
  750. int iCom = (item as IComparable).CompareTo(ld.Data);
  751. if (iCom > 0)
  752. {
  753. if (nRight == nLeft || nPos == nLeft)
  754. {
  755. return null;
  756. }
  757. nRight = nPos - 1;
  758. }
  759. else if (iCom < 0)
  760. {
  761. if (nRight == nLeft || nPos == nRight)
  762. {
  763. return null;
  764. }
  765. nLeft = nPos + 1;
  766. }
  767. else
  768. {
  769. return ld;
  770. }
  771. nPos = nLeft + (nRight - nLeft + 1) / 2;
  772. }
  773. break;
  774. }
  775. case Sortord_.s_min_max:
  776. {
  777. if (Count == 0)
  778. {
  779. return null;
  780. }
  781. if (Count == 1)
  782. {
  783. return (_First.Data as IComparable).CompareTo(item) == 0 ? _First : null;
  784. }
  785. if (Count == 2)
  786. {
  787. if ((_First.Data as IComparable).CompareTo(item) == 0) return _First;
  788. if ((_First.Next.Data as IComparable).CompareTo(item) == 0) return _First.Next;
  789. return null;
  790. }
  791. int nPos = (int)Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  792. int nLeft = 0; //左边远素
  793. int nRight = (int)Count - 1; //右边远素
  794. DListNote_<T> ld = null;
  795. while (nRight >= 0 && nLeft >= 0)
  796. {
  797. ld = IndexOfNote(nPos);
  798. int iCom = (item as IComparable).CompareTo(ld.Data);
  799. if (iCom < 0)
  800. {
  801. if (nRight == nLeft || nPos == nLeft)
  802. {
  803. return null;
  804. }
  805. nRight = nPos - 1;
  806. }
  807. else if (iCom > 0)
  808. {
  809. if (nRight == nLeft || nPos == nRight)
  810. {
  811. return null;
  812. }
  813. nLeft = nPos + 1;
  814. }
  815. else
  816. {
  817. return ld;
  818. }
  819. nPos = nLeft + (nRight - nLeft + 1) / 2;
  820. }
  821. break;
  822. }
  823. case Sortord_.s_null:
  824. {
  825. DListNote_<T> pNote = _First;
  826. while (pNote != null)
  827. {
  828. //总结:Equals比较的永远是变量的内容是否相同,而= =比较的则是引用地址是否相同(前提:此种类型内部没有对Equals 或= = 进行重写操作,
  829. //否则输出可能会有不同)。string 类型是个特例,因为他的内部对这两个都进行了重写。
  830. if ((item as IComparable).CompareTo(pNote.Data) == 0)
  831. {
  832. return pNote;
  833. }
  834. /*
  835. if (pNote.Data.Equals(item))
  836. {
  837. return pNote;
  838. }
  839. */
  840. pNote = pNote.Next;
  841. }
  842. break;
  843. }
  844. default:
  845. {
  846. return null;
  847. }
  848. }
  849. return null;
  850. }
  851. /// <summary>
  852. /// 把索引为nIndex的节点移到最后
  853. /// </summary>
  854. /// <param name="nIndex"></param>
  855. /// <returns></returns>
  856. protected virtual bool MoveLast(int iIndex)
  857. {
  858. DListNote_<T> pNote = IndexOfNote(iIndex);
  859. if (pNote != null)
  860. {
  861. if (pNote == _Last)
  862. return true;
  863. if (pNote == _First) //此时最少两个节点
  864. {
  865. _First = _First.Next;
  866. _First.Prev = null;
  867. _Last.Next = pNote;
  868. pNote.Prev = _Last;
  869. _Last = pNote;
  870. }
  871. else
  872. {
  873. pNote.Prev.Next = pNote.Next;
  874. pNote.Next.Prev = pNote.Prev;
  875. _Last.Next = pNote;
  876. pNote.Prev = _Last;
  877. _Last = pNote;
  878. }
  879. return true;
  880. }
  881. return false;
  882. }
  883. /// <summary>
  884. ///
  885. /// </summary>
  886. /// <param name="dnCurrent"></param>
  887. /// <returns></returns>
  888. /// 创建时间: 2022-02-18 最后一次修改时间:2022-02-18
  889. protected virtual bool MoveLast(DListNote_<T> dnCurrent)
  890. {
  891. if (dnCurrent == null) return false;
  892. _sortord = Sortord_.s_null;
  893. if(_Count == 0)
  894. {
  895. return false;
  896. }
  897. else if(_Count == 1)
  898. {
  899. return true;
  900. }
  901. else if(_Count == 2)
  902. {
  903. if(dnCurrent == _First) //交换_First 与 _Last 数据
  904. {
  905. T tmp = _First.Data;
  906. _First.Data = _Last.Data;
  907. _Last.Data = tmp;
  908. }
  909. return true;
  910. }
  911. else
  912. {
  913. if (dnCurrent == _First)
  914. {
  915. _First = _First.Next;
  916. _First.Prev = null;
  917. _Last.Next = dnCurrent;
  918. dnCurrent.Next = null;
  919. dnCurrent.Prev = _Last;
  920. _Last = dnCurrent;
  921. }
  922. else if (dnCurrent != _Last)
  923. {
  924. dnCurrent.Prev.Next = dnCurrent.Next;
  925. dnCurrent.Next.Prev = dnCurrent.Prev;
  926. _Last.Next = dnCurrent;
  927. dnCurrent.Next = null;
  928. dnCurrent.Prev = _Last;
  929. _Last = dnCurrent;
  930. }
  931. return true;
  932. }
  933. }
  934. /// <summary>
  935. /// 把索引为nIndex的节点移到最前
  936. /// </summary>
  937. /// <param name="nIndex"></param>
  938. /// <returns></returns>
  939. protected virtual bool MoveFirst(int iIndex)
  940. {
  941. DListNote_<T> pNote = IndexOfNote(iIndex);
  942. if (pNote != null)
  943. {
  944. if (pNote == _First)
  945. return true;
  946. if (pNote == _Last) //此时最少两个节点
  947. {
  948. _Last.Prev.Next = null;
  949. _Last = _Last.Prev;
  950. pNote.Prev = null;
  951. pNote.Next = _First;
  952. _First.Prev = pNote;
  953. _First = pNote;
  954. }
  955. else
  956. {
  957. pNote.Prev.Next = pNote.Next;
  958. pNote.Next.Prev = pNote.Prev;
  959. pNote.Next = _First;
  960. _First.Prev = pNote;
  961. pNote.Prev = null;
  962. _First = pNote;
  963. }
  964. return true;
  965. }
  966. return false;
  967. }
  968. /// <summary>
  969. /// 返回第一个节点
  970. /// </summary>
  971. public DListNote_<T> First
  972. {
  973. get
  974. {
  975. return _First;
  976. }
  977. }
  978. /// <summary>
  979. /// 返回最后一个节点
  980. /// </summary>
  981. public DListNote_<T> Last
  982. {
  983. get { return _Last; }
  984. }
  985. //--------------------------------------------------------------------------------------
  986. /// <summary>
  987. /// 构造函数
  988. /// </summary>
  989. public DList_()
  990. {
  991. _Count = 0; _First = null; _Last = null;
  992. _sortord = Sortord_.s_null;
  993. }
  994. /// <summary>
  995. /// 删除链表中的数据
  996. /// </summary>
  997. /// <param name="pData"></param>
  998. /// <returns></returns>
  999. public bool RemoveItem(T pData)
  1000. {
  1001. if (_sortord == Sortord_.s_null)
  1002. {
  1003. DListNote_<T> pListItem = _First;
  1004. while (pListItem != null)
  1005. {
  1006. if (pListItem.Data.Equals(pData)) //找到一项
  1007. {
  1008. if (pListItem == _First) //删除的是第一个节点
  1009. {
  1010. if (_First.Next != null)
  1011. {
  1012. _First.Next.Prev = null;
  1013. _First = _First.Next;
  1014. }
  1015. else
  1016. {
  1017. _First = null;
  1018. _Last = null;
  1019. }
  1020. }
  1021. else if (pListItem == _Last) //删除的是最后一个节点
  1022. {
  1023. if (_Last.Prev != null)
  1024. {
  1025. _Last.Prev.Next = null;
  1026. _Last = _Last.Prev;
  1027. }
  1028. else
  1029. {
  1030. _First = null;
  1031. _Last = null;
  1032. }
  1033. }
  1034. else //删除的是中间的一个节点
  1035. {
  1036. pListItem.Next.Prev = pListItem.Prev;
  1037. pListItem.Prev.Next = pListItem.Next;
  1038. }
  1039. --_Count;
  1040. return true;
  1041. }
  1042. pListItem = pListItem.Next;
  1043. }
  1044. return false;
  1045. }
  1046. else
  1047. {
  1048. return RemoveAt(BinarySearch(pData));
  1049. }
  1050. }
  1051. /// <summary>
  1052. /// 删除链表中的节点
  1053. /// </summary>
  1054. /// <param name="pListItem"></param>
  1055. /// <returns></returns>
  1056. public bool DeleteNode(DListNote_<T> pListItem)
  1057. {
  1058. if (_Count == 0 || pListItem == null)
  1059. {
  1060. return false;
  1061. }
  1062. DListNote_<T> pNote = _First.Next;
  1063. while (pNote != null)
  1064. {
  1065. if (pNote == pListItem) //找到了
  1066. {
  1067. //pListItem->Prev
  1068. if (pListItem.Prev != null)
  1069. {
  1070. pListItem.Prev.Next = pListItem.Next;
  1071. }
  1072. else //删除的是第一个节点
  1073. {
  1074. _First = pListItem.Next;
  1075. }
  1076. //pListItem->Next
  1077. if (pListItem.Next != null)
  1078. {
  1079. pListItem.Next.Prev = pListItem.Prev;
  1080. }
  1081. else //删除的是最后一个节点
  1082. {
  1083. _Last = pListItem.Prev;
  1084. }
  1085. break;
  1086. }
  1087. pNote = pNote.Next;
  1088. }
  1089. if (pNote != null)
  1090. {
  1091. --_Count;
  1092. return true;
  1093. }
  1094. return false;
  1095. }
  1096. /// <summary>
  1097. /// 删除最后一个节点
  1098. /// </summary>
  1099. /// 创建时间:2020-09-12 最后一次修改时间: 2020-09-12
  1100. public bool DeleteLast()
  1101. {
  1102. if (_Count <= 0)
  1103. {
  1104. return false;
  1105. }
  1106. else if (_Count == 1)
  1107. {
  1108. _First = null;
  1109. _Last = null;
  1110. _Count = 0;
  1111. return true;
  1112. }
  1113. else if(_Count == 2)
  1114. {
  1115. _Last = _First;
  1116. _Last.Prev = null;
  1117. _Last.Next = null;
  1118. _First.Next = null;
  1119. _First.Prev = null;
  1120. --_Count;
  1121. }
  1122. else
  1123. {
  1124. _Last.Prev.Next = null;
  1125. _Last = _Last.Prev;
  1126. --_Count;
  1127. }
  1128. return true; ;
  1129. }
  1130. //--------------------------------------------------------------------------接口
  1131. /// <summary>
  1132. //示例为了使一个类支持集合初始化器,它必须实现IEnumerable接口并至少具有一个Add方法。从C#6开始,
  1133. //IEnumerable可以Add使用扩展方法使用自定义方法扩展任何实现的集合。
  1134. /// </summary>
  1135. /// 创建时间:2020-05-07 最后一次修改时间: 2020-05-07
  1136. /// <returns></returns>
  1137. public IEnumerator GetEnumerator()
  1138. {
  1139. return new DListNoteEnum_<T>(_First);
  1140. }
  1141. }
  1142. /// <summary>
  1143. /// 节点数据的foreach迭代
  1144. /// </summary>
  1145. /// 创建时间:2020-05-07 最后一次修改时间: 2022-10-10
  1146. /// <typeparam name="T"></typeparam>
  1147. public class DListNoteEnum_<T> : IEnumerator
  1148. {
  1149. private DListNote_<T> _dn;
  1150. private DListNote_<T> _dnCurr;
  1151. private int _iIndex;
  1152. public DListNoteEnum_(DListNote_<T> dn)
  1153. {
  1154. _dn = dn;
  1155. _iIndex = -1;
  1156. }
  1157. /// <summary>
  1158. /// IEnumerator最终调用的是这个函数访问
  1159. /// </summary>
  1160. public Object Current { get{ return _dnCurr.Data; } }
  1161. public virtual bool MoveNext()
  1162. {
  1163. ++_iIndex; //指针首先向前移动一位
  1164. if (_dnCurr == null)
  1165. {
  1166. _dnCurr = _dn;
  1167. }
  1168. else
  1169. {
  1170. _dnCurr = _dnCurr.Next;
  1171. }
  1172. return _dnCurr != null;
  1173. }
  1174. public virtual void Reset()
  1175. {
  1176. _dnCurr = null;
  1177. _iIndex = -1;
  1178. }
  1179. };
  1180. #endregion
  1181. #region//====================================================== SortList_ 已排序的链表
  1182. /// <summary>
  1183. /// 已排序的链表
  1184. /// </summary>
  1185. /// <typeparam name="T"></typeparam>
  1186. public class SortList_<T> : DList_<T>
  1187. {
  1188. public SortList_(Sortord_ sortord)
  1189. {
  1190. _sortord = sortord;
  1191. }
  1192. //-------------------------------------------------------------------------------重写
  1193. /// <summary>
  1194. /// 添加一项到结尾处,item不能为NULL.
  1195. /// </summary>
  1196. /// <param name="item">项</param>
  1197. /// 创建时间: ????-??-?? 最后一次修改时间:2021-11-07
  1198. public override void Add(T item)
  1199. {
  1200. if (item == null)
  1201. {
  1202. throw new System.Exception("SortList_.Add 方法提示:类型值不能为null!");
  1203. }
  1204. if ( !(item is IComparable) ) // 判断是否具有IComparable接口,以确定是否存在CompareTo()方法
  1205. {
  1206. throw new System.Exception("SortList_<" + item.GetType().Name + ">.Add 方法提示:类型“" + item.GetType().Name + "”没有IComparable接口!");
  1207. }
  1208. if (Count < 3)
  1209. {
  1210. bool bInsett = false; DListNote_<T> ldNote = First;
  1211. while (ldNote != null)
  1212. {
  1213. if (_sortord == Sortord_.s_max_min)
  1214. {
  1215. if ((item as IComparable).CompareTo(ldNote.Data) >= 0)
  1216. {
  1217. base.InserNoteFront(ldNote, item); bInsett = true; break;
  1218. }
  1219. }
  1220. else
  1221. {
  1222. if ((item as IComparable).CompareTo(ldNote.Data) <= 0)
  1223. {
  1224. base.InserNoteFront(ldNote, item); bInsett = true; break;
  1225. }
  1226. }
  1227. ldNote = ldNote.Next;
  1228. }
  1229. if (!bInsett) base.Add(item);
  1230. return;
  1231. }
  1232. int nPos = Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  1233. int nLeft = 0; //左边远素
  1234. int nRight = Count - 1; //右边远素
  1235. if (_sortord == Sortord_.s_max_min)
  1236. {
  1237. DListNote_<T> ldNote = null;
  1238. while (nRight >= 0 && nLeft >= 0)
  1239. {
  1240. ldNote = IndexOfNote(nPos);
  1241. if ((item as IComparable).CompareTo(ldNote.Data) >= 0)
  1242. {
  1243. if (nRight == nLeft || nPos == nLeft)
  1244. {
  1245. InserNoteFront(ldNote, item);
  1246. return;
  1247. }
  1248. nRight = nPos - 1;
  1249. }
  1250. else
  1251. {
  1252. if (nRight == nLeft || nPos == nRight)
  1253. {
  1254. InserNoteBack(ldNote, item);
  1255. return;
  1256. }
  1257. nLeft = nPos + 1;
  1258. }
  1259. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1260. }
  1261. }
  1262. else
  1263. {
  1264. DListNote_<T> ld = null;
  1265. while (nRight >= 0 && nLeft >= 0)
  1266. {
  1267. ld = IndexOfNote(nPos);
  1268. if ((item as IComparable).CompareTo(ld.Data) <= 0)
  1269. {
  1270. if (nRight == nLeft || nPos == nLeft)
  1271. {
  1272. InserNoteFront(ld, item);
  1273. return;
  1274. }
  1275. nRight = nPos - 1;
  1276. }
  1277. else
  1278. {
  1279. if (nRight == nLeft || nPos == nRight)
  1280. {
  1281. InserNoteBack(ld, item);
  1282. return;
  1283. }
  1284. nLeft = nPos + 1;
  1285. }
  1286. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1287. }
  1288. }
  1289. return;
  1290. }
  1291. }
  1292. #endregion
  1293. #region//================================================= UniqueList_ 每个项的值都是唯一的链表
  1294. /// <summary>
  1295. /// 每个项的值都是唯一的链表
  1296. /// </summary>
  1297. /// <typeparam name="T"></typeparam>
  1298. public class UniqueList_<T> : DList_<T>
  1299. {
  1300. public override void Add(T item)
  1301. {
  1302. if (BinarySearch(item) == -1)
  1303. {
  1304. base.Add(item);
  1305. }
  1306. }
  1307. }
  1308. #endregion
  1309. #region //========================== =========SUList_,已排序,且每一项的值都是唯一的链表
  1310. /// <summary>
  1311. /// SUList_,已排序,且每一项的值都是唯一的链表
  1312. /// </summary>
  1313. /// <typeparam name="T"></typeparam>
  1314. public class SUList_<T> : SortList_<T>
  1315. {
  1316. /// <summary>
  1317. /// 将指定集合的元素添加到末尾
  1318. /// </summary>
  1319. /// <param name="item">要添加到的末尾处的对象。对于引用类型,该值可以为 null</param>
  1320. /// <returns>如成功,返回真,否则返回假</returns>
  1321. public override void Add(T item)
  1322. {
  1323. if (BinarySearch(item) == -1)
  1324. {
  1325. base.Add(item);
  1326. }
  1327. }
  1328. public SUList_(Sortord_ sortord)
  1329. : base(sortord)
  1330. {
  1331. }
  1332. }
  1333. #endregion
  1334. #region //=========================================StringList_字符串列表
  1335. /// <summary>
  1336. /// 字符串列表
  1337. /// </summary>
  1338. public class StringList_ : DList_<string>
  1339. {
  1340. /// <summary>
  1341. /// 默认构函数
  1342. /// </summary>
  1343. public StringList_()
  1344. {
  1345. }
  1346. /// <summary>
  1347. /// 以分隔符构造一个字符串列表
  1348. /// </summary>
  1349. /// <param name="sText">原文字符串</param>
  1350. /// <param name="sSplit">分隔符</param>
  1351. /// <param name="bIgnoreEmptyString">返回列表,空字符串不忽略,如果没有分隔符,则回原字符</param>
  1352. /// 创建时间: ????-??-?? 最后一修改时间:2020-09-03
  1353. public StringList_(string sText, string sSplit, bool bIgnoreEmptyString = false)
  1354. {
  1355. if(sText == null || sText.Length == 0){ return; }
  1356. if(sSplit.Length == 0) { Add(sText); return; }
  1357. int nPos = sText.IndexOf(sSplit);
  1358. int nFindStart = 0;
  1359. while(nPos != -1)
  1360. {
  1361. if (nPos - nFindStart == 0)
  1362. {
  1363. if (!bIgnoreEmptyString)
  1364. {
  1365. Add("");
  1366. }
  1367. }
  1368. else
  1369. {
  1370. Add(sText.Substring(nFindStart, nPos - nFindStart));
  1371. }
  1372. nFindStart = nPos + sSplit.Length;
  1373. nPos = sText.IndexOf(sSplit, nFindStart);
  1374. if(nPos == -1) //拷贝最后一个
  1375. {
  1376. if(nFindStart < sText.Length)
  1377. {
  1378. Add(sText.Substring(nFindStart, sText.Length - nFindStart));
  1379. }
  1380. else
  1381. {
  1382. if (!bIgnoreEmptyString)
  1383. {
  1384. Add("");
  1385. }
  1386. }
  1387. }
  1388. }
  1389. }
  1390. #if !WINDOWS_UWP
  1391. /// <summary>
  1392. /// 把列表写入文件
  1393. /// </summary>
  1394. /// <param name="sFileName">文件名</param>
  1395. public void WriteToFile(string sFileName)
  1396. {
  1397. System.IO.File.Delete(sFileName);
  1398. DListNote_<string> dl = First;
  1399. FileStream fs = File.Create(sFileName);
  1400. while (dl != null)
  1401. {
  1402. byte[] bArray = System.Text.Encoding.Default.GetBytes(dl.Data);
  1403. fs.Write(bArray, 0, bArray.Length);
  1404. bArray = System.Text.Encoding.Default.GetBytes("\r\n");
  1405. //fs.WriteByte((byte)'\r'); 不行,UNICODE代码
  1406. //fs.WriteByte((byte)'\n');
  1407. fs.Write(bArray, 0, bArray.Length);
  1408. dl = dl.Next;
  1409. }
  1410. fs.Close();
  1411. }
  1412. /// <summary>
  1413. /// 从文件中读取列表分隔符为"\r\n";
  1414. /// </summary>
  1415. /// <param name="sFileName">文件名</param>
  1416. /// <returns></returns>
  1417. public bool ReadToFile(string sFileName)
  1418. {
  1419. if (File.Exists(sFileName))
  1420. {
  1421. FileStream fs = new FileStream(sFileName, FileMode.Open, FileAccess.Read);
  1422. Byte[] bArray = new Byte[fs.Length];
  1423. fs.Read(bArray, 0, bArray.Length);
  1424. fs.Close();
  1425. CopyFrom(System.Text.Encoding.Default.GetString(bArray)._Split("\r\n"));
  1426. return true;
  1427. }
  1428. return false;
  1429. }
  1430. /// <summary>
  1431. /// 从文件中读取列表分隔符
  1432. /// </summary>
  1433. /// <param name="sFileName"></param>
  1434. /// <param name="sSplit"></param>
  1435. /// <returns></returns>
  1436. public bool readToUnicodeFile(string sFileName,string sSplit)
  1437. {
  1438. if (File.Exists(sFileName))
  1439. {
  1440. FileStream fs = new FileStream(sFileName, FileMode.Open, FileAccess.Read);
  1441. Byte[] bArray = new Byte[fs.Length];
  1442. fs.Read(bArray, 0, bArray.Length);
  1443. fs.Close();
  1444. CopyFrom(System.Text.Encoding.Unicode.GetString(bArray)._Split(sSplit));
  1445. return true;
  1446. }
  1447. return false;
  1448. }
  1449. public void SaveToUnicodeFile(string sFileName, string sSplit)
  1450. {
  1451. /*
  1452. if(_Count > 0)
  1453. {
  1454. string sContent = "";
  1455. int n = 1;
  1456. foreach(string s in this)
  1457. {
  1458. sContent += s;
  1459. if(n != _Count)
  1460. sContent += sSplit;
  1461. }
  1462. Byte[] bArray = System.Text.ASCIIEncoding.ASCII.GetBytes(sContent);
  1463. FileStream fs = new FileStream(sFileName, FileMode.Create, FileAccess.Write);
  1464. fs.Write(bArray, 0, bArray.Length);
  1465. fs.Close();
  1466. }
  1467. */
  1468. }
  1469. /// <summary>
  1470. /// 把所有字符串写入磁盘,但每个字符串中的空格和不可打印字符都不会写入,每15个字符串加入一个换行符。
  1471. /// </summary>
  1472. /// <param name="sFileName"></param>
  1473. /// <param name="sSplit"></param>
  1474. /// 创建时间: 2022-02-09 最后一次修改时间:2022-02-09
  1475. public void WriteToTxtFile(string sFileName, string sSplit)
  1476. {
  1477. if (_Count > 0)
  1478. {
  1479. string sContent = "";
  1480. int n = 1;
  1481. foreach (string s in this)
  1482. {
  1483. sContent += s._RemoveUnprintableAndWhitespace();
  1484. if (n != _Count)
  1485. sContent += sSplit;
  1486. if(n % 15 == 0)
  1487. sContent += "\n";
  1488. ++n;
  1489. }
  1490. File.WriteAllText(sFileName,sContent);
  1491. }
  1492. }
  1493. /// <summary>
  1494. /// 用分隔 符读取文本文件,空格和不可打印字符都不读取。
  1495. /// </summary>
  1496. /// <param name="sFileName"></param>
  1497. /// <param name="sSplit"></param>
  1498. /// 创建时间: 2022-02-09 最后一次修改时间:2022-02-18
  1499. public void ReadFromTxtFile(string sFileName, string sSplit)
  1500. {
  1501. if (!File.Exists(sFileName))
  1502. return;
  1503. string sContent = File.ReadAllText(sFileName)._RemoveUnprintableAndWhitespace();
  1504. if(sContent.Trim().Length > 0)
  1505. {
  1506. CopyFrom(sContent._Split(sSplit));
  1507. }
  1508. }
  1509. #endif
  1510. /// <summary>
  1511. /// 用分隔符把每个项连成一片,如果分隔符为空,则直接连成一片
  1512. /// </summary>
  1513. /// <param name="sSeparator">分隔符</param>
  1514. /// <returns></returns>
  1515. public string ConnectForSeparator(string sSeparator)
  1516. {
  1517. if (Count == 0) return "";
  1518. if (Count == 1) return First.Data;
  1519. string tmp = "";
  1520. DListNote_<string> ldNote = First;
  1521. while (ldNote != Last)
  1522. {
  1523. tmp += ldNote.Data;
  1524. tmp += sSeparator;
  1525. ldNote = ldNote.Next;
  1526. }
  1527. tmp += Last.Data; //加入最后一项
  1528. return tmp;
  1529. }
  1530. /// <summary>
  1531. /// 用分隔符把每个项连成一片,如果分隔符为空,则直接连成一片
  1532. /// </summary>
  1533. /// <param name="cSeparator">分隔符</param>
  1534. /// <returns></returns>
  1535. public string ConnectForSeparator(char cSeparator)
  1536. {
  1537. return ConnectForSeparator(cSeparator.ToString());
  1538. }
  1539. /// <summary>
  1540. /// 清空列表,用分隔符把字符串分裂成多项,返回项数
  1541. /// </summary>
  1542. /// <param name="sText"></param>
  1543. /// <param name="sSplit"></param>
  1544. /// <returns></returns>
  1545. public int splitForSeparator(string sText, char cSplit)
  1546. {
  1547. Clear();
  1548. string[] sl = sText.Split(cSplit);
  1549. for (int i = 0; i < sl.Length; ++i)
  1550. {
  1551. Add(sl[i]);
  1552. }
  1553. return Count;
  1554. }
  1555. /// <summary>
  1556. /// 查找第一个可印的字符串,如果找到则返回它的值,没找到返回空字符中。
  1557. /// </summary>
  1558. /// <returns></returns>
  1559. /// 创建时间: 2022-01-21 最后一次修改时间:2022-01-21
  1560. public string FindFirstPrintableStringValue()
  1561. {
  1562. DListNote_<string> pNote = _First;
  1563. while (pNote != null)
  1564. {
  1565. if(pNote.Data._IsHavePrintableChar())
  1566. {
  1567. return pNote.Data;
  1568. }
  1569. pNote = pNote.Next;
  1570. }
  1571. return "";
  1572. }
  1573. /// <summary>
  1574. /// 查找第一个可印的字符串的索引,如果找到则返回它的索引,没找到返回-1。
  1575. /// </summary>
  1576. /// <returns></returns>
  1577. /// 创建时间: 2022-01-21 最后一次修改时间:2022-01-21
  1578. public int FindFirstPrintableStringIndex()
  1579. {
  1580. DListNote_<string> pNote = _First;
  1581. int nResult = 0;
  1582. while (pNote != null)
  1583. {
  1584. if (pNote.Data._IsHavePrintableChar())
  1585. {
  1586. return nResult;
  1587. }
  1588. pNote = pNote.Next;
  1589. ++nResult;
  1590. }
  1591. return -1;
  1592. }
  1593. /// <summary>
  1594. ///
  1595. /// </summary>
  1596. /// <param name="ls"></param>
  1597. /// <returns></returns>
  1598. /// 创建时间: ????-??-?? 最后一次修改时间:2021-10-10
  1599. public virtual bool Add(StringList_ ls)
  1600. {
  1601. DListNote_<string> pNote = ls._First;
  1602. while (pNote != null)
  1603. {
  1604. Add(pNote.Data);
  1605. pNote = pNote.Next;
  1606. }
  1607. return true;
  1608. }
  1609. /// <summary>
  1610. /// 是开头插入一个字符串
  1611. /// </summary>
  1612. /// <param name="sItem"></param>
  1613. /// <returns></returns>
  1614. /// 创建时间: 2022-01-18 最后一次修改时间:2022-01-18
  1615. public virtual bool InserFront(string sItem)
  1616. {
  1617. if(_Count == 0)
  1618. Add(sItem);
  1619. InserNoteFront(_First,sItem);
  1620. return true;
  1621. }
  1622. /// <summary>
  1623. /// 查找字符吕 S
  1624. /// </summary>
  1625. /// <param name="s"></param>
  1626. /// <returns></returns>
  1627. /// <exception cref="Exception"></exception>
  1628. /// 创建时间: ????-??-?? 最后一次修改时间:2022-09-18
  1629. public int IndexOf(string s)
  1630. {
  1631. //if(s.Length == 0){ throw new Exception("字符串不能为空!");}
  1632. DListNote_<string> pNote = _First;
  1633. int iIndex = 0;
  1634. while (pNote != null)
  1635. {
  1636. if (pNote.Data == s)
  1637. {
  1638. return iIndex;
  1639. }
  1640. pNote = pNote.Next;
  1641. ++iIndex;
  1642. }
  1643. return - 1;
  1644. }
  1645. }
  1646. #endregion
  1647. #region //=========================================LSStringList已排序好的字符串列表
  1648. /// <summary>
  1649. /// 已排序好的字符串列表
  1650. /// </summary>
  1651. public class SStringList_ : StringList_
  1652. {
  1653. public SStringList_(Sortord_ sortord)
  1654. {
  1655. if (sortord == Sortord_.s_null)
  1656. {
  1657. throw new System.Exception("排序不能为空!");
  1658. }
  1659. _sortord = sortord;
  1660. }
  1661. //-------------------------------------------------------------------------------重写
  1662. /// <summary>
  1663. /// 快速添加字符串,差不多用了8个小时(两天),才写成。
  1664. /// </summary>
  1665. /// <param name="s"></param>
  1666. /// <returns></returns>
  1667. public override void Add(string item)
  1668. {
  1669. if (Count < 3)
  1670. {
  1671. bool bInsett = false; DListNote_<string> ld = First;
  1672. while (ld != null)
  1673. {
  1674. if (_sortord == Sortord_.s_max_min)
  1675. {
  1676. if (item.CompareTo(ld.Data) >= 0)
  1677. {
  1678. base.InserNoteFront(ld, item); bInsett = true; break;
  1679. }
  1680. }
  1681. else
  1682. {
  1683. if (item.CompareTo(ld.Data) <= 0)
  1684. {
  1685. base.InserNoteFront(ld, item); bInsett = true; break;
  1686. }
  1687. }
  1688. ld = ld.Next;
  1689. }
  1690. if (!bInsett) base.Add(item);
  1691. return;
  1692. }
  1693. int nPos = Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  1694. int nLeft = 0; //左边远素
  1695. int nRight = Count - 1; //右边远素
  1696. if (_sortord == Sortord_.s_max_min)
  1697. {
  1698. DListNote_<string> ld = null;
  1699. while (nRight >= 0 && nLeft >= 0)
  1700. {
  1701. ld = IndexOfNote(nPos);
  1702. if (item.CompareTo(ld.Data) >= 0)
  1703. {
  1704. if (nRight == nLeft || nPos == nLeft)
  1705. {
  1706. InserNoteFront(ld, item);
  1707. return;
  1708. }
  1709. nRight = nPos - 1;
  1710. }
  1711. else
  1712. {
  1713. if (nRight == nLeft || nPos == nRight)
  1714. {
  1715. InserNoteBack(ld, item);
  1716. return;
  1717. }
  1718. nLeft = nPos + 1;
  1719. }
  1720. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1721. }
  1722. }
  1723. else
  1724. {
  1725. DListNote_<string> ld = null;
  1726. while (nRight >= 0 && nLeft >= 0)
  1727. {
  1728. ld = IndexOfNote(nPos);
  1729. if (item.CompareTo(ld.Data) <= 0)
  1730. {
  1731. if (nRight == nLeft || nPos == nLeft)
  1732. {
  1733. InserNoteFront(ld, item);
  1734. return;
  1735. }
  1736. nRight = nPos - 1;
  1737. }
  1738. else
  1739. {
  1740. if (nRight == nLeft || nPos == nRight)
  1741. {
  1742. InserNoteBack(ld, item);
  1743. return;
  1744. }
  1745. nLeft = nPos + 1;
  1746. }
  1747. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1748. }
  1749. }
  1750. return;
  1751. }
  1752. /// <summary>
  1753. /// 确定某元素是否在列表中
  1754. /// </summary>
  1755. /// <param name="item">查找的对象。对于引用类型,该值可以为 null。</param>
  1756. /// <returns>如果在列表中找到 item,则为 true,否则为 false。</returns>
  1757. public override bool Contains(string item)
  1758. {
  1759. if (Count == 0) return false;
  1760. if (Count == 1) return First.Data.CompareTo(item) == 0;
  1761. if (Count == 2) return First.Data.CompareTo(item) == 0 || First.Next.Data.CompareTo(item) == 0;
  1762. int nPos = (int)Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  1763. int nLeft = 0; //左边远素
  1764. int nRight = (int)Count - 1; //右边远素
  1765. DListNote_<string> ld = null;
  1766. if (_sortord == Sortord_.s_max_min)
  1767. {
  1768. while (nRight >= 0 && nLeft >= 0)
  1769. {
  1770. ld = IndexOfNote(nPos);
  1771. int iCom = item.CompareTo(ld.Data);
  1772. if (iCom > 0)
  1773. {
  1774. if (nRight == nLeft || nPos == nLeft)
  1775. {
  1776. return false;
  1777. }
  1778. nRight = nPos - 1;
  1779. }
  1780. else if (iCom < 0)
  1781. {
  1782. if (nRight == nLeft || nPos == nRight)
  1783. {
  1784. return false;
  1785. }
  1786. nLeft = nPos + 1;
  1787. }
  1788. else
  1789. {
  1790. return true;
  1791. }
  1792. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1793. }
  1794. }
  1795. else
  1796. {
  1797. while (nRight >= 0 && nLeft >= 0)
  1798. {
  1799. ld = IndexOfNote(nPos);
  1800. int iCom = item.CompareTo(ld.Data);
  1801. if (iCom < 0)
  1802. {
  1803. if (nRight == nLeft || nPos == nLeft)
  1804. {
  1805. return false;
  1806. }
  1807. nRight = nPos - 1;
  1808. }
  1809. else if (iCom > 0)
  1810. {
  1811. if (nRight == nLeft || nPos == nRight)
  1812. {
  1813. return false;
  1814. }
  1815. nLeft = nPos + 1;
  1816. }
  1817. else
  1818. {
  1819. return true;
  1820. }
  1821. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1822. }
  1823. }
  1824. return false;
  1825. }
  1826. }
  1827. #endregion
  1828. #region //=========================================UStringList_值都是唯一的字符串列表,区分大小写
  1829. /// <summary>
  1830. /// 值都是唯一的字符串列表
  1831. /// </summary>
  1832. /// <typeparam name="T"></typeparam>
  1833. public class UStringList_ : StringList_
  1834. {
  1835. public override void Add(string item)
  1836. {
  1837. if(BinarySearch(item) == -1)
  1838. base.Add(item);
  1839. }
  1840. public void Add(string[] sArray)
  1841. {
  1842. for (int i = 0; i < sArray.Length; ++i)
  1843. {
  1844. Add(sArray[i]);
  1845. }
  1846. }
  1847. public override bool Add(StringList_ ls)
  1848. {
  1849. bool bResult = true;
  1850. DListNote_<string> pFirst = ls.First;
  1851. while (pFirst != null)
  1852. {
  1853. if (BinarySearch(pFirst.Data) == -1)
  1854. {
  1855. base.Add(pFirst.Data);
  1856. }
  1857. else
  1858. {
  1859. bResult = false;
  1860. }
  1861. pFirst = pFirst.Next;
  1862. }
  1863. return bResult;
  1864. }
  1865. }
  1866. #endregion
  1867. #region//======================================SUStringList_ 值都是唯一的字符串列表,且已排好序,区分大小写
  1868. /// <summary>
  1869. /// 值都是唯一的字符串列表,且已排好序,区分大小写
  1870. /// </summary>
  1871. public class SUStringList_ : SStringList_
  1872. {
  1873. public override void Add(string item)
  1874. {
  1875. if (Contains(item))
  1876. return;
  1877. base.Add(item);
  1878. }
  1879. public SUStringList_(Sortord_ sortord)
  1880. : base(sortord)
  1881. {
  1882. }
  1883. }
  1884. #endregion
  1885. #region //=========================================UStringListCI_值都是唯一的字符串列表,不区分大小写
  1886. /// <summary>
  1887. /// 值都是唯一的字符串列表, Case Insensitive(不区分大小写)
  1888. /// </summary>
  1889. public class UStringListCI_ : StringList_
  1890. {
  1891. /// <summary>
  1892. /// 加入一个串,如果这个串存在,则把这项移到最后。
  1893. /// </summary>
  1894. /// <param name="item"></param>
  1895. /// 创建时间: ????-??-?? 最后一次修改时间:2022-02-18
  1896. public override void Add(string item)
  1897. {
  1898. bool bFind = false;
  1899. DListNote_<string> dnTemp = First;
  1900. while(dnTemp != null)
  1901. {
  1902. if(dnTemp.Data.ToLower() == item.ToLower())
  1903. {
  1904. MoveLast(dnTemp);
  1905. bFind = true;
  1906. break;
  1907. }
  1908. dnTemp = dnTemp.Next;
  1909. }
  1910. if (!bFind)
  1911. base.Add(item);
  1912. }
  1913. /// <summary>
  1914. /// 返回前面一个值
  1915. /// </summary>
  1916. /// <param name="tCurrValue"></param>
  1917. /// <returns></returns>
  1918. public string GetForward(string sCurr)
  1919. {
  1920. int iIndex = BinarySearch(sCurr);
  1921. if (iIndex != -1)
  1922. {
  1923. if (iIndex + 1 < Count)
  1924. return this[iIndex + 1];
  1925. }
  1926. return null;
  1927. }
  1928. /// <summary>
  1929. /// 返回后面的一个值
  1930. /// </summary>
  1931. /// <param name="sCurr"></param>
  1932. /// <returns></returns>
  1933. public string GetBack(string sCurr)
  1934. {
  1935. int iIndex = BinarySearch(sCurr);
  1936. if (iIndex != -1)
  1937. {
  1938. if (iIndex - 1 < Count && iIndex - 1 >= 0)
  1939. return this[iIndex - 1];
  1940. }
  1941. return null;
  1942. }
  1943. }
  1944. #endregion
  1945. #region //=========================================UStringListCI_值都是唯一,且已排序的字符串列表,不区分大小写
  1946. /// <summary>
  1947. /// UStringListCI_值都是唯一,且已排序的字符串列表,不区分大小写
  1948. /// </summary>
  1949. public class SUStringListUI_ : SUStringList_
  1950. {
  1951. public SUStringListUI_(Sortord_ sortord): base(sortord)
  1952. {
  1953. }
  1954. /// <summary>
  1955. /// 确定某元素是否在列表中
  1956. /// </summary>
  1957. /// <param name="item">查找的对象。对于引用类型,该值可以为 null。</param>
  1958. /// <returns>如果在列表中找到 item,则为 true,否则为 false。</returns>
  1959. public override bool Contains(string item)
  1960. {
  1961. if (Count == 0) return false;
  1962. if (Count == 1) return First.Data.ToLower().CompareTo(item.ToLower()) == 0;
  1963. if (Count == 2) return First.Data.ToLower().CompareTo(item.ToLower()) == 0 || First.Next.Data.ToLower().CompareTo(item.ToLower()) == 0;
  1964. int nPos = (int)Count / 2; //nPos在中间,所以无素一定要大于等于3才行
  1965. int nLeft = 0; //左边远素
  1966. int nRight = (int)Count - 1; //右边远素
  1967. DListNote_<string> ld = null;
  1968. if (_sortord == Sortord_.s_max_min)
  1969. {
  1970. while (nRight >= 0 && nLeft >= 0)
  1971. {
  1972. ld = IndexOfNote(nPos);
  1973. int iCom = item.ToLower().CompareTo(ld.Data.ToLower());
  1974. if (iCom > 0)
  1975. {
  1976. if (nRight == nLeft || nPos == nLeft)
  1977. {
  1978. return false;
  1979. }
  1980. nRight = nPos - 1;
  1981. }
  1982. else if (iCom < 0)
  1983. {
  1984. if (nRight == nLeft || nPos == nRight)
  1985. {
  1986. return false;
  1987. }
  1988. nLeft = nPos + 1;
  1989. }
  1990. else
  1991. {
  1992. return true;
  1993. }
  1994. nPos = nLeft + (nRight - nLeft + 1) / 2;
  1995. }
  1996. }
  1997. else
  1998. {
  1999. while (nRight >= 0 && nLeft >= 0)
  2000. {
  2001. ld = IndexOfNote(nPos);
  2002. int iCom = item.ToLower().CompareTo(ld.Data.ToLower());
  2003. if (iCom < 0)
  2004. {
  2005. if (nRight == nLeft || nPos == nLeft)
  2006. {
  2007. return false;
  2008. }
  2009. nRight = nPos - 1;
  2010. }
  2011. else if (iCom > 0)
  2012. {
  2013. if (nRight == nLeft || nPos == nRight)
  2014. {
  2015. return false;
  2016. }
  2017. nLeft = nPos + 1;
  2018. }
  2019. else
  2020. {
  2021. return true;
  2022. }
  2023. nPos = nLeft + (nRight - nLeft + 1) / 2;
  2024. }
  2025. }
  2026. return false;
  2027. }
  2028. }
  2029. #endregion
  2030. /// <summary>
  2031. /// 历史记录,相当于栈
  2032. /// </summary>
  2033. /// <typeparam name="T"></typeparam>
  2034. /// 创建时间:2022-03-06 最后一次修改时间:2022-04-19
  2035. public class UniqueStack_<T>
  2036. {
  2037. private DList_<T> m_List;
  2038. private int m_Capacity;
  2039. public DList_<T> List => m_List;
  2040. /// <summary>
  2041. /// 元素容量
  2042. /// </summary>
  2043. public int Capacity => m_Capacity;
  2044. /// <summary>
  2045. /// 无素个数
  2046. /// </summary>
  2047. public int Count => m_List.Count;
  2048. public UniqueStack_(int nCapacity = 15)
  2049. {
  2050. if(nCapacity <= 0)
  2051. {
  2052. lg.ShowError("容量不能小于等于 0 !");
  2053. m_Capacity = 15;
  2054. }
  2055. else
  2056. {
  2057. m_Capacity = nCapacity;
  2058. }
  2059. m_List = new DList_<T>();
  2060. }
  2061. /// <summary>
  2062. /// 添加一项
  2063. /// </summary>
  2064. /// <param name="item"></param>
  2065. /// 创建时间: 2022-04-19 最后一次修改时间:2022-04-19
  2066. public void Push(T item)
  2067. {
  2068. bool bFind = m_List.RemoveItem(item); //如果找到,则删除
  2069. if (!bFind)
  2070. {
  2071. if (m_List.Count < m_Capacity)
  2072. {
  2073. m_List.StackPush(item);
  2074. }
  2075. else
  2076. {
  2077. //插入一个Item,所有元素后移一位
  2078. m_List.StackPush(item,true);
  2079. }
  2080. }
  2081. else
  2082. {
  2083. //插入一个Item,所有元素后移一位
  2084. m_List.StackPush(item);
  2085. }
  2086. }
  2087. /// <summary>
  2088. /// 出栈
  2089. /// </summary>
  2090. public void Pop() => List.StackPop();
  2091. }
  2092. public class HistoryStringList_ : UniqueStack_<string>
  2093. {
  2094. public override string ToString()
  2095. {
  2096. string sResult = "";
  2097. foreach (string s in List)
  2098. {
  2099. sResult += s + "||";
  2100. }
  2101. if (sResult != "")
  2102. {
  2103. sResult = sResult.Substring(0, sResult.Length - 2);
  2104. }
  2105. return sResult;
  2106. }
  2107. public void FromString(string sVaule)
  2108. {
  2109. List.Clear();
  2110. StringList_ ls = sVaule._Split("||");
  2111. DListNote_<string> dnNote = ls.Last;
  2112. while (dnNote != null){
  2113. Push(dnNote.Data);
  2114. dnNote = dnNote.Prev;
  2115. }
  2116. }
  2117. public HistoryStringList_(int nCapacity = 15) : base(nCapacity) { }
  2118. }
  2119. public class HistoryStringListPair_ : UniqueStack_<Pair_<string, string>>
  2120. {
  2121. public override string ToString()
  2122. {
  2123. string sResult = "";
  2124. foreach (Pair_<string, string> pair in List)
  2125. {
  2126. sResult += pair.First + "," + pair.Second + "||";
  2127. }
  2128. if (sResult != "")
  2129. {
  2130. sResult = sResult.Substring(0, sResult.Length - 2);
  2131. }
  2132. return sResult;
  2133. }
  2134. public void FromString(string sVaule)
  2135. {
  2136. List.Clear();
  2137. StringList_ ls1 = sVaule._Split("||");
  2138. DListNote_<string> dnNote = ls1.Last;
  2139. while (dnNote != null)
  2140. {
  2141. StringList_ ls2 = dnNote.Data._Split(",");
  2142. if (ls2.Count == 2)
  2143. {
  2144. Push(ls2[0], ls2[1]);
  2145. }
  2146. dnNote = dnNote.Prev;
  2147. }
  2148. }
  2149. public HistoryStringListPair_(int nCapacity = 15) : base(nCapacity) { }
  2150. public void Push(string s1, string s2) { base.Push(new Pair_<string, string>(s1, s2)); }
  2151. public Pair_<string, string> IndexOfFirst(string sFirst)
  2152. {
  2153. foreach (Pair_<string, string> pair in List)
  2154. {
  2155. if (pair.First == sFirst)
  2156. return pair;
  2157. }
  2158. return null;
  2159. }
  2160. public Pair_<string, string> IndexOfSecond(string sSecond)
  2161. {
  2162. foreach(Pair_<string, string> pair in List)
  2163. {
  2164. if(pair.Second == sSecond)
  2165. return pair;
  2166. }
  2167. return null;
  2168. }
  2169. }
  2170. public class LPairList<T1, T2> : IEnumerable
  2171. {
  2172. DList_<Pair_<T1, T2>> m_list;
  2173. public DList_<Pair_<T1, T2>> List { get { return m_list; } }
  2174. public LPairList()
  2175. {
  2176. m_list = new DList_<Pair_<T1, T2>>();
  2177. }
  2178. public Pair_<T1, T2> GetIndex(int iIndex)
  2179. {
  2180. DListNote_<Pair_<T1, T2>> dn = m_list.IndexOfNote(iIndex);
  2181. if (dn == null)
  2182. return null;
  2183. else
  2184. return dn.Data;
  2185. }
  2186. public void RemoveAt(int iIndex)
  2187. {
  2188. m_list.RemoveAt(iIndex);
  2189. }
  2190. public void Clear()
  2191. {
  2192. m_list.Clear();
  2193. }
  2194. public void Add(T1 First, T2 Second)
  2195. {
  2196. m_list.Add(new Pair_<T1, T2>(First, Second));
  2197. }
  2198. public void Add(Pair_<T1, T2> p)
  2199. {
  2200. m_list.Add(p);
  2201. }
  2202. public void CopyTo(IList il1, IList il2)
  2203. {
  2204. il1.Clear();
  2205. il2.Clear();
  2206. foreach (DListNote_<Pair_<T1, T2>> dn in m_list)
  2207. {
  2208. il1.Add(dn.Data.First);
  2209. il2.Add(dn.Data.First);
  2210. }
  2211. }
  2212. public int Count { get { return m_list.Count; } }
  2213. /// <summary>
  2214. /// 创建时间: ????-??-?? 最后一次修改时间:2020-05-31
  2215. /// 查找sFirstStringValue,找不到返回NULL
  2216. /// </summary>
  2217. /// <param name="sFirst"></param>
  2218. /// <returns></returns>
  2219. public Pair_<T1, T2> IndexFirst(T1 sFirstStringValue)
  2220. {
  2221. foreach (Pair_<T1, T2> p in m_list)
  2222. {
  2223. if (p.First.Equals(sFirstStringValue))
  2224. return p;
  2225. }
  2226. return null;
  2227. }
  2228. /// <summary>
  2229. /// 创建时间: ????-??-?? 最后一次修改时间:2020-05-31
  2230. /// 查找sSecondStringValue,找不到返回NULL
  2231. /// </summary>
  2232. /// <param name="sFirst"></param>
  2233. /// <returns></returns>
  2234. public Pair_<T1, T2> IndexSecond(T2 sSecondStringValue)
  2235. {
  2236. foreach (Pair_<T1, T2> p in m_list)
  2237. {
  2238. if (p.Second.Equals(sSecondStringValue))
  2239. return p;
  2240. }
  2241. return null;
  2242. }
  2243. /// <summary>
  2244. /// 创建时间: 2020-05-31 最后一次修改时间:2020-05-31
  2245. /// 查找第一项,找到返回第二项的值,没找到返回第二项的默认值。
  2246. /// </summary>
  2247. /// <param name="sFirstStringValue"></param>
  2248. /// <returns></returns>
  2249. public T2 IndexFirstValue(T1 sFirstStringValue)
  2250. {
  2251. foreach (Pair_<T1, T2> p in m_list)
  2252. {
  2253. if (p.First.Equals(sFirstStringValue))
  2254. return p.Second;
  2255. }
  2256. return default(T2);
  2257. }
  2258. /// <summary>
  2259. /// 创建时间: 2020-05-31 最后一次修改时间:2020-05-31
  2260. /// 查找第三项,找到返回第一项的值,没找到返回第一项的默认值。
  2261. /// </summary>
  2262. /// <param name="sSecondStringValue"></param>
  2263. /// <returns></returns>
  2264. public T1 IndexSecondValue(T2 sSecondStringValue)
  2265. {
  2266. foreach (Pair_<T1, T2> p in m_list)
  2267. {
  2268. if (p.Second.Equals(sSecondStringValue))
  2269. return p.First;
  2270. }
  2271. return default(T1);
  2272. }
  2273. IEnumerator IEnumerable.GetEnumerator()
  2274. {
  2275. return m_list.GetEnumerator();
  2276. }
  2277. }
  2278. public class LStringPairList : LPairList<string, string>
  2279. {
  2280. /// <summary>
  2281. /// 依据slFirst查找Second
  2282. /// </summary>
  2283. /// <param name="slFirst"></param>
  2284. /// 创建时间:2020-05-09 最后一次修改时间:2020-05-09
  2285. /// <returns></returns>
  2286. public StringList_ GetSecondList(StringList_ slFirst)
  2287. {
  2288. StringList_ slResult = new StringList_();
  2289. foreach (Pair_<string, string> p in this)
  2290. {
  2291. if (slFirst.FindNoteItem(p.First) != null)
  2292. {
  2293. slResult.Add(p.Second);
  2294. }
  2295. }
  2296. return slResult;
  2297. }
  2298. /// <summary>
  2299. /// 依据slSecond查找First
  2300. /// </summary>
  2301. /// <param name="slSecond"></param>
  2302. /// 创建时间:2020-05-09 最后一次修改时间:2020-05-09
  2303. /// <returns></returns>
  2304. public StringList_ GetFirstList(StringList_ slSecond)
  2305. {
  2306. StringList_ slResult = new StringList_();
  2307. foreach (Pair_<string, string> p in this)
  2308. {
  2309. if (slSecond.FindNoteItem(p.Second) != null)
  2310. {
  2311. slResult.Add(p.First);
  2312. }
  2313. }
  2314. return slResult;
  2315. }
  2316. }
  2317. }

3. Java 版

  1. /***************************************************************************************************
  2. 创建时间 : 2020年01月12日
  3. 文件名: : LDList.java
  4. 作者 : 李锋
  5. Email : ruizhilf@139.com
  6. 联系电话 : 13828778863
  7. 作用 : 双向链表
  8. 此文件暂时以 C# 编程风格,因为 C#也有一份代码,是从C#移植过来的。
  9. ----------------------------------------------------------------------最后一次修改时间: 2022年07月02日
  10. **************************************************************************************************/
  11. package JavaPlatform.System;
  12. import java.util.ArrayList;
  13. import java.util.Iterator;
  14. import JavaPlatform.jp;
  15. class DListNote_<T>
  16. {
  17. /**
  18. * 节点数据
  19. */
  20. public T data;
  21. /**
  22. * 前一个节点
  23. */
  24. public DListNote_<T> prev;
  25. /**
  26. * 下一个节点
  27. */
  28. public DListNote_<T> next;
  29. /**
  30. * 功能:定位节点指针。
  31. *
  32. * @param nMove 指针移动的个数,0为不变,负数是向上prev方法移动,正数是向下next移动。
  33. * @return 返回指向节点的指针 ,移动超出范围返回值为null。
  34. * 创建时间:2022/07/02 最后一次修改时间:2022/07/02
  35. */
  36. public DListNote_<T> pointerTo(int nMove)
  37. {
  38. if ( nMove >= 0){ //向下
  39. int n = 0;
  40. DListNote_<T> pTemp = this;
  41. //计数
  42. while(pTemp != null){
  43. if( n == nMove) break;
  44. pTemp = pTemp.next;
  45. ++ n;
  46. }
  47. return pTemp;
  48. }else{ //向上
  49. int n = 0;
  50. DListNote_<T> pTemp = this;
  51. //计数
  52. while(pTemp != null){
  53. if( n == - nMove ) break;
  54. pTemp = pTemp.prev;
  55. ++ n;
  56. }
  57. return pTemp;
  58. }
  59. }
  60. public DListNote_(T adata) {
  61. data = adata;
  62. }
  63. }
  64. /**
  65. * The type D list.
  66. *
  67. * @param <T> the type parameter
  68. */
  69. public class DList_<T extends Comparable<T>> implements Iterable<T>{
  70. /**
  71. * 排序方式
  72. */
  73. public enum Sortord_
  74. {
  75. s_min_max, //从小到大
  76. s_max_min, //从大到小
  77. s_null //无排序顺序
  78. }
  79. protected DListNote_<T> _first; //第一个节点
  80. protected DListNote_<T> _last; //最后一个节点
  81. protected int _count; //节点个数
  82. protected Sortord_ _sortord; //排序顺序
  83. /**
  84. * 适用于 foreach 语句
  85. * @return
  86. */
  87. public Iterator<T> iterator() {
  88. /*
  89. return new Iterator() {
  90. private int m_cursor = -1;
  91. @Override
  92. public T next() {
  93. ++m_cursor;
  94. return indexOfNote(m_cursor).data;
  95. }
  96. @Override
  97. public boolean hasNext() {
  98. return m_cursor + 1 < _count;
  99. }
  100. };*/
  101. return new DListNoteEnum_<T>(_first);
  102. }
  103. private void initData(){
  104. _count = 0;
  105. _first = null;
  106. _last = null;
  107. _sortord = Sortord_.s_null;
  108. }
  109. /**
  110. * Instantiates a new D list.
  111. */
  112. /// <summary>
  113. /// 构造函数
  114. /// </summary>
  115. public DList_() { initData(); }
  116. @SafeVarargs
  117. public DList_(T... args){
  118. initData();
  119. for( T t: args){ add(t); }
  120. }
  121. /**
  122. * Get first d list note.
  123. *
  124. * @return the d list note
  125. */
  126. public DListNote_<T> getFirst(){ return _first; }
  127. /**
  128. * Get last d list note.
  129. *
  130. * @return the d list note
  131. */
  132. public DListNote_<T> getLast(){ return _last; }
  133. /**
  134. * Get sortord sortord.
  135. *
  136. * @return the sortord
  137. */
  138. public Sortord_ getSortord(){ return _sortord; }
  139. /**
  140. * Get count int.
  141. *
  142. * @return the int
  143. */
  144. /// <summary>
  145. /// 实际包含的元素数
  146. /// </summary>
  147. public int getCount(){
  148. return _count;
  149. }
  150. /**
  151. * Add boolean.
  152. *
  153. * @param item the item
  154. * @return the boolean
  155. */
  156. /// <summary>
  157. /// 将指定集合的元素添加到末尾
  158. /// </summary>
  159. /// <param name="item">要添加到的末尾处的对象。对于引用类型,该值可以为 null</param>
  160. /// <returns>如成功,返回真,否则返回假</returns>
  161. public Boolean add(T item){
  162. if (_count == 0){
  163. _first = new DListNote_<T>(item);
  164. _first.next = null;
  165. _first.prev = null;
  166. _last = _first;
  167. }else{
  168. DListNote_ pNew = new DListNote_<T>(item);
  169. pNew.next = null;
  170. pNew.prev = _last;
  171. _last.next = pNew;
  172. _last = pNew;
  173. }
  174. ++_count;
  175. return true;
  176. }
  177. /**
  178. * Add.
  179. *
  180. * @param dList the d list
  181. */
  182. public void add(DList_<T> dList){
  183. if (dList == null){
  184. throw new NullPointerException();
  185. }
  186. DListNote_<T> ld = dList._first;
  187. while (ld != null){
  188. add(ld.data);
  189. ld = ld.next;
  190. }
  191. }
  192. /**
  193. * Index of note d list note.
  194. *
  195. * @param iPos the pos
  196. * @return the d list note
  197. */
  198. /// <summary>
  199. /// 返回索引的节点,从零开始
  200. /// </summary>
  201. /// <param name="nPos"></param>
  202. /// <returns></returns>
  203. public DListNote_<T> indexOfNote(int iPos)
  204. {
  205. if (iPos >= _count || iPos < 0) throw new IndexOutOfBoundsException();
  206. int nindex = 0;
  207. if (iPos > _count / 2)
  208. {
  209. DListNote_<T> pNote = _last;
  210. while (pNote != null)
  211. {
  212. if (nindex++ == _count - iPos - 1){ return pNote;}
  213. pNote = pNote.prev;
  214. }
  215. }
  216. else
  217. {
  218. DListNote_<T> pNote = _first;
  219. while (pNote != null)
  220. {
  221. if (nindex++ == iPos)
  222. {
  223. return pNote;
  224. }
  225. pNote = pNote.next;
  226. }
  227. }
  228. return null;
  229. }
  230. /**
  231. * Bnary search int.
  232. *
  233. * @param item the item
  234. * @return the int
  235. */
  236. /// <summary>
  237. /// 使用指定的比较器在整个已排序的 中搜索元素,并返回该元素从零开始的索引
  238. /// </summary>
  239. /// <param name="item">要定位的对象。对于引用类型,该值可以为 null。</param>
  240. /// <returns>如果找到 item,则为已排序的 的从零开始的索引;否则为-1; </returns>
  241. public int bnarySearch(T item)
  242. {
  243. switch (_sortord)
  244. {
  245. case s_max_min:
  246. {
  247. if (_count == 0)
  248. {
  249. return -1;
  250. }
  251. if (_count == 1)
  252. {
  253. return _first.data.compareTo(item) == 0 ? 0 : -1;
  254. }
  255. if (_count == 2)
  256. {
  257. if( _first.data.compareTo(item) == 0) return 0;
  258. if ( _first.next.data.compareTo(item) == 0) return 1;
  259. return -1;
  260. }
  261. int nPos = _count / 2; //nPos在中间,所以无素一定要大于等于3才行
  262. int nLeft = 0; //左边远素
  263. int nRight = _count - 1; //右边远素
  264. DListNote_<T> ld;
  265. while (nRight >= 0 && nLeft >= 0)
  266. {
  267. ld = indexOfNote(nPos);
  268. int iCom = item.compareTo(ld.data);
  269. if (iCom > 0)
  270. {
  271. if (nRight == nLeft || nPos == nLeft)
  272. {
  273. return -1;
  274. }
  275. nRight = nPos - 1;
  276. }
  277. else if (iCom < 0)
  278. {
  279. if (nRight == nLeft || nPos == nRight)
  280. {
  281. return -1;
  282. }
  283. nLeft = nPos + 1;
  284. }
  285. else
  286. {
  287. return nPos;
  288. }
  289. nPos = nLeft + (nRight - nLeft + 1) / 2;
  290. }
  291. break;
  292. }
  293. case s_min_max:
  294. {
  295. if (_count == 0)
  296. {
  297. return -1;
  298. }
  299. if (_count == 1)
  300. {
  301. return _first.data.compareTo(item) == 0 ? 0 : -1;
  302. }
  303. if (_count == 2)
  304. {
  305. if (_first.data.compareTo(item) == 0) return 0;
  306. if (_first.next.data.compareTo(item) == 0) return 1;
  307. return -1;
  308. }
  309. int nPos = (int)_count / 2; //nPos在中间,所以无素一定要大于等于3才行
  310. int nLeft = 0; //左边远素
  311. int nRight = (int)_count - 1; //右边远素
  312. DListNote_<T> ld = null;
  313. while (nRight >= 0 && nLeft >= 0)
  314. {
  315. ld = indexOfNote(nPos);
  316. int iCom = item.compareTo(ld.data);
  317. if (iCom < 0)
  318. {
  319. if (nRight == nLeft || nPos == nLeft)
  320. {
  321. return -1;
  322. }
  323. nRight = nPos - 1;
  324. }
  325. else if (iCom > 0)
  326. {
  327. if (nRight == nLeft || nPos == nRight)
  328. {
  329. return -1;
  330. }
  331. nLeft = nPos + 1;
  332. }
  333. else
  334. {
  335. return nPos;
  336. }
  337. nPos = nLeft + (nRight - nLeft + 1) / 2;
  338. }
  339. break;
  340. }
  341. case s_null:
  342. {
  343. DListNote_<T> pNote = _first;
  344. int iCount = 0;
  345. while (pNote != null)
  346. {
  347. if (pNote.data.equals(item))
  348. {
  349. return iCount;
  350. }
  351. pNote = pNote.next;
  352. ++iCount;
  353. }
  354. break;
  355. }
  356. default:
  357. {
  358. return -1;
  359. }
  360. }
  361. return -1;
  362. }
  363. /**
  364. * Contains boolean.
  365. *
  366. * @param item the item
  367. * @return the boolean
  368. */
  369. /// <summary>
  370. /// 确定某元素是否在列表中
  371. /// </summary>
  372. /// <param name="item">查找的对象。对于引用类型,该值可以为 null。</param>
  373. /// <returns>如果在列表中找到 item,则为 true,否则为 false。</returns>
  374. public boolean contains(T item)
  375. {
  376. return bnarySearch(item) != -1;
  377. }
  378. /**
  379. * Copy from.
  380. *
  381. * @param ld the ld
  382. */
  383. /// <summary>
  384. /// 复制一个链表,清除原来链表的数据
  385. /// </summary>
  386. /// <param name="ld"></param>
  387. public void copyFrom(DList_<T> ld)
  388. {
  389. if (!this.equals(ld))
  390. {
  391. clear();
  392. DListNote_<T> ldItem = ld._first;
  393. while (ldItem != null)
  394. {
  395. add(ldItem.data);
  396. ldItem = ldItem.next;
  397. }
  398. }
  399. }
  400. /*
  401. /// <summary>
  402. /// 转换成数组
  403. /// </summary>
  404. /// <returns></returns>
  405. public T[] toArray()
  406. {
  407. T[] aResult = new T[_count]; //错误: 创建泛型数组
  408. int n = 0;
  409. DListNote_ pNoteTemp = _first;
  410. while (pNoteTemp != null)
  411. {
  412. aResult[n++] = pNoteTemp.data;
  413. pNoteTemp = pNoteTemp.next;
  414. }
  415. return aResult;
  416. }
  417. */
  418. /**
  419. * Swap notedata boolean.
  420. *
  421. * @param iIndex1 the index 1
  422. * @param iIndex2 the index 2
  423. * @return the boolean
  424. */
  425. /// <summary>
  426. /// 交换两个节点的数据
  427. /// </summary>
  428. /// <param name="nIndex1"></param>
  429. /// <param name="nIndex2"></param>
  430. /// <returns></returns>
  431. public boolean swapNotedata(int iIndex1, int iIndex2)
  432. {
  433. DListNote_<T> pNote1, pNote2;
  434. pNote1 = indexOfNote(iIndex1);
  435. pNote2 = indexOfNote(iIndex2);
  436. if (!(pNote1 != null && pNote2 != null))
  437. {
  438. return false;
  439. }
  440. T pTmp = pNote1.data;
  441. pNote1.data = pNote2.data;
  442. pNote2.data = pTmp;
  443. return true;
  444. }
  445. /**
  446. * Sort selection.
  447. *
  448. * @param sortord the sortord
  449. */
  450. /// <summary>
  451. /// 选择排序可以说是最简单的一种排序方法:
  452. /// 1.找到数组中最小的那个元素
  453. /// 2.将最小的这个元素和数组中第一个元素交换位置
  454. /// 3.在剩下的元素中找到最小的的元素,与数组第二个元素交换位置
  455. /// 重复以上步骤,即可以得到有序数组。
  456. /// </summary>
  457. public void sort_selection(Sortord_ sortord)
  458. {
  459. _sortord = sortord; //已排序
  460. if (_count == 0 || _count == 1) return;
  461. DListNote_<T> min = _first, tmp = _first.next;
  462. if (sortord == Sortord_.s_min_max)
  463. {
  464. while (min.next != null)
  465. {
  466. while (tmp != null)
  467. {
  468. if ( tmp.data.compareTo(min.data) < 0) //交换位置
  469. {
  470. T pt = tmp.data;
  471. tmp.data = min.data;
  472. min.data = pt;
  473. }
  474. tmp = tmp.next;
  475. }
  476. min = min.next;
  477. tmp = min.next;
  478. }
  479. }
  480. else
  481. {
  482. while (min.next != null)
  483. {
  484. while (tmp != null)
  485. {
  486. if (tmp.data.compareTo(min.data) > 0)
  487. {
  488. T pt = tmp.data;
  489. tmp.data = min.data;
  490. min.data = pt;
  491. }
  492. tmp = tmp.next;
  493. }
  494. min = min.next;
  495. tmp = min.next;
  496. }
  497. }
  498. }
  499. /**
  500. * Inser note front d list note.
  501. *
  502. * @param pListItem the p list item
  503. * @param pData the p data
  504. * @return the d list note
  505. */
  506. /// <summary>
  507. /// 在结点pListItem前面插入一个结点,成功,返回新的结点,否则返回0
  508. /// </summary>
  509. /// <param name="pListItem"></param>
  510. /// <param name="pData"></param>
  511. /// <returns></returns>
  512. protected DListNote_ InserNoteFront(DListNote_ pListItem, T pData)
  513. {
  514. if (pListItem == null)
  515. {
  516. throw new NullPointerException();
  517. }
  518. DListNote_ pNote = new DListNote_(pData);
  519. //pNote
  520. pNote.next = pListItem;
  521. pNote.prev = pListItem.prev;
  522. //--pListItem->prev
  523. if (pListItem.prev != null)
  524. {
  525. pListItem.prev.next = pNote;
  526. }
  527. else
  528. {
  529. _first = pNote;
  530. }
  531. //pListItem
  532. pListItem.prev = pNote;
  533. ++_count;
  534. return pNote;
  535. }
  536. /**
  537. * Inser note back d list note.
  538. *
  539. * @param pListItem the p list item
  540. * @param pData the p data
  541. * @return the d list note
  542. */
  543. /// <summary>
  544. /// 在结点pListItem后面插入一个结点,成功,返回新的结点,否则返回0;
  545. /// </summary>
  546. /// <param name="pListItem"></param>
  547. /// <param name="pData"></param>
  548. /// <returns></returns>
  549. protected DListNote_ InserNoteBack(DListNote_ pListItem, T pData)
  550. {
  551. if (pListItem == null) return null;
  552. DListNote_ pNote = new DListNote_(pData);
  553. //pNote
  554. pNote.prev = pListItem;
  555. pNote.next = pListItem.next;
  556. //pListItem->next
  557. if (pListItem.next != null)
  558. {
  559. pListItem.next.prev = pNote;
  560. }
  561. else
  562. {
  563. _last = pNote;
  564. }
  565. //--pListItem
  566. pListItem.next = pNote;
  567. ++_count;
  568. return pNote;
  569. }
  570. /**
  571. * Find note item d list note.
  572. *
  573. * @param item the item
  574. * @return the d list note
  575. */
  576. /// <summary>
  577. /// 找查一个项,而不是节点,返回的这个节点相当于指针。
  578. /// </summary>
  579. /// <param name="pData">项值</param>
  580. /// <returns></returns>
  581. public DListNote_ findNoteItem(T item)
  582. {
  583. switch (_sortord)
  584. {
  585. case s_max_min:
  586. {
  587. if (_count == 0)
  588. {
  589. return null;
  590. }
  591. if (_count == 1)
  592. {
  593. return _first.data.compareTo(item) == 0 ? _first : null;
  594. }
  595. if (_count == 2)
  596. {
  597. if (_first.data.compareTo(item) == 0) return _first;
  598. if (_first.next.data.compareTo(item) == 0) return _first.next;
  599. return null;
  600. }
  601. int nPos = _count / 2; //nPos在中间,所以无素一定要大于等于3才行
  602. int nLeft = 0; //左边远素
  603. int nRight = _count - 1; //右边远素
  604. DListNote_<T> ld = null;
  605. while (nRight >= 0 && nLeft >= 0)
  606. {
  607. ld = indexOfNote(nPos);
  608. int iCom = item.compareTo(ld.data);
  609. if (iCom > 0)
  610. {
  611. if (nRight == nLeft || nPos == nLeft)
  612. {
  613. return null;
  614. }
  615. nRight = nPos - 1;
  616. }
  617. else if (iCom < 0)
  618. {
  619. if (nRight == nLeft || nPos == nRight)
  620. {
  621. return null;
  622. }
  623. nLeft = nPos + 1;
  624. }
  625. else
  626. {
  627. return ld;
  628. }
  629. nPos = nLeft + (nRight - nLeft + 1) / 2;
  630. }
  631. break;
  632. }
  633. case s_min_max:
  634. {
  635. if (_count == 0)
  636. {
  637. return null;
  638. }
  639. if (_count == 1)
  640. {
  641. return _first.data.compareTo(item) == 0 ? _first : null;
  642. }
  643. if (_count == 2)
  644. {
  645. if (_first.data.compareTo(item) == 0) return _first;
  646. if (_first.next.data.compareTo(item) == 0) return _first.next;
  647. return null;
  648. }
  649. int nPos = _count / 2; //nPos在中间,所以无素一定要大于等于3才行
  650. int nLeft = 0; //左边远素
  651. int nRight = _count - 1; //右边远素
  652. DListNote_<T> ld = null;
  653. while (nRight >= 0 && nLeft >= 0)
  654. {
  655. ld = indexOfNote(nPos);
  656. int iCom = item.compareTo(ld.data);
  657. if (iCom < 0)
  658. {
  659. if (nRight == nLeft || nPos == nLeft)
  660. {
  661. return null;
  662. }
  663. nRight = nPos - 1;
  664. }
  665. else if (iCom > 0)
  666. {
  667. if (nRight == nLeft || nPos == nRight)
  668. {
  669. return null;
  670. }
  671. nLeft = nPos + 1;
  672. }
  673. else
  674. {
  675. return ld;
  676. }
  677. nPos = nLeft + (nRight - nLeft + 1) / 2;
  678. }
  679. break;
  680. }
  681. case s_null:
  682. {
  683. DListNote_<T> pNote = _first;
  684. while (pNote != null)
  685. {
  686. //总结:Equals比较的永远是变量的内容是否相同,而= =比较的则是引用地址是否相同(前提:此种类型内部没有对Equals 或= = 进行重写操作,
  687. //否则输出可能会有不同)。string 类型是个特例,因为他的内部对这两个都进行了重写。
  688. if (item.compareTo(pNote.data) == 0)
  689. {
  690. return pNote;
  691. }
  692. /*
  693. if (pNote.data.Equals(item))
  694. {
  695. return pNote;
  696. }
  697. */
  698. pNote = pNote.next;
  699. }
  700. break;
  701. }
  702. default:
  703. {
  704. return null;
  705. }
  706. }
  707. return null;
  708. }
  709. /**
  710. * Move last boolean.
  711. *
  712. * @param iIndex the index
  713. * @return the boolean
  714. */
  715. /// <summary>
  716. /// 把索引为nIndex的节点移到最后
  717. /// </summary>
  718. /// <param name="nIndex"></param>
  719. /// <returns></returns>
  720. protected boolean moveLast(int iIndex)
  721. {
  722. DListNote_ pNote = indexOfNote(iIndex);
  723. if (pNote != null)
  724. {
  725. if (pNote == _last)
  726. return true;
  727. if (pNote == _first) //此时最少两个节点
  728. {
  729. _first = _first.next;
  730. _first.prev = null;
  731. _last.next = pNote;
  732. pNote.prev = _last;
  733. _last = pNote;
  734. }
  735. else
  736. {
  737. pNote.prev.next = pNote.next;
  738. pNote.next.prev = pNote.prev;
  739. _last.next = pNote;
  740. pNote.prev = _last;
  741. _last = pNote;
  742. }
  743. return true;
  744. }
  745. return false;
  746. }
  747. /**
  748. * Move first boolean.
  749. *
  750. * @param iIndex the index
  751. * @return the boolean
  752. */
  753. /// <summary>
  754. /// 把索引为nIndex的节点移到最前
  755. /// </summary>
  756. /// <param name="nIndex"></param>
  757. /// <returns></returns>
  758. protected boolean moveFirst(int iIndex)
  759. {
  760. DListNote_ pNote = indexOfNote(iIndex);
  761. if (pNote != null)
  762. {
  763. if (pNote == _first)
  764. return true;
  765. if (pNote == _last) //此时最少两个节点
  766. {
  767. _last.prev.next = null;
  768. _last = _last.prev;
  769. pNote.prev = null;
  770. pNote.next = _first;
  771. _first.prev = pNote;
  772. _first = pNote;
  773. }
  774. else
  775. {
  776. pNote.prev.next = pNote.next;
  777. pNote.next.prev = pNote.prev;
  778. pNote.next = _first;
  779. _first.prev = pNote;
  780. pNote.prev = null;
  781. _first = pNote;
  782. }
  783. return true;
  784. }
  785. return false;
  786. }
  787. /**
  788. * Remove item boolean.
  789. *
  790. * @param pData the p data
  791. * @return the boolean
  792. */
  793. /// <summary>
  794. /// 删除链表中的数据
  795. /// </summary>
  796. /// <param name="pData"></param>
  797. /// <returns></returns>
  798. public boolean RemoveItem(T pData)
  799. {
  800. if (_sortord == Sortord_.s_null)
  801. {
  802. DListNote_ pListItem = _first;
  803. while (pListItem != null)
  804. {
  805. if (pListItem.data.equals(pData)) //找到一项
  806. {
  807. if (pListItem == _first) //删除的是第一个节点
  808. {
  809. if (_first.next != null)
  810. {
  811. _first.next.prev = null;
  812. _first = _first.next;
  813. }
  814. else
  815. {
  816. _first = null;
  817. _last = null;
  818. }
  819. }
  820. else if (pListItem == _last) //删除的是最后一个节点
  821. {
  822. if (_last.prev != null)
  823. {
  824. _last.prev.next = null;
  825. _last = _last.prev;
  826. }
  827. else
  828. {
  829. _first = null;
  830. _last = null;
  831. }
  832. }
  833. else //删除的是中间的一个节点
  834. {
  835. pListItem.next.prev = pListItem.prev;
  836. pListItem.prev.next = pListItem.next;
  837. }
  838. --_count;
  839. return true;
  840. }
  841. pListItem = pListItem.next;
  842. }
  843. return false;
  844. }
  845. else
  846. {
  847. return removeAt(bnarySearch(pData));
  848. }
  849. }
  850. /**
  851. * Delete node boolean.
  852. *
  853. * @param pListItem the p list item
  854. * @return the boolean
  855. */
  856. /// <summary>
  857. /// 删除链表中的节点
  858. /// </summary>
  859. /// <param name="pListItem"></param>
  860. /// <returns></returns>
  861. protected boolean deleteNode(DListNote_ pListItem)
  862. {
  863. if (_count == 0 || pListItem == null)
  864. {
  865. return false;
  866. }
  867. DListNote_ pNote = _first.next;
  868. while (pNote != null)
  869. {
  870. if (pNote == pListItem) //找到了
  871. {
  872. //pListItem->prev
  873. if (pListItem.prev != null)
  874. {
  875. pListItem.prev.next = pListItem.next;
  876. }
  877. else //删除的是第一个节点
  878. {
  879. _first = pListItem.next;
  880. }
  881. //pListItem->next
  882. if (pListItem.next != null)
  883. {
  884. pListItem.next.prev = pListItem.prev;
  885. }
  886. else //删除的是最后一个节点
  887. {
  888. _last = pListItem.prev;
  889. }
  890. break;
  891. }
  892. pNote = pNote.next;
  893. }
  894. if (pNote != null)
  895. {
  896. --_count;
  897. return true;
  898. }
  899. return false;
  900. }
  901. /**
  902. * 功能:清空所有元素的所有数据,并清空链表
  903. * 创建时间:????/??/??
  904. * 最后一次修改时间:2022-07-02
  905. */
  906. public void clear(){
  907. _count = 0;
  908. DListNote_ pTemp1 = _first;
  909. while (pTemp1 != null){
  910. DListNote_ pTemp2 = pTemp1.next;
  911. pTemp1.data = null;
  912. pTemp1.next = null;
  913. pTemp1.prev = null;
  914. pTemp1 = pTemp2;
  915. }
  916. _first = null;
  917. _last = null;
  918. }
  919. /**
  920. * Remove at boolean.
  921. *
  922. * @param iIndex the index
  923. * @return the boolean
  924. */
  925. /// <summary>
  926. /// 移除指定索引处的元素
  927. /// </summary>
  928. /// <param name="iIndex">要移除的元素的从零开始的索引。</param>
  929. /// <returns>成功返回true,否则返回false</returns>
  930. public Boolean removeAt(int iIndex)
  931. {
  932. if (iIndex < 0 || iIndex + 1 > _count) { return false; }
  933. DListNote_ pNode = _first;
  934. int iCount = 0;
  935. while (pNode != null)
  936. {
  937. if (iCount == iIndex)
  938. {
  939. if (pNode == _first)
  940. {
  941. if (_first.next == null) //只有一个
  942. {
  943. clear();
  944. return true;
  945. }
  946. else
  947. {
  948. _first = _first.next;
  949. _first.prev = null;
  950. --_count;
  951. return true;
  952. }
  953. }
  954. else if (pNode == _last)
  955. {
  956. if (_last.prev == null)
  957. {
  958. clear();
  959. return true;
  960. }
  961. else
  962. {
  963. _last = _last.prev;
  964. _last.next = null;
  965. --_count;
  966. return true;
  967. }
  968. }
  969. else
  970. {
  971. pNode.prev.next = pNode.next;
  972. pNode.next.prev = pNode.prev;
  973. pNode = null;
  974. --_count;
  975. return true;
  976. }
  977. }
  978. pNode = pNode.next;
  979. ++iCount;
  980. }
  981. return false;
  982. }
  983. /**
  984. * Printlf.
  985. */
  986. public void printlf(){
  987. jp.p(toString());
  988. }
  989. /**
  990. * 功能:删除一段链表,注意:pDeleteNoteStart 一定要在链表内。
  991. *
  992. * @param pDeleteNoteStart 开始删除的位置
  993. * @param bDown 删除方向,向下还是向上,prev 为向上,next 为向上
  994. * @param nCount 要删除的个数,包括 pDeleteNoteStart
  995. * @return 返回实际删除的个数 作者:李锋 创建时间:2022/07/02 最后一次修改时间:2022/07/02
  996. */
  997. public int removeNotes(DListNote_ pDeleteNoteStart,boolean bDown,int nCount){
  998. if(_count <= 0 || nCount <= 0 || pDeleteNoteStart == null ) return 0;
  999. if(pDeleteNoteStart == _first){ //如果删除的开始位置是链表中的第一个节点
  1000. if( bDown ){ //向下
  1001. int n = 0;
  1002. DListNote_ pTemp = _first;
  1003. //计数
  1004. while(pTemp != null){
  1005. ++ n;
  1006. pTemp.data = null;
  1007. pTemp = pTemp.next;
  1008. if( n == nCount) break;
  1009. }
  1010. if(pTemp == null){
  1011. clear();
  1012. return _count;
  1013. }
  1014. else { //重新设置 _first
  1015. pTemp.prev = null;
  1016. _first = pTemp;
  1017. _count -= nCount;
  1018. return nCount;
  1019. }
  1020. }
  1021. else{ //向上,只删除一个,重新设置 _first
  1022. if(_count == 1){
  1023. clear();
  1024. }else{
  1025. -- _count;
  1026. _first.data = null;
  1027. DListNote_ pTemp = _first.next;
  1028. pTemp.prev = null;
  1029. _first = pTemp;
  1030. }
  1031. return 1;
  1032. }
  1033. }else if(pDeleteNoteStart == _last){ //如果删除的开始位置是链表中的最后一个节点
  1034. if( bDown ){ //向下,只删除一个,重新设置 _last
  1035. if(_count == 1){
  1036. clear();
  1037. }else{
  1038. -- _count;
  1039. _last.data = null;
  1040. DListNote_ pTemp = _last.prev;
  1041. pTemp.next = null;
  1042. _last = pTemp;
  1043. }
  1044. return 1;
  1045. }
  1046. else{ //向上
  1047. int n = 0;
  1048. DListNote_ pTemp = _last;
  1049. //计数
  1050. while(pTemp != null){
  1051. ++ n;
  1052. pTemp.data = null;
  1053. pTemp = pTemp.prev;
  1054. if( n == nCount) break;
  1055. }
  1056. if(pTemp == null){
  1057. clear();
  1058. return _count;
  1059. }
  1060. else { //重新设置 _last
  1061. pTemp.next = null;
  1062. _last = pTemp;
  1063. _count -= nCount;
  1064. return nCount;
  1065. }
  1066. }
  1067. }else{
  1068. if( bDown ){
  1069. int n = 0;
  1070. DListNote_ pTemp = pDeleteNoteStart;
  1071. //计数
  1072. while(pTemp != null){
  1073. ++ n;
  1074. pTemp.data = null;
  1075. pTemp = pTemp.next;
  1076. if( n == nCount) break;
  1077. }
  1078. if(pTemp == null) //_last也删掉了
  1079. {
  1080. pDeleteNoteStart.prev.next = null;
  1081. _last = pDeleteNoteStart.prev;
  1082. _count -= n;
  1083. return n; //实际删除个数
  1084. }
  1085. else {
  1086. pDeleteNoteStart.prev.next = pTemp;
  1087. pTemp.prev = pDeleteNoteStart.prev;
  1088. _count -= nCount;
  1089. return nCount;
  1090. }
  1091. }
  1092. else
  1093. {
  1094. int n = 0;
  1095. DListNote_ pTemp = pDeleteNoteStart;
  1096. //计数
  1097. while(pTemp != null){
  1098. ++ n;
  1099. pTemp.data = null;
  1100. pTemp = pTemp.prev;
  1101. if( n == nCount) break;
  1102. }
  1103. if(pTemp == null) { //_first 也删掉了
  1104. pDeleteNoteStart.next.prev = null;
  1105. _first = pDeleteNoteStart.next;
  1106. _count -= n;
  1107. return n; //实际删除个数
  1108. }
  1109. else {
  1110. pTemp.next = pDeleteNoteStart.next;
  1111. pDeleteNoteStart.next.prev = pTemp;
  1112. _count -= nCount;
  1113. return nCount;
  1114. }
  1115. }
  1116. }
  1117. }
  1118. /**
  1119. * 添加一个元素,并把它放在首位,其它元素后移,如果后面的元素删除,总无素个数不变,如果无素个数为零,则添加一个无素。
  1120. *
  1121. * @param Item the item
  1122. * @param bRemoveLast 创建时间: 2022-04-19 最后一次修改时间:2022-04-19
  1123. */
  1124. public void stackPush(T Item, boolean bRemoveLast){
  1125. if (_count == 0){
  1126. add(Item);
  1127. }
  1128. else if (_count == 1){
  1129. if (bRemoveLast){
  1130. _first.data = Item;
  1131. }
  1132. else{
  1133. //把无素放在最前
  1134. DListNote_ dnNew = new DListNote_(Item);
  1135. _first.prev = dnNew;
  1136. dnNew.next = _first;
  1137. _first = dnNew;
  1138. ++_count;
  1139. }
  1140. }
  1141. else{
  1142. if (bRemoveLast){
  1143. //删除最后一个元素
  1144. _last = _last.prev;
  1145. _last.next = null;
  1146. //把无素放在最前
  1147. DListNote_ dnNew = new DListNote_(Item);
  1148. _first.prev = dnNew;
  1149. dnNew.next = _first;
  1150. dnNew.prev = null;
  1151. _first = dnNew;
  1152. }
  1153. else {
  1154. //把无素放在最前
  1155. DListNote_ dnNew = new DListNote_(Item);
  1156. _first.prev = dnNew;
  1157. dnNew.next = _first;
  1158. dnNew.prev = null;
  1159. _first = dnNew;
  1160. ++_count;
  1161. }
  1162. }
  1163. }
  1164. /**
  1165. * Stack pop.
  1166. */
  1167. /// <summary>
  1168. /// 删除第一个元素,出栈
  1169. /// </summary>
  1170. /// 创建时间: 2022-04-19 最后一次修改时间:2022-04-19
  1171. public void stackPop(){ removeAt(0); }
  1172. /**
  1173. * To array list array list.
  1174. *
  1175. * @return the array list
  1176. */
  1177. public ArrayList<T> toArrayList(){
  1178. ArrayList<T> la = new ArrayList<T>();
  1179. for(T value : this){
  1180. la.add(value);
  1181. }
  1182. return la;
  1183. }
  1184. /**
  1185. * 功能: 转为字符串格式 类名:{ a 分隔符 b 分隔符 c }
  1186. *
  1187. * @param separator 分隔符
  1188. * @return string
  1189. * @author 李锋
  1190. * @since 创建日期 :2022-08-08,最后一次修改日期:2022-08-08
  1191. */
  1192. public String toString(String sConnector){
  1193. String info = this.getClass() + " :\t";
  1194. //info += "{";
  1195. int i = 0;
  1196. for ( T t : this) {
  1197. info += t.toString();
  1198. ++ i ;
  1199. if( i != _count)
  1200. info += sConnector;
  1201. }
  1202. //info += "}";
  1203. return info;
  1204. }
  1205. /**
  1206. * 功能: 转为字符串格式 类名:{ a , b , c }
  1207. * @return
  1208. * @since 创建日期:2022-08-08,最后一次修改日期:2022-08-08
  1209. * @author 李锋
  1210. */
  1211. @Override
  1212. public String toString() {
  1213. return toString(",");
  1214. }
  1215. }
  1216. class DListNoteEnum_<T> implements Iterator<T> {
  1217. private DListNote_<T> _dnCurr;
  1218. private int _index = -1;
  1219. public DListNoteEnum_(DListNote_<T> dn){
  1220. _dnCurr = dn;
  1221. }
  1222. @Override
  1223. public boolean hasNext() {
  1224. return _dnCurr.next != null;
  1225. }
  1226. @Override
  1227. public T next() {
  1228. ++ _index;
  1229. if( _index > 0){
  1230. _dnCurr = _dnCurr.next;
  1231. }
  1232. return _dnCurr.data;
  1233. }
  1234. }

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/运维做开发/article/detail/948499
推荐阅读
相关标签
  

闽ICP备14008679号