• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1/*
2 * Copyright (c) 2022 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15declare function requireNapi(s: string): any;
16interface ArkPrivate {
17  TreeSet: number;
18  Load(key: number): Object;
19}
20let flag: boolean = false;
21let fastTreeSet: Object = undefined;
22let arkPritvate: ArkPrivate = globalThis['ArkPrivate'] || undefined;
23if (arkPritvate !== undefined) {
24  fastTreeSet = arkPritvate.Load(arkPritvate.TreeSet);
25} else {
26  flag = true;
27}
28if (flag || fastTreeSet === undefined) {
29  const treeAbility = requireNapi('util.struct');
30  const errorUtil = treeAbility.errorUtil;
31  interface IterableIterator<T> {
32    next: () => {
33      value: T | undefined;
34      done: boolean;
35    };
36  }
37  class HandlerTreeSet<T> {
38    set(target: TreeSet<T>, p: string, value: string): boolean {
39      if (p in target) {
40        target[p] = value;
41        return true;
42      }
43      return false;
44    }
45    defineProperty(): boolean {
46      throw new Error(`Can't define Property on TreeSet Object`);
47    }
48    deleteProperty(): boolean {
49      throw new Error(`Can't delete Property on TreeSet Object`);
50    }
51    setPrototypeOf(): boolean {
52      throw new Error(`Can't set Prototype on TreeSet Object`);
53    }
54  }
55  class TreeSet<T> {
56    private constitute: any;
57    constructor(comparator?: (firstValue: T, secondValue: T) => boolean) {
58      errorUtil.checkNewTargetIsNullError('TreeSet', !new.target);
59      if (comparator) {
60        errorUtil.checkTypeError('comparator', 'callable', comparator);
61      }
62      this.constitute = new treeAbility.TreeClass(comparator);
63      return new Proxy(this, new HandlerTreeSet());
64    }
65    get length(): number {
66      return this.constitute.memberNumber;
67    }
68    isEmpty(): boolean {
69      errorUtil.checkBindError('isEmpty', TreeSet, this);
70      return this.constitute.isEmpty();
71    }
72    has(value: T): boolean {
73      errorUtil.checkBindError('has', TreeSet, this);
74      return this.constitute.getNode(value) !== undefined;
75    }
76    add(value: T): boolean {
77      errorUtil.checkBindError('add', TreeSet, this);
78      this.constitute.addNode(value);
79      return true;
80    }
81    remove(value: T): boolean {
82      errorUtil.checkBindError('remove', TreeSet, this);
83      let result: T = undefined;
84      result = this.constitute.removeNode(value);
85      return result !== undefined;
86    }
87    clear(): void {
88      errorUtil.checkBindError('clear', TreeSet, this);
89      this.constitute.clearTree();
90    }
91    getFirstValue(): T {
92      errorUtil.checkBindError('getFirstValue', TreeSet, this);
93      let tempNode: any = undefined;
94      tempNode = this.constitute.firstNode();
95      if (tempNode === undefined) {
96        return tempNode;
97      }
98      return tempNode.key;
99    }
100    getLastValue(): T {
101      errorUtil.checkBindError('getLastValue', TreeSet, this);
102      let tempNode: any = undefined;
103      tempNode = this.constitute.lastNode();
104      if (tempNode === undefined) {
105        return tempNode;
106      }
107      return tempNode.key;
108    }
109    getLowerValue(key: T): T {
110      errorUtil.checkBindError('getLowerValue', TreeSet, this);
111      let tempNode: any = undefined;
112      tempNode = this.constitute.getNode(key);
113      if (tempNode === undefined) {
114        return tempNode;
115      }
116      if (tempNode.left !== undefined) {
117        return tempNode.left.key;
118      }
119      let node: any = tempNode;
120      while (node.parent !== undefined) {
121        if (node.parent.right === node) {
122          return node.parent.key;
123        }
124        node = node.parent; // node.parent.left === node is true;
125      }
126      return undefined;
127    }
128    getHigherValue(key: T): T {
129      errorUtil.checkBindError('getHigherValue', TreeSet, this);
130      let tempNode: any = undefined;
131      tempNode = this.constitute.getNode(key);
132      if (tempNode === undefined) {
133        return tempNode;
134      }
135      if (tempNode.right !== undefined) {
136        return tempNode.right.key;
137      }
138      let node: any = tempNode;
139      while (node.parent !== undefined) {
140        if (node.parent.left === node) {
141          return node.parent.key;
142        }
143        node = node.parent; // node.parent.right === node is true;
144      }
145      return undefined;
146    }
147    popFirst(): T {
148      errorUtil.checkBindError('popFirst', TreeSet, this);
149      let firstNode: any = undefined;
150      firstNode = this.constitute.firstNode();
151      if (firstNode === undefined) {
152        return firstNode;
153      }
154      let value: T = firstNode.value;
155      this.constitute.removeNodeProcess(firstNode);
156      return value;
157    }
158    popLast(): T {
159      errorUtil.checkBindError('popLast', TreeSet, this);
160      let lastNode: any = undefined;
161      lastNode = this.constitute.lastNode();
162      if (lastNode === undefined) {
163        return lastNode;
164      }
165      let value: T = lastNode.value;
166      this.constitute.removeNodeProcess(lastNode);
167      return value;
168    }
169    values(): IterableIterator<T> {
170      errorUtil.checkBindError('values', TreeSet, this);
171      let data: any = this.constitute;
172      let count: number = 0;
173      return {
174        next: function (): { done: boolean, value: T } {
175          let done: boolean = false;
176          let value: T = undefined;
177          done = count >= data.memberNumber;
178          value = done ? undefined : data.keyValueArray[count].value as T;
179          count++;
180          return {
181            done: done,
182            value: value,
183          };
184        },
185      };
186    }
187    forEach(callbackfn: (value?: T, key?: T, set?: TreeSet<T>) => void,
188      thisArg?: Object): void {
189      errorUtil.checkBindError('forEach', TreeSet, this);
190      errorUtil.checkTypeError('callbackfn', 'callable', callbackfn);
191      let data: any = this.constitute;
192      let tagetArray: Array<any> = data.keyValueArray;
193      for (let i: number = 0; i < data.memberNumber; i++) {
194        callbackfn.call(thisArg, tagetArray[i].value as T, tagetArray[i].key);
195      }
196    }
197    entries(): IterableIterator<[T, T]> {
198      errorUtil.checkBindError('entries', TreeSet, this);
199      let data: any = this.constitute;
200      let count: number = 0;
201      return {
202        next: function (): { done: boolean, value: [T, T] } {
203          let done: boolean = false;
204          let value: [T, T] = undefined;
205          done = count >= data.memberNumber;
206          value = done ? undefined : data.keyValueArray[count].entry();
207          count++;
208          return {
209            done: done,
210            value: value,
211          };
212        },
213      };
214    }
215    [Symbol.iterator](): IterableIterator<T> {
216      errorUtil.checkBindError('Symbol.iterator', TreeSet, this);
217      return this.values();
218    }
219  }
220  Object.freeze(TreeSet);
221  fastTreeSet = TreeSet;
222}
223export default fastTreeSet;
224