UNPKG

@amaui/heap

Version:
119 lines (118 loc) 5.38 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.AmauiHeap = exports.AmauiNode = void 0; const is_1 = __importDefault(require("@amaui/utils/is")); class AmauiNode { constructor(value) { this.value = value; } } exports.AmauiNode = AmauiNode; class AmauiHeap { constructor(variant = 'min') { this.variant = variant; this.values = []; } static get min() { return new AmauiHeap('min'); } static get max() { return new AmauiHeap('max'); } static make(value, variant) { return new AmauiHeap(variant).make(value); } static left(index) { return (2 * index) + 1; } static right(index) { return (2 * index) + 2; } static parent(index) { return Math.floor((index - 1) / 2); } static isPriority(index) { return index === 0; } static isLeft(index) { return !!(index !== 0 && index % 2); } static isRight(index) { return !!(index !== 0 && !(index % 2)); } static isLeaf(index, values) { return index >= Math.floor(values.length / 2) && index <= values.length - 1; } get array() { return this.values.map(item => item.value); } get first() { return this.values[0]; } get leafs() { return this.values.filter((_, index) => AmauiHeap.isLeaf(index, this.values)); } get remove() { if (!this.values.length) return; const first = this.first; const end = this.values.pop(); this.values[0] = end; // Heapify down first values value this.heapifyDown(); return first; } add(value) { const amauiNode = value instanceof AmauiNode ? value : new AmauiNode(value); // Push to the end of the values array this.values.push(amauiNode); // Heapify up the added values value this.heapifyUp(); return this; } swap(index, index1) { [this.values[index], this.values[index1]] = [this.values[index1], this.values[index]]; return this; } make(value) { this.values = value.map(value_ => value_ instanceof AmauiNode ? value_ : new AmauiNode(value_)); for (let i = Math.floor(this.values.length / 2); i >= 0; i--) { this.heapifyDown(i); } return this; } forEach(method) { if ((0, is_1.default)('function', method)) this.values.forEach((value, index) => { const parent = this.values[AmauiHeap.parent(index)]; const left = this.values[AmauiHeap.left(index)]; const right = this.values[AmauiHeap.right(index)]; const isPriority = AmauiHeap.isPriority(index); const isLeaf = AmauiHeap.isLeaf(index, this.values); const isLeft = AmauiHeap.isLeft(index); const isRight = AmauiHeap.isRight(index); method(value, index, parent, left, right, isPriority, isLeaf, isLeft, isRight); }); } heapifyUp(index_ = this.values.length - 1) { var _a, _b, _c, _d; if (this.values.length > 0) { let index = index_; let parentIndex = AmauiHeap.parent(index); while (index > 0 && (this.variant === 'min' ? ((_a = this.values[parentIndex]) === null || _a === void 0 ? void 0 : _a.value) > ((_b = this.values[index]) === null || _b === void 0 ? void 0 : _b.value) : ((_c = this.values[parentIndex]) === null || _c === void 0 ? void 0 : _c.value) < ((_d = this.values[index]) === null || _d === void 0 ? void 0 : _d.value))) { // Swap parent and child this.swap(parentIndex, index); index = parentIndex; parentIndex = AmauiHeap.parent(index); } } } heapifyDown(index_ = 0) { var _a, _b, _c, _d, _e, _f, _g, _h; if (!AmauiHeap.isLeaf(index_, this.values)) { const index = index_; const left = AmauiHeap.left(index); const right = AmauiHeap.right(index); let swapIndex = index; // Swap left and parent if swap to be made if (this.variant === 'min' ? ((_a = this.values[left]) === null || _a === void 0 ? void 0 : _a.value) < ((_b = this.values[swapIndex]) === null || _b === void 0 ? void 0 : _b.value) : ((_c = this.values[left]) === null || _c === void 0 ? void 0 : _c.value) > ((_d = this.values[swapIndex]) === null || _d === void 0 ? void 0 : _d.value)) swapIndex = left; // Swap right and parent if swap to be made if (this.variant === 'min' ? ((_e = this.values[right]) === null || _e === void 0 ? void 0 : _e.value) < ((_f = this.values[swapIndex]) === null || _f === void 0 ? void 0 : _f.value) : ((_g = this.values[right]) === null || _g === void 0 ? void 0 : _g.value) > ((_h = this.values[swapIndex]) === null || _h === void 0 ? void 0 : _h.value)) swapIndex = right; if (index !== swapIndex) { this.swap(index, swapIndex); this.heapifyDown(swapIndex); } } } } exports.AmauiHeap = AmauiHeap;