1 | import { DoubleLinkListNode } from "../doublelinklist/ZKDoubleLinkListNode";
|
2 | export class DoubleLinkListCycle {
|
3 | constructor() {
|
4 | this.headNode = null;
|
5 | this.tailNode = null;
|
6 | this.size = 0;
|
7 | }
|
8 | get Size() {
|
9 | return this.size;
|
10 | }
|
11 | append(node) {
|
12 | const currentNode = new DoubleLinkListNode(node);
|
13 | if (!this.tailNode) {
|
14 | this.headNode = this.tailNode = currentNode;
|
15 | this.headNode.setNext(this.tailNode);
|
16 | this.tailNode.setPre(this.headNode);
|
17 | }
|
18 | else {
|
19 | currentNode.setPre(this.tailNode);
|
20 | currentNode.setNext(this.headNode);
|
21 | this.tailNode.setNext(currentNode);
|
22 | this.headNode.setPre(currentNode);
|
23 | this.tailNode = currentNode;
|
24 | }
|
25 | this.size++;
|
26 | return this;
|
27 | }
|
28 | prepend(node) {
|
29 | const currentNode = new DoubleLinkListNode(node);
|
30 | if (!this.headNode) {
|
31 | this.headNode = this.tailNode = currentNode;
|
32 | this.headNode.setNext(this.tailNode);
|
33 | this.tailNode.setPre(this.headNode);
|
34 | }
|
35 | else {
|
36 | this.headNode.setPre(currentNode);
|
37 | currentNode.setNext(this.headNode);
|
38 | currentNode.setPre(this.tailNode);
|
39 | this.tailNode.setNext(currentNode);
|
40 | this.headNode = currentNode;
|
41 | }
|
42 | this.size++;
|
43 | return this;
|
44 | }
|
45 | emptyList() {
|
46 | this.headNode = this.tailNode = null;
|
47 | this.size = 0;
|
48 | }
|
49 | shift() {
|
50 | const result = this.headNode;
|
51 | if (this.headNode === this.tailNode) {
|
52 | this.emptyList();
|
53 | }
|
54 | else {
|
55 | this.headNode = this.headNode.next;
|
56 | this.headNode.setPre(this.tailNode);
|
57 | this.size--;
|
58 | }
|
59 | return result;
|
60 | }
|
61 | pop() {
|
62 | const result = this.tailNode;
|
63 | if (this.headNode === this.tailNode) {
|
64 | this.emptyList();
|
65 | }
|
66 | else {
|
67 | this.tailNode = this.tailNode.Prev;
|
68 | this.tailNode.setNext(this.headNode);
|
69 | this.size--;
|
70 | }
|
71 | return result;
|
72 | }
|
73 | deleteNode(arg) {
|
74 | const deleteArr = [];
|
75 | if (this.isEmpty()) {
|
76 | return deleteArr;
|
77 | }
|
78 | let cycleNode = this.headNode;
|
79 | let index = 0;
|
80 | while (cycleNode) {
|
81 | const match = typeof arg === "function" ? arg(cycleNode.value) : (cycleNode.value === arg);
|
82 | let deleteNode = null;
|
83 | if (match) {
|
84 | if (this.headNode === this.tailNode) {
|
85 | this.emptyList();
|
86 | break;
|
87 | }
|
88 | else {
|
89 | cycleNode.Prev.setNext(cycleNode.Next);
|
90 | cycleNode.Next.setPre(cycleNode.Prev);
|
91 | }
|
92 | deleteNode = cycleNode;
|
93 | deleteArr.push(index);
|
94 | }
|
95 | cycleNode = cycleNode.Next;
|
96 | const shouldBreak = cycleNode === this.headNode;
|
97 | if (deleteNode) {
|
98 | if (deleteNode === this.headNode) {
|
99 | this.headNode = deleteNode.Next;
|
100 | }
|
101 | if (deleteNode === this.tailNode) {
|
102 | this.tailNode = deleteNode.Prev;
|
103 | }
|
104 | deleteNode.setNext(null);
|
105 | deleteNode.setPre(null);
|
106 | }
|
107 | if (shouldBreak) {
|
108 | break;
|
109 | }
|
110 | index++;
|
111 | }
|
112 | }
|
113 | findNode(arg) {
|
114 | let cycleNode = this.headNode;
|
115 | let result = null;
|
116 | while (cycleNode) {
|
117 | const match = typeof arg === "function" ? arg(cycleNode.value) : (cycleNode.value === arg);
|
118 | if (match) {
|
119 | result = cycleNode;
|
120 | break;
|
121 | }
|
122 | else if (cycleNode === this.tailNode) {
|
123 | break;
|
124 | }
|
125 | cycleNode = cycleNode.Next;
|
126 | }
|
127 | return result;
|
128 | }
|
129 | getHeadNode() {
|
130 | return this.headNode;
|
131 | }
|
132 | getTailNode() {
|
133 | return this.tailNode;
|
134 | }
|
135 | isEmpty() {
|
136 | return !this.Size;
|
137 | }
|
138 | toString() {
|
139 | let temp = this.headNode;
|
140 | const arr = [];
|
141 | while (temp) {
|
142 | arr.push(temp);
|
143 | temp = temp.Next;
|
144 | if (temp === this.headNode) {
|
145 | break;
|
146 | }
|
147 | }
|
148 | return arr.toString();
|
149 | }
|
150 | getEnumerator() {
|
151 | let temp = this.getHeadNode();
|
152 | const enumerator = {
|
153 | next: () => {
|
154 | temp = temp.Next;
|
155 | enumerator.Current = {
|
156 | value: temp.value,
|
157 | done: false,
|
158 | };
|
159 | return enumerator;
|
160 | },
|
161 | Current: {
|
162 | value: temp.value,
|
163 | done: false,
|
164 | },
|
165 | };
|
166 | return enumerator;
|
167 | }
|
168 | }
|
169 | export default DoubleLinkListCycle;
|