UNPKG

arachnea

Version:

A simple api to perform array operations in a single loop

128 lines (127 loc) 3.88 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); var ActionType; (function (ActionType) { ActionType[ActionType["MAP"] = 0] = "MAP"; ActionType[ActionType["FILTER"] = 1] = "FILTER"; ActionType[ActionType["REMOVE"] = 2] = "REMOVE"; ActionType[ActionType["FOREACH"] = 3] = "FOREACH"; ActionType[ActionType["REDUCE"] = 4] = "REDUCE"; ActionType[ActionType["FIND"] = 5] = "FIND"; ActionType[ActionType["COLLECT"] = 6] = "COLLECT"; })(ActionType || (ActionType = {})); const conditionToArrayTransformer = (condition) => { if (typeof condition === 'function') { return condition; } return (ele) => ele === condition; }; class Stream { constructor(list) { this.list = list; this.actionStack = []; } map(transformer) { this.actionStack.push({ type: ActionType.MAP, transformer: transformer }); return this; } forEach(transformer) { this.actionStack.push({ type: ActionType.FOREACH, transformer: transformer, }); return this; } filter(transformer) { this.actionStack.push({ type: ActionType.FILTER, transformer: transformer, }); return this; } remove(condition) { const transformer = conditionToArrayTransformer(condition); this.actionStack.push({ type: ActionType.REMOVE, transformer, }); return this; } actionLoop(operation, interupt = { interrupted: false }) { let index = 0; let exclude = false; while (index < this.list.length) { if (interupt.interrupted) { break; } let ele = this.list[index]; exclude = false; for (let i = 0; i < this.actionStack.length; i++) { if (!this.actionStack[i]) { continue; } const action = this.actionStack[i]; switch (action.type) { case ActionType.MAP: ele = action.transformer(ele); break; case ActionType.FOREACH: action.transformer(ele); break; case ActionType.FILTER: exclude = !action.transformer(ele); break; case ActionType.REMOVE: exclude = action.transformer(ele); if (exclude) { this.actionStack[i] = null; } break; } if (exclude) { break; } } if (!exclude) { operation(ele); } index++; } } reduce(transformer, initialValue) { if (this.actionStack.length === 0) { return this.list.reduce(transformer, initialValue); } let accumulator = initialValue; this.actionLoop(ele => { accumulator = transformer(accumulator, ele); }); return accumulator; } find(condition) { const condition_ = conditionToArrayTransformer(condition); let result; let interrupt = { interrupted: false, }; this.actionLoop(ele => { if (condition_(ele)) { result = ele; interrupt.interrupted = true; } }, interrupt); return result; } collect() { let result = []; this.actionLoop(ele => { result.push(ele); }); return result; } } const stream = (arr) => new Stream(arr); exports.default = stream;