@x-oasis/recycler 0.1.20
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +25 -0
- package/dist/FixedBuffer.d.ts +14 -0
- package/dist/common.d.ts +6 -0
- package/dist/index.d.ts +32 -0
- package/dist/index.js +8 -0
- package/dist/recycler.cjs.development.js +204 -0
- package/dist/recycler.cjs.development.js.map +1 -0
- package/dist/recycler.cjs.production.min.js +2 -0
- package/dist/recycler.cjs.production.min.js.map +1 -0
- package/dist/recycler.esm.js +198 -0
- package/dist/recycler.esm.js.map +1 -0
- package/dist/types.d.ts +27 -0
- package/package.json +27 -0
- package/src/FixedBuffer.ts +54 -0
- package/src/common.ts +7 -0
- package/src/index.ts +164 -0
- package/src/types.ts +40 -0
package/README.md
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# @x-oasis/recycler
|
|
2
|
+
|
|
3
|
+
## Installation
|
|
4
|
+
|
|
5
|
+
```bash
|
|
6
|
+
$ npm i @x-oasis/recycler
|
|
7
|
+
```
|
|
8
|
+
|
|
9
|
+
## How to use
|
|
10
|
+
|
|
11
|
+
```typescript
|
|
12
|
+
import IntegerBufferSet from '@x-oasis/recycler'
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
## How to run test
|
|
16
|
+
|
|
17
|
+
```bash
|
|
18
|
+
$ pnpm test
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
## Philosophy
|
|
22
|
+
|
|
23
|
+
Basically, give an List index then get a placed position(recycler list index); In order to reuse more elements, object ref should be considered..
|
|
24
|
+
|
|
25
|
+
For Example, remove / delete / add an element, they all cause index change of original source data. but
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { SafeRange, FixedBufferProps } from './types';
|
|
2
|
+
declare class FixedBuffer {
|
|
3
|
+
private _bufferSet;
|
|
4
|
+
private _thresholdIndexValue;
|
|
5
|
+
private _recyclerType;
|
|
6
|
+
constructor(props: FixedBufferProps);
|
|
7
|
+
get thresholdIndexValue(): number;
|
|
8
|
+
get recyclerType(): string;
|
|
9
|
+
place(index: number, safeRange: SafeRange): void;
|
|
10
|
+
getMaxValue(): number;
|
|
11
|
+
getMinValue(): number;
|
|
12
|
+
getIndices(): any[];
|
|
13
|
+
}
|
|
14
|
+
export default FixedBuffer;
|
package/dist/common.d.ts
ADDED
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
export declare const DEFAULT_RECYCLER_TYPE = "__default_recycler_buffer__";
|
|
2
|
+
export declare const RECYCLER_THRESHOLD_INDEX_VALUE = 0;
|
|
3
|
+
export declare const RECYCLER_RESERVED_BUFFER_PER_BATCH = 4;
|
|
4
|
+
export declare const RECYCLER_BUFFER_SIZE = 10;
|
|
5
|
+
export declare const RECYCLER_RESERVED_BUFFER_SIZE_RATIO = 1.5;
|
|
6
|
+
export declare const defaultGetType: () => string;
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import FixedBuffer from './FixedBuffer';
|
|
2
|
+
import { RecyclerProps } from './types';
|
|
3
|
+
declare class Recycler {
|
|
4
|
+
private _queue;
|
|
5
|
+
private _thresholdIndexValue;
|
|
6
|
+
private _recyclerReservedBufferPerBatch;
|
|
7
|
+
private _recyclerBufferSize;
|
|
8
|
+
private _recyclerReservedBufferSize;
|
|
9
|
+
private _metaExtractor;
|
|
10
|
+
private _indexExtractor;
|
|
11
|
+
private _getType;
|
|
12
|
+
constructor(props?: RecyclerProps);
|
|
13
|
+
get queue(): FixedBuffer[];
|
|
14
|
+
get thresholdIndexValue(): number;
|
|
15
|
+
get recyclerReservedBufferPerBatch(): number;
|
|
16
|
+
getIndices(): any[];
|
|
17
|
+
addBuffer(type: string): FixedBuffer;
|
|
18
|
+
ensureBuffer(type: string): FixedBuffer;
|
|
19
|
+
updateIndices(props: {
|
|
20
|
+
safeRange: {
|
|
21
|
+
startIndex: number;
|
|
22
|
+
endIndex: number;
|
|
23
|
+
};
|
|
24
|
+
startIndex: number;
|
|
25
|
+
maxCount: number;
|
|
26
|
+
step: number;
|
|
27
|
+
maxIndex: number;
|
|
28
|
+
}): any;
|
|
29
|
+
getMinValue(): number;
|
|
30
|
+
getMaxValue(): number;
|
|
31
|
+
}
|
|
32
|
+
export default Recycler;
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,204 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, '__esModule', { value: true });
|
|
4
|
+
|
|
5
|
+
function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; }
|
|
6
|
+
|
|
7
|
+
var IntegerBufferSet = _interopDefault(require('@x-oasis/integer-buffer-set'));
|
|
8
|
+
|
|
9
|
+
function _defineProperties(target, props) {
|
|
10
|
+
for (var i = 0; i < props.length; i++) {
|
|
11
|
+
var descriptor = props[i];
|
|
12
|
+
descriptor.enumerable = descriptor.enumerable || false;
|
|
13
|
+
descriptor.configurable = true;
|
|
14
|
+
if ("value" in descriptor) descriptor.writable = true;
|
|
15
|
+
Object.defineProperty(target, _toPropertyKey(descriptor.key), descriptor);
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
function _createClass(Constructor, protoProps, staticProps) {
|
|
19
|
+
if (protoProps) _defineProperties(Constructor.prototype, protoProps);
|
|
20
|
+
if (staticProps) _defineProperties(Constructor, staticProps);
|
|
21
|
+
Object.defineProperty(Constructor, "prototype", {
|
|
22
|
+
writable: false
|
|
23
|
+
});
|
|
24
|
+
return Constructor;
|
|
25
|
+
}
|
|
26
|
+
function _toPrimitive(input, hint) {
|
|
27
|
+
if (typeof input !== "object" || input === null) return input;
|
|
28
|
+
var prim = input[Symbol.toPrimitive];
|
|
29
|
+
if (prim !== undefined) {
|
|
30
|
+
var res = prim.call(input, hint || "default");
|
|
31
|
+
if (typeof res !== "object") return res;
|
|
32
|
+
throw new TypeError("@@toPrimitive must return a primitive value.");
|
|
33
|
+
}
|
|
34
|
+
return (hint === "string" ? String : Number)(input);
|
|
35
|
+
}
|
|
36
|
+
function _toPropertyKey(arg) {
|
|
37
|
+
var key = _toPrimitive(arg, "string");
|
|
38
|
+
return typeof key === "symbol" ? key : String(key);
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
var DEFAULT_RECYCLER_TYPE = '__default_recycler_buffer__';
|
|
42
|
+
var RECYCLER_THRESHOLD_INDEX_VALUE = 0;
|
|
43
|
+
var RECYCLER_RESERVED_BUFFER_PER_BATCH = 4;
|
|
44
|
+
var RECYCLER_BUFFER_SIZE = 10;
|
|
45
|
+
var RECYCLER_RESERVED_BUFFER_SIZE_RATIO = 1.5;
|
|
46
|
+
|
|
47
|
+
var FixedBuffer = /*#__PURE__*/function () {
|
|
48
|
+
function FixedBuffer(props) {
|
|
49
|
+
this._thresholdIndexValue = 0;
|
|
50
|
+
var _props$thresholdIndex = props.thresholdIndexValue,
|
|
51
|
+
thresholdIndexValue = _props$thresholdIndex === void 0 ? 0 : _props$thresholdIndex,
|
|
52
|
+
_props$bufferSize = props.bufferSize,
|
|
53
|
+
bufferSize = _props$bufferSize === void 0 ? RECYCLER_BUFFER_SIZE : _props$bufferSize,
|
|
54
|
+
_props$recyclerType = props.recyclerType,
|
|
55
|
+
recyclerType = _props$recyclerType === void 0 ? DEFAULT_RECYCLER_TYPE : _props$recyclerType,
|
|
56
|
+
metaExtractor = props.metaExtractor,
|
|
57
|
+
indexExtractor = props.indexExtractor;
|
|
58
|
+
this._bufferSet = new IntegerBufferSet({
|
|
59
|
+
bufferSize: bufferSize,
|
|
60
|
+
metaExtractor: metaExtractor,
|
|
61
|
+
indexExtractor: indexExtractor,
|
|
62
|
+
name: recyclerType
|
|
63
|
+
});
|
|
64
|
+
this._recyclerType = recyclerType;
|
|
65
|
+
this._thresholdIndexValue = thresholdIndexValue;
|
|
66
|
+
}
|
|
67
|
+
var _proto = FixedBuffer.prototype;
|
|
68
|
+
_proto.place = function place(index, safeRange) {
|
|
69
|
+
this._bufferSet.getPosition(index, safeRange);
|
|
70
|
+
};
|
|
71
|
+
_proto.getMaxValue = function getMaxValue() {
|
|
72
|
+
return this._bufferSet.getMaxValue();
|
|
73
|
+
};
|
|
74
|
+
_proto.getMinValue = function getMinValue() {
|
|
75
|
+
return this._bufferSet.getMinValue();
|
|
76
|
+
};
|
|
77
|
+
_proto.getIndices = function getIndices() {
|
|
78
|
+
return this._bufferSet.getIndices();
|
|
79
|
+
};
|
|
80
|
+
_createClass(FixedBuffer, [{
|
|
81
|
+
key: "thresholdIndexValue",
|
|
82
|
+
get: function get() {
|
|
83
|
+
return this._thresholdIndexValue;
|
|
84
|
+
}
|
|
85
|
+
}, {
|
|
86
|
+
key: "recyclerType",
|
|
87
|
+
get: function get() {
|
|
88
|
+
return this._recyclerType;
|
|
89
|
+
}
|
|
90
|
+
}]);
|
|
91
|
+
return FixedBuffer;
|
|
92
|
+
}();
|
|
93
|
+
|
|
94
|
+
var Recycler = /*#__PURE__*/function () {
|
|
95
|
+
function Recycler(props) {
|
|
96
|
+
var _this = this;
|
|
97
|
+
this._queue = [];
|
|
98
|
+
this._thresholdIndexValue = 0;
|
|
99
|
+
var _ref = props || {},
|
|
100
|
+
getType = _ref.getType,
|
|
101
|
+
metaExtractor = _ref.metaExtractor,
|
|
102
|
+
indexExtractor = _ref.indexExtractor,
|
|
103
|
+
_ref$recyclerTypes = _ref.recyclerTypes,
|
|
104
|
+
recyclerTypes = _ref$recyclerTypes === void 0 ? [] : _ref$recyclerTypes,
|
|
105
|
+
_ref$recyclerBufferSi = _ref.recyclerBufferSize,
|
|
106
|
+
recyclerBufferSize = _ref$recyclerBufferSi === void 0 ? RECYCLER_BUFFER_SIZE : _ref$recyclerBufferSi,
|
|
107
|
+
_ref$thresholdIndexVa = _ref.thresholdIndexValue,
|
|
108
|
+
thresholdIndexValue = _ref$thresholdIndexVa === void 0 ? RECYCLER_THRESHOLD_INDEX_VALUE : _ref$thresholdIndexVa,
|
|
109
|
+
_ref$recyclerReserved = _ref.recyclerReservedBufferPerBatch,
|
|
110
|
+
recyclerReservedBufferPerBatch = _ref$recyclerReserved === void 0 ? RECYCLER_RESERVED_BUFFER_PER_BATCH : _ref$recyclerReserved;
|
|
111
|
+
this._metaExtractor = metaExtractor;
|
|
112
|
+
this._indexExtractor = indexExtractor;
|
|
113
|
+
this._getType = getType;
|
|
114
|
+
this._recyclerBufferSize = recyclerBufferSize;
|
|
115
|
+
this._thresholdIndexValue = thresholdIndexValue;
|
|
116
|
+
this._recyclerReservedBufferSize = Math.floor(recyclerBufferSize * RECYCLER_RESERVED_BUFFER_SIZE_RATIO);
|
|
117
|
+
this._recyclerReservedBufferPerBatch = recyclerReservedBufferPerBatch;
|
|
118
|
+
recyclerTypes.forEach(function (type) {
|
|
119
|
+
return _this.addBuffer(type);
|
|
120
|
+
});
|
|
121
|
+
}
|
|
122
|
+
var _proto = Recycler.prototype;
|
|
123
|
+
_proto.getIndices = function getIndices() {
|
|
124
|
+
return this._queue.reduce(function (acc, cur) {
|
|
125
|
+
return acc.concat(cur.getIndices());
|
|
126
|
+
}, []);
|
|
127
|
+
};
|
|
128
|
+
_proto.addBuffer = function addBuffer(type) {
|
|
129
|
+
if (!type) return null;
|
|
130
|
+
var index = this._queue.findIndex(function (buffer) {
|
|
131
|
+
return buffer.recyclerType === type;
|
|
132
|
+
});
|
|
133
|
+
if (index !== -1) return this._queue[index];
|
|
134
|
+
var buffer = new FixedBuffer({
|
|
135
|
+
recyclerType: type,
|
|
136
|
+
metaExtractor: this._metaExtractor,
|
|
137
|
+
indexExtractor: this._indexExtractor,
|
|
138
|
+
bufferSize: this._recyclerBufferSize,
|
|
139
|
+
thresholdIndexValue: this._thresholdIndexValue
|
|
140
|
+
});
|
|
141
|
+
this._queue.push(buffer);
|
|
142
|
+
return buffer;
|
|
143
|
+
};
|
|
144
|
+
_proto.ensureBuffer = function ensureBuffer(type) {
|
|
145
|
+
return this.addBuffer(type || DEFAULT_RECYCLER_TYPE);
|
|
146
|
+
};
|
|
147
|
+
_proto.updateIndices = function updateIndices(props) {
|
|
148
|
+
var _startIndex = props.startIndex,
|
|
149
|
+
safeRange = props.safeRange,
|
|
150
|
+
step = props.step,
|
|
151
|
+
maxCount = props.maxCount,
|
|
152
|
+
maxIndex = props.maxIndex;
|
|
153
|
+
var startIndex = Math.max(_startIndex, 0);
|
|
154
|
+
var count = 0;
|
|
155
|
+
if (maxCount < 0) return null;
|
|
156
|
+
for (var index = startIndex; step > 0 ? index <= maxIndex : index >= 0; index += step) {
|
|
157
|
+
if (index < this._thresholdIndexValue) continue;
|
|
158
|
+
var recyclerType = this._getType(index);
|
|
159
|
+
if (count < maxCount) {
|
|
160
|
+
var buffer = this.ensureBuffer(recyclerType);
|
|
161
|
+
buffer.place(index, safeRange);
|
|
162
|
+
} else {
|
|
163
|
+
break;
|
|
164
|
+
}
|
|
165
|
+
if (index >= this._thresholdIndexValue) count++;
|
|
166
|
+
}
|
|
167
|
+
};
|
|
168
|
+
_proto.getMinValue = function getMinValue() {
|
|
169
|
+
var minValue = Number.MAX_SAFE_INTEGER;
|
|
170
|
+
this._queue.forEach(function (buffer) {
|
|
171
|
+
var v = buffer.getMinValue();
|
|
172
|
+
if (typeof v === 'number') minValue = Math.min(v, minValue);
|
|
173
|
+
});
|
|
174
|
+
return minValue;
|
|
175
|
+
};
|
|
176
|
+
_proto.getMaxValue = function getMaxValue() {
|
|
177
|
+
var maxValue = 0;
|
|
178
|
+
this._queue.forEach(function (buffer) {
|
|
179
|
+
var v = buffer.getMaxValue();
|
|
180
|
+
if (typeof v === 'number') maxValue = Math.max(v, maxValue);
|
|
181
|
+
});
|
|
182
|
+
return maxValue;
|
|
183
|
+
};
|
|
184
|
+
_createClass(Recycler, [{
|
|
185
|
+
key: "queue",
|
|
186
|
+
get: function get() {
|
|
187
|
+
return this._queue;
|
|
188
|
+
}
|
|
189
|
+
}, {
|
|
190
|
+
key: "thresholdIndexValue",
|
|
191
|
+
get: function get() {
|
|
192
|
+
return this._thresholdIndexValue;
|
|
193
|
+
}
|
|
194
|
+
}, {
|
|
195
|
+
key: "recyclerReservedBufferPerBatch",
|
|
196
|
+
get: function get() {
|
|
197
|
+
return this._recyclerReservedBufferPerBatch;
|
|
198
|
+
}
|
|
199
|
+
}]);
|
|
200
|
+
return Recycler;
|
|
201
|
+
}();
|
|
202
|
+
|
|
203
|
+
exports.default = Recycler;
|
|
204
|
+
//# sourceMappingURL=recycler.cjs.development.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"recycler.cjs.development.js","sources":["../src/common.ts","../src/FixedBuffer.ts","../src/index.ts"],"sourcesContent":["export const DEFAULT_RECYCLER_TYPE = '__default_recycler_buffer__';\nexport const RECYCLER_THRESHOLD_INDEX_VALUE = 0;\nexport const RECYCLER_RESERVED_BUFFER_PER_BATCH = 4;\nexport const RECYCLER_BUFFER_SIZE = 10;\nexport const RECYCLER_RESERVED_BUFFER_SIZE_RATIO = 1.5;\n\nexport const defaultGetType = () => DEFAULT_RECYCLER_TYPE;\n","import IntegerBufferSet from '@x-oasis/integer-buffer-set';\nimport { SafeRange, FixedBufferProps } from './types';\nimport { DEFAULT_RECYCLER_TYPE, RECYCLER_BUFFER_SIZE } from './common';\n\nclass FixedBuffer {\n private _bufferSet: IntegerBufferSet;\n private _thresholdIndexValue = 0;\n\n private _recyclerType: string;\n\n constructor(props: FixedBufferProps) {\n const {\n thresholdIndexValue = 0,\n bufferSize = RECYCLER_BUFFER_SIZE,\n recyclerType = DEFAULT_RECYCLER_TYPE,\n metaExtractor,\n indexExtractor,\n } = props;\n this._bufferSet = new IntegerBufferSet({\n bufferSize,\n metaExtractor,\n indexExtractor,\n name: recyclerType,\n });\n this._recyclerType = recyclerType;\n this._thresholdIndexValue = thresholdIndexValue;\n }\n\n get thresholdIndexValue() {\n return this._thresholdIndexValue;\n }\n\n get recyclerType() {\n return this._recyclerType;\n }\n\n place(index: number, safeRange: SafeRange) {\n this._bufferSet.getPosition(index, safeRange);\n }\n\n getMaxValue() {\n return this._bufferSet.getMaxValue();\n }\n\n getMinValue() {\n return this._bufferSet.getMinValue();\n }\n\n getIndices() {\n return this._bufferSet.getIndices();\n }\n}\n\nexport default FixedBuffer;\n","import FixedBuffer from './FixedBuffer';\nimport { RecyclerProps } from './types';\nimport {\n DEFAULT_RECYCLER_TYPE,\n RECYCLER_BUFFER_SIZE,\n RECYCLER_RESERVED_BUFFER_PER_BATCH,\n RECYCLER_RESERVED_BUFFER_SIZE_RATIO,\n RECYCLER_THRESHOLD_INDEX_VALUE,\n} from './common';\n\nclass Recycler {\n private _queue: Array<FixedBuffer> = [];\n\n /**\n * start index\n */\n private _thresholdIndexValue = 0;\n private _recyclerReservedBufferPerBatch: number;\n /**\n * buffer size, the oversize node will run into recycle strategy\n */\n private _recyclerBufferSize: number;\n private _recyclerReservedBufferSize: number;\n private _metaExtractor: (index: number) => any;\n private _indexExtractor: (meta: any) => number;\n private _getType: (index: number) => string;\n\n constructor(props?: RecyclerProps) {\n const {\n getType,\n metaExtractor,\n indexExtractor,\n recyclerTypes = [],\n recyclerBufferSize = RECYCLER_BUFFER_SIZE,\n thresholdIndexValue = RECYCLER_THRESHOLD_INDEX_VALUE,\n recyclerReservedBufferPerBatch = RECYCLER_RESERVED_BUFFER_PER_BATCH,\n } = props || {};\n\n this._metaExtractor = metaExtractor;\n this._indexExtractor = indexExtractor;\n this._getType = getType;\n this._recyclerBufferSize = recyclerBufferSize;\n this._thresholdIndexValue = thresholdIndexValue;\n this._recyclerReservedBufferSize = Math.floor(\n recyclerBufferSize * RECYCLER_RESERVED_BUFFER_SIZE_RATIO\n );\n this._recyclerReservedBufferPerBatch = recyclerReservedBufferPerBatch;\n recyclerTypes.forEach((type) => this.addBuffer(type));\n }\n\n get queue() {\n return this._queue;\n }\n\n get thresholdIndexValue() {\n return this._thresholdIndexValue;\n }\n\n get recyclerReservedBufferPerBatch() {\n return this._recyclerReservedBufferPerBatch;\n }\n\n getIndices() {\n return this._queue.reduce((acc, cur) => acc.concat(cur.getIndices()), []);\n }\n\n addBuffer(type: string) {\n if (!type) return null;\n const index = this._queue.findIndex(\n (buffer) => buffer.recyclerType === type\n );\n if (index !== -1) return this._queue[index];\n const buffer = new FixedBuffer({\n recyclerType: type,\n metaExtractor: this._metaExtractor,\n indexExtractor: this._indexExtractor,\n bufferSize: this._recyclerBufferSize,\n thresholdIndexValue: this._thresholdIndexValue,\n });\n this._queue.push(buffer);\n return buffer;\n }\n\n ensureBuffer(type: string) {\n return this.addBuffer(type || DEFAULT_RECYCLER_TYPE);\n }\n\n updateIndices(props: {\n /**\n * index in range should not be recycled\n */\n safeRange: {\n startIndex: number;\n endIndex: number;\n };\n startIndex: number;\n maxCount: number;\n step: number;\n\n // /** the max index value, always be the length of data */\n maxIndex: number;\n }) {\n // this._queue.forEach((buffer) => buffer.start());\n const {\n startIndex: _startIndex,\n safeRange,\n step,\n maxCount,\n maxIndex,\n } = props;\n const startIndex = Math.max(_startIndex, 0);\n let count = 0;\n if (maxCount < 0) return null;\n for (\n let index = startIndex;\n step > 0 ? index <= maxIndex : index >= 0;\n index += step\n ) {\n if (index < this._thresholdIndexValue) continue;\n const recyclerType = this._getType(index);\n\n // itemLayout should not be a condition, may cause too many unLayout item\n if (count < maxCount) {\n const buffer = this.ensureBuffer(recyclerType);\n buffer.place(index, safeRange);\n } else {\n break;\n }\n\n if (index >= this._thresholdIndexValue) count++;\n }\n }\n\n getMinValue() {\n let minValue = Number.MAX_SAFE_INTEGER;\n this._queue.forEach((buffer) => {\n const v = buffer.getMinValue();\n if (typeof v === 'number') minValue = Math.min(v, minValue);\n });\n return minValue;\n }\n\n getMaxValue() {\n let maxValue = 0;\n this._queue.forEach((buffer) => {\n const v = buffer.getMaxValue();\n if (typeof v === 'number') maxValue = Math.max(v, maxValue);\n });\n return maxValue;\n }\n}\n\nexport default Recycler;\n\n// const origin = [163, 168, 142, 147, 152, 173, 178, 137, 157, 162]\n\n// const target = [163, 163, 142, 147, 152, 168, 173, 137, 157]\n\n// const next = [168, 168, 142, 147, 152, 173, 178, 137, 157, 162]\n\n// Next Sample\n// const origin = [35, 36, 37, 38, 39, 40, 41, 32, 33, 34]\n// const target = [35, 36, 37, 36, 37, 40, 41, 32, 33, 34]\n// const target = [35, 38, 39, 38, 39, 40, 41, 32, 33, 34]\n"],"names":["DEFAULT_RECYCLER_TYPE","RECYCLER_THRESHOLD_INDEX_VALUE","RECYCLER_RESERVED_BUFFER_PER_BATCH","RECYCLER_BUFFER_SIZE","RECYCLER_RESERVED_BUFFER_SIZE_RATIO","FixedBuffer","props","_props$thresholdIndex","thresholdIndexValue","_props$bufferSize","bufferSize","_props$recyclerType","recyclerType","metaExtractor","indexExtractor","_bufferSet","IntegerBufferSet","name","_recyclerType","_thresholdIndexValue","_proto","prototype","place","index","safeRange","getPosition","getMaxValue","getMinValue","getIndices","_createClass","key","get","Recycler","_ref","getType","_ref$recyclerTypes","recyclerTypes","_ref$recyclerBufferSi","recyclerBufferSize","_ref$thresholdIndexVa","_ref$recyclerReserved","recyclerReservedBufferPerBatch","_metaExtractor","_indexExtractor","_getType","_recyclerBufferSize","_recyclerReservedBufferSize","Math","floor","_recyclerReservedBufferPerBatch","forEach","type","_this","addBuffer","_queue","reduce","acc","cur","concat","findIndex","buffer","push","ensureBuffer","updateIndices","_startIndex","startIndex","step","maxCount","maxIndex","max","count","minValue","Number","MAX_SAFE_INTEGER","v","min","maxValue"],"mappings":"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"}
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,"__esModule",{value:!0});var e,r=(e=require("@x-oasis/integer-buffer-set"))&&"object"==typeof e&&"default"in e?e.default:e;function t(e,r){for(var t=0;t<r.length;t++){var u=r[t];u.enumerable=u.enumerable||!1,u.configurable=!0,"value"in u&&(u.writable=!0),Object.defineProperty(e,"symbol"==typeof(n=function(e,r){if("object"!=typeof e||null===e)return e;var t=e[Symbol.toPrimitive];if(void 0!==t){var u=t.call(e,"string");if("object"!=typeof u)return u;throw new TypeError("@@toPrimitive must return a primitive value.")}return String(e)}(u.key))?n:String(n),u)}var n}function u(e,r,u){return r&&t(e.prototype,r),u&&t(e,u),Object.defineProperty(e,"prototype",{writable:!1}),e}var n=function(){function e(e){this._thresholdIndexValue=0;var t=e.thresholdIndexValue,u=void 0===t?0:t,n=e.bufferSize,i=e.recyclerType,a=void 0===i?"__default_recycler_buffer__":i;this._bufferSet=new r({bufferSize:void 0===n?10:n,metaExtractor:e.metaExtractor,indexExtractor:e.indexExtractor,name:a}),this._recyclerType=a,this._thresholdIndexValue=u}var t=e.prototype;return t.place=function(e,r){this._bufferSet.getPosition(e,r)},t.getMaxValue=function(){return this._bufferSet.getMaxValue()},t.getMinValue=function(){return this._bufferSet.getMinValue()},t.getIndices=function(){return this._bufferSet.getIndices()},u(e,[{key:"thresholdIndexValue",get:function(){return this._thresholdIndexValue}},{key:"recyclerType",get:function(){return this._recyclerType}}]),e}();exports.default=function(){function e(e){var r=this;this._queue=[],this._thresholdIndexValue=0;var t=e||{},u=t.getType,n=t.indexExtractor,i=t.recyclerTypes,a=void 0===i?[]:i,f=t.recyclerBufferSize,o=void 0===f?10:f,c=t.thresholdIndexValue,l=void 0===c?0:c,s=t.recyclerReservedBufferPerBatch,h=void 0===s?4:s;this._metaExtractor=t.metaExtractor,this._indexExtractor=n,this._getType=u,this._recyclerBufferSize=o,this._thresholdIndexValue=l,this._recyclerReservedBufferSize=Math.floor(1.5*o),this._recyclerReservedBufferPerBatch=h,a.forEach((function(e){return r.addBuffer(e)}))}var r=e.prototype;return r.getIndices=function(){return this._queue.reduce((function(e,r){return e.concat(r.getIndices())}),[])},r.addBuffer=function(e){if(!e)return null;var r=this._queue.findIndex((function(r){return r.recyclerType===e}));if(-1!==r)return this._queue[r];var t=new n({recyclerType:e,metaExtractor:this._metaExtractor,indexExtractor:this._indexExtractor,bufferSize:this._recyclerBufferSize,thresholdIndexValue:this._thresholdIndexValue});return this._queue.push(t),t},r.ensureBuffer=function(e){return this.addBuffer(e||"__default_recycler_buffer__")},r.updateIndices=function(e){var r=e.safeRange,t=e.step,u=e.maxCount,n=e.maxIndex,i=Math.max(e.startIndex,0),a=0;if(u<0)return null;for(var f=i;t>0?f<=n:f>=0;f+=t)if(!(f<this._thresholdIndexValue)){var o=this._getType(f);if(!(a<u))break;this.ensureBuffer(o).place(f,r),f>=this._thresholdIndexValue&&a++}},r.getMinValue=function(){var e=Number.MAX_SAFE_INTEGER;return this._queue.forEach((function(r){var t=r.getMinValue();"number"==typeof t&&(e=Math.min(t,e))})),e},r.getMaxValue=function(){var e=0;return this._queue.forEach((function(r){var t=r.getMaxValue();"number"==typeof t&&(e=Math.max(t,e))})),e},u(e,[{key:"queue",get:function(){return this._queue}},{key:"thresholdIndexValue",get:function(){return this._thresholdIndexValue}},{key:"recyclerReservedBufferPerBatch",get:function(){return this._recyclerReservedBufferPerBatch}}]),e}();
|
|
2
|
+
//# sourceMappingURL=recycler.cjs.production.min.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"recycler.cjs.production.min.js","sources":["../src/common.ts","../src/FixedBuffer.ts","../src/index.ts"],"sourcesContent":["export const DEFAULT_RECYCLER_TYPE = '__default_recycler_buffer__';\nexport const RECYCLER_THRESHOLD_INDEX_VALUE = 0;\nexport const RECYCLER_RESERVED_BUFFER_PER_BATCH = 4;\nexport const RECYCLER_BUFFER_SIZE = 10;\nexport const RECYCLER_RESERVED_BUFFER_SIZE_RATIO = 1.5;\n\nexport const defaultGetType = () => DEFAULT_RECYCLER_TYPE;\n","import IntegerBufferSet from '@x-oasis/integer-buffer-set';\nimport { SafeRange, FixedBufferProps } from './types';\nimport { DEFAULT_RECYCLER_TYPE, RECYCLER_BUFFER_SIZE } from './common';\n\nclass FixedBuffer {\n private _bufferSet: IntegerBufferSet;\n private _thresholdIndexValue = 0;\n\n private _recyclerType: string;\n\n constructor(props: FixedBufferProps) {\n const {\n thresholdIndexValue = 0,\n bufferSize = RECYCLER_BUFFER_SIZE,\n recyclerType = DEFAULT_RECYCLER_TYPE,\n metaExtractor,\n indexExtractor,\n } = props;\n this._bufferSet = new IntegerBufferSet({\n bufferSize,\n metaExtractor,\n indexExtractor,\n name: recyclerType,\n });\n this._recyclerType = recyclerType;\n this._thresholdIndexValue = thresholdIndexValue;\n }\n\n get thresholdIndexValue() {\n return this._thresholdIndexValue;\n }\n\n get recyclerType() {\n return this._recyclerType;\n }\n\n place(index: number, safeRange: SafeRange) {\n this._bufferSet.getPosition(index, safeRange);\n }\n\n getMaxValue() {\n return this._bufferSet.getMaxValue();\n }\n\n getMinValue() {\n return this._bufferSet.getMinValue();\n }\n\n getIndices() {\n return this._bufferSet.getIndices();\n }\n}\n\nexport default FixedBuffer;\n","import FixedBuffer from './FixedBuffer';\nimport { RecyclerProps } from './types';\nimport {\n DEFAULT_RECYCLER_TYPE,\n RECYCLER_BUFFER_SIZE,\n RECYCLER_RESERVED_BUFFER_PER_BATCH,\n RECYCLER_RESERVED_BUFFER_SIZE_RATIO,\n RECYCLER_THRESHOLD_INDEX_VALUE,\n} from './common';\n\nclass Recycler {\n private _queue: Array<FixedBuffer> = [];\n\n /**\n * start index\n */\n private _thresholdIndexValue = 0;\n private _recyclerReservedBufferPerBatch: number;\n /**\n * buffer size, the oversize node will run into recycle strategy\n */\n private _recyclerBufferSize: number;\n private _recyclerReservedBufferSize: number;\n private _metaExtractor: (index: number) => any;\n private _indexExtractor: (meta: any) => number;\n private _getType: (index: number) => string;\n\n constructor(props?: RecyclerProps) {\n const {\n getType,\n metaExtractor,\n indexExtractor,\n recyclerTypes = [],\n recyclerBufferSize = RECYCLER_BUFFER_SIZE,\n thresholdIndexValue = RECYCLER_THRESHOLD_INDEX_VALUE,\n recyclerReservedBufferPerBatch = RECYCLER_RESERVED_BUFFER_PER_BATCH,\n } = props || {};\n\n this._metaExtractor = metaExtractor;\n this._indexExtractor = indexExtractor;\n this._getType = getType;\n this._recyclerBufferSize = recyclerBufferSize;\n this._thresholdIndexValue = thresholdIndexValue;\n this._recyclerReservedBufferSize = Math.floor(\n recyclerBufferSize * RECYCLER_RESERVED_BUFFER_SIZE_RATIO\n );\n this._recyclerReservedBufferPerBatch = recyclerReservedBufferPerBatch;\n recyclerTypes.forEach((type) => this.addBuffer(type));\n }\n\n get queue() {\n return this._queue;\n }\n\n get thresholdIndexValue() {\n return this._thresholdIndexValue;\n }\n\n get recyclerReservedBufferPerBatch() {\n return this._recyclerReservedBufferPerBatch;\n }\n\n getIndices() {\n return this._queue.reduce((acc, cur) => acc.concat(cur.getIndices()), []);\n }\n\n addBuffer(type: string) {\n if (!type) return null;\n const index = this._queue.findIndex(\n (buffer) => buffer.recyclerType === type\n );\n if (index !== -1) return this._queue[index];\n const buffer = new FixedBuffer({\n recyclerType: type,\n metaExtractor: this._metaExtractor,\n indexExtractor: this._indexExtractor,\n bufferSize: this._recyclerBufferSize,\n thresholdIndexValue: this._thresholdIndexValue,\n });\n this._queue.push(buffer);\n return buffer;\n }\n\n ensureBuffer(type: string) {\n return this.addBuffer(type || DEFAULT_RECYCLER_TYPE);\n }\n\n updateIndices(props: {\n /**\n * index in range should not be recycled\n */\n safeRange: {\n startIndex: number;\n endIndex: number;\n };\n startIndex: number;\n maxCount: number;\n step: number;\n\n // /** the max index value, always be the length of data */\n maxIndex: number;\n }) {\n // this._queue.forEach((buffer) => buffer.start());\n const {\n startIndex: _startIndex,\n safeRange,\n step,\n maxCount,\n maxIndex,\n } = props;\n const startIndex = Math.max(_startIndex, 0);\n let count = 0;\n if (maxCount < 0) return null;\n for (\n let index = startIndex;\n step > 0 ? index <= maxIndex : index >= 0;\n index += step\n ) {\n if (index < this._thresholdIndexValue) continue;\n const recyclerType = this._getType(index);\n\n // itemLayout should not be a condition, may cause too many unLayout item\n if (count < maxCount) {\n const buffer = this.ensureBuffer(recyclerType);\n buffer.place(index, safeRange);\n } else {\n break;\n }\n\n if (index >= this._thresholdIndexValue) count++;\n }\n }\n\n getMinValue() {\n let minValue = Number.MAX_SAFE_INTEGER;\n this._queue.forEach((buffer) => {\n const v = buffer.getMinValue();\n if (typeof v === 'number') minValue = Math.min(v, minValue);\n });\n return minValue;\n }\n\n getMaxValue() {\n let maxValue = 0;\n this._queue.forEach((buffer) => {\n const v = buffer.getMaxValue();\n if (typeof v === 'number') maxValue = Math.max(v, maxValue);\n });\n return maxValue;\n }\n}\n\nexport default Recycler;\n\n// const origin = [163, 168, 142, 147, 152, 173, 178, 137, 157, 162]\n\n// const target = [163, 163, 142, 147, 152, 168, 173, 137, 157]\n\n// const next = [168, 168, 142, 147, 152, 173, 178, 137, 157, 162]\n\n// Next Sample\n// const origin = [35, 36, 37, 38, 39, 40, 41, 32, 33, 34]\n// const target = [35, 36, 37, 36, 37, 40, 41, 32, 33, 34]\n// const target = [35, 38, 39, 38, 39, 40, 41, 32, 33, 34]\n"],"names":["FixedBuffer","props","this","_props$thresholdIndex","thresholdIndexValue","_props$bufferSize","bufferSize","_props$recyclerType","recyclerType","_bufferSet","IntegerBufferSet","metaExtractor","indexExtractor","name","_recyclerType","_thresholdIndexValue","_proto","prototype","place","index","safeRange","getPosition","getMaxValue","getMinValue","getIndices","_createClass","key","get","Recycler","_ref","getType","_ref$recyclerTypes","recyclerTypes","_ref$recyclerBufferSi","recyclerBufferSize","_ref$thresholdIndexVa","_ref$recyclerReserved","recyclerReservedBufferPerBatch","_metaExtractor","_indexExtractor","_getType","_recyclerBufferSize","_recyclerReservedBufferSize","Math","floor","_recyclerReservedBufferPerBatch","forEach","type","_this","addBuffer","_queue","reduce","acc","cur","concat","findIndex","buffer","push","ensureBuffer","updateIndices","step","maxCount","maxIndex","startIndex","max","count","minValue","Number","MAX_SAFE_INTEGER","v","min","maxValue"],"mappings":"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"}
|
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
import IntegerBufferSet from '@x-oasis/integer-buffer-set';
|
|
2
|
+
|
|
3
|
+
function _defineProperties(target, props) {
|
|
4
|
+
for (var i = 0; i < props.length; i++) {
|
|
5
|
+
var descriptor = props[i];
|
|
6
|
+
descriptor.enumerable = descriptor.enumerable || false;
|
|
7
|
+
descriptor.configurable = true;
|
|
8
|
+
if ("value" in descriptor) descriptor.writable = true;
|
|
9
|
+
Object.defineProperty(target, _toPropertyKey(descriptor.key), descriptor);
|
|
10
|
+
}
|
|
11
|
+
}
|
|
12
|
+
function _createClass(Constructor, protoProps, staticProps) {
|
|
13
|
+
if (protoProps) _defineProperties(Constructor.prototype, protoProps);
|
|
14
|
+
if (staticProps) _defineProperties(Constructor, staticProps);
|
|
15
|
+
Object.defineProperty(Constructor, "prototype", {
|
|
16
|
+
writable: false
|
|
17
|
+
});
|
|
18
|
+
return Constructor;
|
|
19
|
+
}
|
|
20
|
+
function _toPrimitive(input, hint) {
|
|
21
|
+
if (typeof input !== "object" || input === null) return input;
|
|
22
|
+
var prim = input[Symbol.toPrimitive];
|
|
23
|
+
if (prim !== undefined) {
|
|
24
|
+
var res = prim.call(input, hint || "default");
|
|
25
|
+
if (typeof res !== "object") return res;
|
|
26
|
+
throw new TypeError("@@toPrimitive must return a primitive value.");
|
|
27
|
+
}
|
|
28
|
+
return (hint === "string" ? String : Number)(input);
|
|
29
|
+
}
|
|
30
|
+
function _toPropertyKey(arg) {
|
|
31
|
+
var key = _toPrimitive(arg, "string");
|
|
32
|
+
return typeof key === "symbol" ? key : String(key);
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
var DEFAULT_RECYCLER_TYPE = '__default_recycler_buffer__';
|
|
36
|
+
var RECYCLER_THRESHOLD_INDEX_VALUE = 0;
|
|
37
|
+
var RECYCLER_RESERVED_BUFFER_PER_BATCH = 4;
|
|
38
|
+
var RECYCLER_BUFFER_SIZE = 10;
|
|
39
|
+
var RECYCLER_RESERVED_BUFFER_SIZE_RATIO = 1.5;
|
|
40
|
+
|
|
41
|
+
var FixedBuffer = /*#__PURE__*/function () {
|
|
42
|
+
function FixedBuffer(props) {
|
|
43
|
+
this._thresholdIndexValue = 0;
|
|
44
|
+
var _props$thresholdIndex = props.thresholdIndexValue,
|
|
45
|
+
thresholdIndexValue = _props$thresholdIndex === void 0 ? 0 : _props$thresholdIndex,
|
|
46
|
+
_props$bufferSize = props.bufferSize,
|
|
47
|
+
bufferSize = _props$bufferSize === void 0 ? RECYCLER_BUFFER_SIZE : _props$bufferSize,
|
|
48
|
+
_props$recyclerType = props.recyclerType,
|
|
49
|
+
recyclerType = _props$recyclerType === void 0 ? DEFAULT_RECYCLER_TYPE : _props$recyclerType,
|
|
50
|
+
metaExtractor = props.metaExtractor,
|
|
51
|
+
indexExtractor = props.indexExtractor;
|
|
52
|
+
this._bufferSet = new IntegerBufferSet({
|
|
53
|
+
bufferSize: bufferSize,
|
|
54
|
+
metaExtractor: metaExtractor,
|
|
55
|
+
indexExtractor: indexExtractor,
|
|
56
|
+
name: recyclerType
|
|
57
|
+
});
|
|
58
|
+
this._recyclerType = recyclerType;
|
|
59
|
+
this._thresholdIndexValue = thresholdIndexValue;
|
|
60
|
+
}
|
|
61
|
+
var _proto = FixedBuffer.prototype;
|
|
62
|
+
_proto.place = function place(index, safeRange) {
|
|
63
|
+
this._bufferSet.getPosition(index, safeRange);
|
|
64
|
+
};
|
|
65
|
+
_proto.getMaxValue = function getMaxValue() {
|
|
66
|
+
return this._bufferSet.getMaxValue();
|
|
67
|
+
};
|
|
68
|
+
_proto.getMinValue = function getMinValue() {
|
|
69
|
+
return this._bufferSet.getMinValue();
|
|
70
|
+
};
|
|
71
|
+
_proto.getIndices = function getIndices() {
|
|
72
|
+
return this._bufferSet.getIndices();
|
|
73
|
+
};
|
|
74
|
+
_createClass(FixedBuffer, [{
|
|
75
|
+
key: "thresholdIndexValue",
|
|
76
|
+
get: function get() {
|
|
77
|
+
return this._thresholdIndexValue;
|
|
78
|
+
}
|
|
79
|
+
}, {
|
|
80
|
+
key: "recyclerType",
|
|
81
|
+
get: function get() {
|
|
82
|
+
return this._recyclerType;
|
|
83
|
+
}
|
|
84
|
+
}]);
|
|
85
|
+
return FixedBuffer;
|
|
86
|
+
}();
|
|
87
|
+
|
|
88
|
+
var Recycler = /*#__PURE__*/function () {
|
|
89
|
+
function Recycler(props) {
|
|
90
|
+
var _this = this;
|
|
91
|
+
this._queue = [];
|
|
92
|
+
this._thresholdIndexValue = 0;
|
|
93
|
+
var _ref = props || {},
|
|
94
|
+
getType = _ref.getType,
|
|
95
|
+
metaExtractor = _ref.metaExtractor,
|
|
96
|
+
indexExtractor = _ref.indexExtractor,
|
|
97
|
+
_ref$recyclerTypes = _ref.recyclerTypes,
|
|
98
|
+
recyclerTypes = _ref$recyclerTypes === void 0 ? [] : _ref$recyclerTypes,
|
|
99
|
+
_ref$recyclerBufferSi = _ref.recyclerBufferSize,
|
|
100
|
+
recyclerBufferSize = _ref$recyclerBufferSi === void 0 ? RECYCLER_BUFFER_SIZE : _ref$recyclerBufferSi,
|
|
101
|
+
_ref$thresholdIndexVa = _ref.thresholdIndexValue,
|
|
102
|
+
thresholdIndexValue = _ref$thresholdIndexVa === void 0 ? RECYCLER_THRESHOLD_INDEX_VALUE : _ref$thresholdIndexVa,
|
|
103
|
+
_ref$recyclerReserved = _ref.recyclerReservedBufferPerBatch,
|
|
104
|
+
recyclerReservedBufferPerBatch = _ref$recyclerReserved === void 0 ? RECYCLER_RESERVED_BUFFER_PER_BATCH : _ref$recyclerReserved;
|
|
105
|
+
this._metaExtractor = metaExtractor;
|
|
106
|
+
this._indexExtractor = indexExtractor;
|
|
107
|
+
this._getType = getType;
|
|
108
|
+
this._recyclerBufferSize = recyclerBufferSize;
|
|
109
|
+
this._thresholdIndexValue = thresholdIndexValue;
|
|
110
|
+
this._recyclerReservedBufferSize = Math.floor(recyclerBufferSize * RECYCLER_RESERVED_BUFFER_SIZE_RATIO);
|
|
111
|
+
this._recyclerReservedBufferPerBatch = recyclerReservedBufferPerBatch;
|
|
112
|
+
recyclerTypes.forEach(function (type) {
|
|
113
|
+
return _this.addBuffer(type);
|
|
114
|
+
});
|
|
115
|
+
}
|
|
116
|
+
var _proto = Recycler.prototype;
|
|
117
|
+
_proto.getIndices = function getIndices() {
|
|
118
|
+
return this._queue.reduce(function (acc, cur) {
|
|
119
|
+
return acc.concat(cur.getIndices());
|
|
120
|
+
}, []);
|
|
121
|
+
};
|
|
122
|
+
_proto.addBuffer = function addBuffer(type) {
|
|
123
|
+
if (!type) return null;
|
|
124
|
+
var index = this._queue.findIndex(function (buffer) {
|
|
125
|
+
return buffer.recyclerType === type;
|
|
126
|
+
});
|
|
127
|
+
if (index !== -1) return this._queue[index];
|
|
128
|
+
var buffer = new FixedBuffer({
|
|
129
|
+
recyclerType: type,
|
|
130
|
+
metaExtractor: this._metaExtractor,
|
|
131
|
+
indexExtractor: this._indexExtractor,
|
|
132
|
+
bufferSize: this._recyclerBufferSize,
|
|
133
|
+
thresholdIndexValue: this._thresholdIndexValue
|
|
134
|
+
});
|
|
135
|
+
this._queue.push(buffer);
|
|
136
|
+
return buffer;
|
|
137
|
+
};
|
|
138
|
+
_proto.ensureBuffer = function ensureBuffer(type) {
|
|
139
|
+
return this.addBuffer(type || DEFAULT_RECYCLER_TYPE);
|
|
140
|
+
};
|
|
141
|
+
_proto.updateIndices = function updateIndices(props) {
|
|
142
|
+
var _startIndex = props.startIndex,
|
|
143
|
+
safeRange = props.safeRange,
|
|
144
|
+
step = props.step,
|
|
145
|
+
maxCount = props.maxCount,
|
|
146
|
+
maxIndex = props.maxIndex;
|
|
147
|
+
var startIndex = Math.max(_startIndex, 0);
|
|
148
|
+
var count = 0;
|
|
149
|
+
if (maxCount < 0) return null;
|
|
150
|
+
for (var index = startIndex; step > 0 ? index <= maxIndex : index >= 0; index += step) {
|
|
151
|
+
if (index < this._thresholdIndexValue) continue;
|
|
152
|
+
var recyclerType = this._getType(index);
|
|
153
|
+
if (count < maxCount) {
|
|
154
|
+
var buffer = this.ensureBuffer(recyclerType);
|
|
155
|
+
buffer.place(index, safeRange);
|
|
156
|
+
} else {
|
|
157
|
+
break;
|
|
158
|
+
}
|
|
159
|
+
if (index >= this._thresholdIndexValue) count++;
|
|
160
|
+
}
|
|
161
|
+
};
|
|
162
|
+
_proto.getMinValue = function getMinValue() {
|
|
163
|
+
var minValue = Number.MAX_SAFE_INTEGER;
|
|
164
|
+
this._queue.forEach(function (buffer) {
|
|
165
|
+
var v = buffer.getMinValue();
|
|
166
|
+
if (typeof v === 'number') minValue = Math.min(v, minValue);
|
|
167
|
+
});
|
|
168
|
+
return minValue;
|
|
169
|
+
};
|
|
170
|
+
_proto.getMaxValue = function getMaxValue() {
|
|
171
|
+
var maxValue = 0;
|
|
172
|
+
this._queue.forEach(function (buffer) {
|
|
173
|
+
var v = buffer.getMaxValue();
|
|
174
|
+
if (typeof v === 'number') maxValue = Math.max(v, maxValue);
|
|
175
|
+
});
|
|
176
|
+
return maxValue;
|
|
177
|
+
};
|
|
178
|
+
_createClass(Recycler, [{
|
|
179
|
+
key: "queue",
|
|
180
|
+
get: function get() {
|
|
181
|
+
return this._queue;
|
|
182
|
+
}
|
|
183
|
+
}, {
|
|
184
|
+
key: "thresholdIndexValue",
|
|
185
|
+
get: function get() {
|
|
186
|
+
return this._thresholdIndexValue;
|
|
187
|
+
}
|
|
188
|
+
}, {
|
|
189
|
+
key: "recyclerReservedBufferPerBatch",
|
|
190
|
+
get: function get() {
|
|
191
|
+
return this._recyclerReservedBufferPerBatch;
|
|
192
|
+
}
|
|
193
|
+
}]);
|
|
194
|
+
return Recycler;
|
|
195
|
+
}();
|
|
196
|
+
|
|
197
|
+
export default Recycler;
|
|
198
|
+
//# sourceMappingURL=recycler.esm.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"recycler.esm.js","sources":["../src/common.ts","../src/FixedBuffer.ts","../src/index.ts"],"sourcesContent":["export const DEFAULT_RECYCLER_TYPE = '__default_recycler_buffer__';\nexport const RECYCLER_THRESHOLD_INDEX_VALUE = 0;\nexport const RECYCLER_RESERVED_BUFFER_PER_BATCH = 4;\nexport const RECYCLER_BUFFER_SIZE = 10;\nexport const RECYCLER_RESERVED_BUFFER_SIZE_RATIO = 1.5;\n\nexport const defaultGetType = () => DEFAULT_RECYCLER_TYPE;\n","import IntegerBufferSet from '@x-oasis/integer-buffer-set';\nimport { SafeRange, FixedBufferProps } from './types';\nimport { DEFAULT_RECYCLER_TYPE, RECYCLER_BUFFER_SIZE } from './common';\n\nclass FixedBuffer {\n private _bufferSet: IntegerBufferSet;\n private _thresholdIndexValue = 0;\n\n private _recyclerType: string;\n\n constructor(props: FixedBufferProps) {\n const {\n thresholdIndexValue = 0,\n bufferSize = RECYCLER_BUFFER_SIZE,\n recyclerType = DEFAULT_RECYCLER_TYPE,\n metaExtractor,\n indexExtractor,\n } = props;\n this._bufferSet = new IntegerBufferSet({\n bufferSize,\n metaExtractor,\n indexExtractor,\n name: recyclerType,\n });\n this._recyclerType = recyclerType;\n this._thresholdIndexValue = thresholdIndexValue;\n }\n\n get thresholdIndexValue() {\n return this._thresholdIndexValue;\n }\n\n get recyclerType() {\n return this._recyclerType;\n }\n\n place(index: number, safeRange: SafeRange) {\n this._bufferSet.getPosition(index, safeRange);\n }\n\n getMaxValue() {\n return this._bufferSet.getMaxValue();\n }\n\n getMinValue() {\n return this._bufferSet.getMinValue();\n }\n\n getIndices() {\n return this._bufferSet.getIndices();\n }\n}\n\nexport default FixedBuffer;\n","import FixedBuffer from './FixedBuffer';\nimport { RecyclerProps } from './types';\nimport {\n DEFAULT_RECYCLER_TYPE,\n RECYCLER_BUFFER_SIZE,\n RECYCLER_RESERVED_BUFFER_PER_BATCH,\n RECYCLER_RESERVED_BUFFER_SIZE_RATIO,\n RECYCLER_THRESHOLD_INDEX_VALUE,\n} from './common';\n\nclass Recycler {\n private _queue: Array<FixedBuffer> = [];\n\n /**\n * start index\n */\n private _thresholdIndexValue = 0;\n private _recyclerReservedBufferPerBatch: number;\n /**\n * buffer size, the oversize node will run into recycle strategy\n */\n private _recyclerBufferSize: number;\n private _recyclerReservedBufferSize: number;\n private _metaExtractor: (index: number) => any;\n private _indexExtractor: (meta: any) => number;\n private _getType: (index: number) => string;\n\n constructor(props?: RecyclerProps) {\n const {\n getType,\n metaExtractor,\n indexExtractor,\n recyclerTypes = [],\n recyclerBufferSize = RECYCLER_BUFFER_SIZE,\n thresholdIndexValue = RECYCLER_THRESHOLD_INDEX_VALUE,\n recyclerReservedBufferPerBatch = RECYCLER_RESERVED_BUFFER_PER_BATCH,\n } = props || {};\n\n this._metaExtractor = metaExtractor;\n this._indexExtractor = indexExtractor;\n this._getType = getType;\n this._recyclerBufferSize = recyclerBufferSize;\n this._thresholdIndexValue = thresholdIndexValue;\n this._recyclerReservedBufferSize = Math.floor(\n recyclerBufferSize * RECYCLER_RESERVED_BUFFER_SIZE_RATIO\n );\n this._recyclerReservedBufferPerBatch = recyclerReservedBufferPerBatch;\n recyclerTypes.forEach((type) => this.addBuffer(type));\n }\n\n get queue() {\n return this._queue;\n }\n\n get thresholdIndexValue() {\n return this._thresholdIndexValue;\n }\n\n get recyclerReservedBufferPerBatch() {\n return this._recyclerReservedBufferPerBatch;\n }\n\n getIndices() {\n return this._queue.reduce((acc, cur) => acc.concat(cur.getIndices()), []);\n }\n\n addBuffer(type: string) {\n if (!type) return null;\n const index = this._queue.findIndex(\n (buffer) => buffer.recyclerType === type\n );\n if (index !== -1) return this._queue[index];\n const buffer = new FixedBuffer({\n recyclerType: type,\n metaExtractor: this._metaExtractor,\n indexExtractor: this._indexExtractor,\n bufferSize: this._recyclerBufferSize,\n thresholdIndexValue: this._thresholdIndexValue,\n });\n this._queue.push(buffer);\n return buffer;\n }\n\n ensureBuffer(type: string) {\n return this.addBuffer(type || DEFAULT_RECYCLER_TYPE);\n }\n\n updateIndices(props: {\n /**\n * index in range should not be recycled\n */\n safeRange: {\n startIndex: number;\n endIndex: number;\n };\n startIndex: number;\n maxCount: number;\n step: number;\n\n // /** the max index value, always be the length of data */\n maxIndex: number;\n }) {\n // this._queue.forEach((buffer) => buffer.start());\n const {\n startIndex: _startIndex,\n safeRange,\n step,\n maxCount,\n maxIndex,\n } = props;\n const startIndex = Math.max(_startIndex, 0);\n let count = 0;\n if (maxCount < 0) return null;\n for (\n let index = startIndex;\n step > 0 ? index <= maxIndex : index >= 0;\n index += step\n ) {\n if (index < this._thresholdIndexValue) continue;\n const recyclerType = this._getType(index);\n\n // itemLayout should not be a condition, may cause too many unLayout item\n if (count < maxCount) {\n const buffer = this.ensureBuffer(recyclerType);\n buffer.place(index, safeRange);\n } else {\n break;\n }\n\n if (index >= this._thresholdIndexValue) count++;\n }\n }\n\n getMinValue() {\n let minValue = Number.MAX_SAFE_INTEGER;\n this._queue.forEach((buffer) => {\n const v = buffer.getMinValue();\n if (typeof v === 'number') minValue = Math.min(v, minValue);\n });\n return minValue;\n }\n\n getMaxValue() {\n let maxValue = 0;\n this._queue.forEach((buffer) => {\n const v = buffer.getMaxValue();\n if (typeof v === 'number') maxValue = Math.max(v, maxValue);\n });\n return maxValue;\n }\n}\n\nexport default Recycler;\n\n// const origin = [163, 168, 142, 147, 152, 173, 178, 137, 157, 162]\n\n// const target = [163, 163, 142, 147, 152, 168, 173, 137, 157]\n\n// const next = [168, 168, 142, 147, 152, 173, 178, 137, 157, 162]\n\n// Next Sample\n// const origin = [35, 36, 37, 38, 39, 40, 41, 32, 33, 34]\n// const target = [35, 36, 37, 36, 37, 40, 41, 32, 33, 34]\n// const target = [35, 38, 39, 38, 39, 40, 41, 32, 33, 34]\n"],"names":["DEFAULT_RECYCLER_TYPE","RECYCLER_THRESHOLD_INDEX_VALUE","RECYCLER_RESERVED_BUFFER_PER_BATCH","RECYCLER_BUFFER_SIZE","RECYCLER_RESERVED_BUFFER_SIZE_RATIO","FixedBuffer","props","_props$thresholdIndex","thresholdIndexValue","_props$bufferSize","bufferSize","_props$recyclerType","recyclerType","metaExtractor","indexExtractor","_bufferSet","IntegerBufferSet","name","_recyclerType","_thresholdIndexValue","_proto","prototype","place","index","safeRange","getPosition","getMaxValue","getMinValue","getIndices","_createClass","key","get","Recycler","_ref","getType","_ref$recyclerTypes","recyclerTypes","_ref$recyclerBufferSi","recyclerBufferSize","_ref$thresholdIndexVa","_ref$recyclerReserved","recyclerReservedBufferPerBatch","_metaExtractor","_indexExtractor","_getType","_recyclerBufferSize","_recyclerReservedBufferSize","Math","floor","_recyclerReservedBufferPerBatch","forEach","type","_this","addBuffer","_queue","reduce","acc","cur","concat","findIndex","buffer","push","ensureBuffer","updateIndices","_startIndex","startIndex","step","maxCount","maxIndex","max","count","minValue","Number","MAX_SAFE_INTEGER","v","min","maxValue"],"mappings":"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"}
|
package/dist/types.d.ts
ADDED
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
export declare type RecyclerProps = {
|
|
2
|
+
recyclerTypes?: Array<string>;
|
|
3
|
+
recyclerBufferSize?: number;
|
|
4
|
+
thresholdIndexValue?: number;
|
|
5
|
+
recyclerReservedBufferPerBatch?: number;
|
|
6
|
+
metaExtractor?: (index: number) => any;
|
|
7
|
+
indexExtractor?: (meta: any) => number;
|
|
8
|
+
getType?: (index: number) => string;
|
|
9
|
+
};
|
|
10
|
+
export declare type SafeRange = {
|
|
11
|
+
startIndex: number;
|
|
12
|
+
endIndex: number;
|
|
13
|
+
};
|
|
14
|
+
export declare type FixedBufferProps = {
|
|
15
|
+
thresholdIndexValue?: number;
|
|
16
|
+
bufferSize?: number;
|
|
17
|
+
recyclerType?: string;
|
|
18
|
+
metaExtractor?: (index: number) => any;
|
|
19
|
+
indexExtractor?: (meta: any) => number;
|
|
20
|
+
};
|
|
21
|
+
export declare type ItemMeta = any;
|
|
22
|
+
export declare type FixedBufferStateItem = {
|
|
23
|
+
targetIndex: number;
|
|
24
|
+
recyclerKey: string;
|
|
25
|
+
itemMeta: any;
|
|
26
|
+
};
|
|
27
|
+
export declare type FixedBufferState = Array<FixedBufferStateItem>;
|
package/package.json
ADDED
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@x-oasis/recycler",
|
|
3
|
+
"version": "0.1.20",
|
|
4
|
+
"description": "IntegerBufferSet function",
|
|
5
|
+
"main": "dist/index.js",
|
|
6
|
+
"typings": "dist/index.d.ts",
|
|
7
|
+
"module": "dist/recycler.esm.js",
|
|
8
|
+
"files": [
|
|
9
|
+
"dist",
|
|
10
|
+
"index.ts",
|
|
11
|
+
"src"
|
|
12
|
+
],
|
|
13
|
+
"author": "",
|
|
14
|
+
"license": "ISC",
|
|
15
|
+
"devDependencies": {
|
|
16
|
+
"tsdx": "^0.14.1"
|
|
17
|
+
},
|
|
18
|
+
"dependencies": {
|
|
19
|
+
"@x-oasis/integer-buffer-set": "0.1.20"
|
|
20
|
+
},
|
|
21
|
+
"scripts": {
|
|
22
|
+
"build": "tsdx build --tsconfig tsconfig.build.json",
|
|
23
|
+
"clean": "rimraf ./dist",
|
|
24
|
+
"test": "vitest",
|
|
25
|
+
"compile": "tsc -p tsconfig.build.json"
|
|
26
|
+
}
|
|
27
|
+
}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import IntegerBufferSet from '@x-oasis/integer-buffer-set';
|
|
2
|
+
import { SafeRange, FixedBufferProps } from './types';
|
|
3
|
+
import { DEFAULT_RECYCLER_TYPE, RECYCLER_BUFFER_SIZE } from './common';
|
|
4
|
+
|
|
5
|
+
class FixedBuffer {
|
|
6
|
+
private _bufferSet: IntegerBufferSet;
|
|
7
|
+
private _thresholdIndexValue = 0;
|
|
8
|
+
|
|
9
|
+
private _recyclerType: string;
|
|
10
|
+
|
|
11
|
+
constructor(props: FixedBufferProps) {
|
|
12
|
+
const {
|
|
13
|
+
thresholdIndexValue = 0,
|
|
14
|
+
bufferSize = RECYCLER_BUFFER_SIZE,
|
|
15
|
+
recyclerType = DEFAULT_RECYCLER_TYPE,
|
|
16
|
+
metaExtractor,
|
|
17
|
+
indexExtractor,
|
|
18
|
+
} = props;
|
|
19
|
+
this._bufferSet = new IntegerBufferSet({
|
|
20
|
+
bufferSize,
|
|
21
|
+
metaExtractor,
|
|
22
|
+
indexExtractor,
|
|
23
|
+
name: recyclerType,
|
|
24
|
+
});
|
|
25
|
+
this._recyclerType = recyclerType;
|
|
26
|
+
this._thresholdIndexValue = thresholdIndexValue;
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
get thresholdIndexValue() {
|
|
30
|
+
return this._thresholdIndexValue;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
get recyclerType() {
|
|
34
|
+
return this._recyclerType;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
place(index: number, safeRange: SafeRange) {
|
|
38
|
+
this._bufferSet.getPosition(index, safeRange);
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
getMaxValue() {
|
|
42
|
+
return this._bufferSet.getMaxValue();
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
getMinValue() {
|
|
46
|
+
return this._bufferSet.getMinValue();
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
getIndices() {
|
|
50
|
+
return this._bufferSet.getIndices();
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
export default FixedBuffer;
|
package/src/common.ts
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
export const DEFAULT_RECYCLER_TYPE = '__default_recycler_buffer__';
|
|
2
|
+
export const RECYCLER_THRESHOLD_INDEX_VALUE = 0;
|
|
3
|
+
export const RECYCLER_RESERVED_BUFFER_PER_BATCH = 4;
|
|
4
|
+
export const RECYCLER_BUFFER_SIZE = 10;
|
|
5
|
+
export const RECYCLER_RESERVED_BUFFER_SIZE_RATIO = 1.5;
|
|
6
|
+
|
|
7
|
+
export const defaultGetType = () => DEFAULT_RECYCLER_TYPE;
|
package/src/index.ts
ADDED
|
@@ -0,0 +1,164 @@
|
|
|
1
|
+
import FixedBuffer from './FixedBuffer';
|
|
2
|
+
import { RecyclerProps } from './types';
|
|
3
|
+
import {
|
|
4
|
+
DEFAULT_RECYCLER_TYPE,
|
|
5
|
+
RECYCLER_BUFFER_SIZE,
|
|
6
|
+
RECYCLER_RESERVED_BUFFER_PER_BATCH,
|
|
7
|
+
RECYCLER_RESERVED_BUFFER_SIZE_RATIO,
|
|
8
|
+
RECYCLER_THRESHOLD_INDEX_VALUE,
|
|
9
|
+
} from './common';
|
|
10
|
+
|
|
11
|
+
class Recycler {
|
|
12
|
+
private _queue: Array<FixedBuffer> = [];
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* start index
|
|
16
|
+
*/
|
|
17
|
+
private _thresholdIndexValue = 0;
|
|
18
|
+
private _recyclerReservedBufferPerBatch: number;
|
|
19
|
+
/**
|
|
20
|
+
* buffer size, the oversize node will run into recycle strategy
|
|
21
|
+
*/
|
|
22
|
+
private _recyclerBufferSize: number;
|
|
23
|
+
private _recyclerReservedBufferSize: number;
|
|
24
|
+
private _metaExtractor: (index: number) => any;
|
|
25
|
+
private _indexExtractor: (meta: any) => number;
|
|
26
|
+
private _getType: (index: number) => string;
|
|
27
|
+
|
|
28
|
+
constructor(props?: RecyclerProps) {
|
|
29
|
+
const {
|
|
30
|
+
getType,
|
|
31
|
+
metaExtractor,
|
|
32
|
+
indexExtractor,
|
|
33
|
+
recyclerTypes = [],
|
|
34
|
+
recyclerBufferSize = RECYCLER_BUFFER_SIZE,
|
|
35
|
+
thresholdIndexValue = RECYCLER_THRESHOLD_INDEX_VALUE,
|
|
36
|
+
recyclerReservedBufferPerBatch = RECYCLER_RESERVED_BUFFER_PER_BATCH,
|
|
37
|
+
} = props || {};
|
|
38
|
+
|
|
39
|
+
this._metaExtractor = metaExtractor;
|
|
40
|
+
this._indexExtractor = indexExtractor;
|
|
41
|
+
this._getType = getType;
|
|
42
|
+
this._recyclerBufferSize = recyclerBufferSize;
|
|
43
|
+
this._thresholdIndexValue = thresholdIndexValue;
|
|
44
|
+
this._recyclerReservedBufferSize = Math.floor(
|
|
45
|
+
recyclerBufferSize * RECYCLER_RESERVED_BUFFER_SIZE_RATIO
|
|
46
|
+
);
|
|
47
|
+
this._recyclerReservedBufferPerBatch = recyclerReservedBufferPerBatch;
|
|
48
|
+
recyclerTypes.forEach((type) => this.addBuffer(type));
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
get queue() {
|
|
52
|
+
return this._queue;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
get thresholdIndexValue() {
|
|
56
|
+
return this._thresholdIndexValue;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
get recyclerReservedBufferPerBatch() {
|
|
60
|
+
return this._recyclerReservedBufferPerBatch;
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
getIndices() {
|
|
64
|
+
return this._queue.reduce((acc, cur) => acc.concat(cur.getIndices()), []);
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
addBuffer(type: string) {
|
|
68
|
+
if (!type) return null;
|
|
69
|
+
const index = this._queue.findIndex(
|
|
70
|
+
(buffer) => buffer.recyclerType === type
|
|
71
|
+
);
|
|
72
|
+
if (index !== -1) return this._queue[index];
|
|
73
|
+
const buffer = new FixedBuffer({
|
|
74
|
+
recyclerType: type,
|
|
75
|
+
metaExtractor: this._metaExtractor,
|
|
76
|
+
indexExtractor: this._indexExtractor,
|
|
77
|
+
bufferSize: this._recyclerBufferSize,
|
|
78
|
+
thresholdIndexValue: this._thresholdIndexValue,
|
|
79
|
+
});
|
|
80
|
+
this._queue.push(buffer);
|
|
81
|
+
return buffer;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
ensureBuffer(type: string) {
|
|
85
|
+
return this.addBuffer(type || DEFAULT_RECYCLER_TYPE);
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
updateIndices(props: {
|
|
89
|
+
/**
|
|
90
|
+
* index in range should not be recycled
|
|
91
|
+
*/
|
|
92
|
+
safeRange: {
|
|
93
|
+
startIndex: number;
|
|
94
|
+
endIndex: number;
|
|
95
|
+
};
|
|
96
|
+
startIndex: number;
|
|
97
|
+
maxCount: number;
|
|
98
|
+
step: number;
|
|
99
|
+
|
|
100
|
+
// /** the max index value, always be the length of data */
|
|
101
|
+
maxIndex: number;
|
|
102
|
+
}) {
|
|
103
|
+
// this._queue.forEach((buffer) => buffer.start());
|
|
104
|
+
const {
|
|
105
|
+
startIndex: _startIndex,
|
|
106
|
+
safeRange,
|
|
107
|
+
step,
|
|
108
|
+
maxCount,
|
|
109
|
+
maxIndex,
|
|
110
|
+
} = props;
|
|
111
|
+
const startIndex = Math.max(_startIndex, 0);
|
|
112
|
+
let count = 0;
|
|
113
|
+
if (maxCount < 0) return null;
|
|
114
|
+
for (
|
|
115
|
+
let index = startIndex;
|
|
116
|
+
step > 0 ? index <= maxIndex : index >= 0;
|
|
117
|
+
index += step
|
|
118
|
+
) {
|
|
119
|
+
if (index < this._thresholdIndexValue) continue;
|
|
120
|
+
const recyclerType = this._getType(index);
|
|
121
|
+
|
|
122
|
+
// itemLayout should not be a condition, may cause too many unLayout item
|
|
123
|
+
if (count < maxCount) {
|
|
124
|
+
const buffer = this.ensureBuffer(recyclerType);
|
|
125
|
+
buffer.place(index, safeRange);
|
|
126
|
+
} else {
|
|
127
|
+
break;
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
if (index >= this._thresholdIndexValue) count++;
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
getMinValue() {
|
|
135
|
+
let minValue = Number.MAX_SAFE_INTEGER;
|
|
136
|
+
this._queue.forEach((buffer) => {
|
|
137
|
+
const v = buffer.getMinValue();
|
|
138
|
+
if (typeof v === 'number') minValue = Math.min(v, minValue);
|
|
139
|
+
});
|
|
140
|
+
return minValue;
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
getMaxValue() {
|
|
144
|
+
let maxValue = 0;
|
|
145
|
+
this._queue.forEach((buffer) => {
|
|
146
|
+
const v = buffer.getMaxValue();
|
|
147
|
+
if (typeof v === 'number') maxValue = Math.max(v, maxValue);
|
|
148
|
+
});
|
|
149
|
+
return maxValue;
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
export default Recycler;
|
|
154
|
+
|
|
155
|
+
// const origin = [163, 168, 142, 147, 152, 173, 178, 137, 157, 162]
|
|
156
|
+
|
|
157
|
+
// const target = [163, 163, 142, 147, 152, 168, 173, 137, 157]
|
|
158
|
+
|
|
159
|
+
// const next = [168, 168, 142, 147, 152, 173, 178, 137, 157, 162]
|
|
160
|
+
|
|
161
|
+
// Next Sample
|
|
162
|
+
// const origin = [35, 36, 37, 38, 39, 40, 41, 32, 33, 34]
|
|
163
|
+
// const target = [35, 36, 37, 36, 37, 40, 41, 32, 33, 34]
|
|
164
|
+
// const target = [35, 38, 39, 38, 39, 40, 41, 32, 33, 34]
|
package/src/types.ts
ADDED
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
export type RecyclerProps = {
|
|
2
|
+
recyclerTypes?: Array<string>;
|
|
3
|
+
recyclerBufferSize?: number;
|
|
4
|
+
thresholdIndexValue?: number;
|
|
5
|
+
recyclerReservedBufferPerBatch?: number;
|
|
6
|
+
metaExtractor?: (index: number) => any;
|
|
7
|
+
indexExtractor?: (meta: any) => number;
|
|
8
|
+
getType?: (index: number) => string;
|
|
9
|
+
};
|
|
10
|
+
|
|
11
|
+
export type SafeRange = {
|
|
12
|
+
startIndex: number;
|
|
13
|
+
endIndex: number;
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
export type FixedBufferProps = {
|
|
17
|
+
/**
|
|
18
|
+
* index which start to replace
|
|
19
|
+
*/
|
|
20
|
+
thresholdIndexValue?: number;
|
|
21
|
+
/**
|
|
22
|
+
* max size
|
|
23
|
+
*/
|
|
24
|
+
bufferSize?: number;
|
|
25
|
+
|
|
26
|
+
recyclerType?: string;
|
|
27
|
+
|
|
28
|
+
metaExtractor?: (index: number) => any;
|
|
29
|
+
indexExtractor?: (meta: any) => number;
|
|
30
|
+
};
|
|
31
|
+
|
|
32
|
+
export type ItemMeta = any;
|
|
33
|
+
|
|
34
|
+
export type FixedBufferStateItem = {
|
|
35
|
+
targetIndex: number;
|
|
36
|
+
recyclerKey: string;
|
|
37
|
+
itemMeta: any;
|
|
38
|
+
};
|
|
39
|
+
|
|
40
|
+
export type FixedBufferState = Array<FixedBufferStateItem>;
|