flat-pair 1.0.0
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/LICENSE +21 -0
- package/README.md +153 -0
- package/dist/index.d.ts +50 -0
- package/dist/index.mjs +1 -0
- package/package.json +57 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 kasukabe tsumugi
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
# flat-pair
|
|
2
|
+
|
|
3
|
+
[](https://www.npmjs.com/package/flat-pair) [](https://npmcharts.com/compare/flat-pair,token-types?start=1200&interval=30)
|
|
4
|
+
[](https://opensource.org/licenses/MIT) [](https://www.codacy.com/app/Borewit/flat-pair?utm_source=github.com&utm_medium=referral&utm_content=Borewit/flat-pair&utm_campaign=Badge_Grade)
|
|
5
|
+
|
|
6
|
+
A lightweight TypeScript library for storing key-value pairs using arrays. Provides serializable storage with efficient value-based lookups and zero-cost static methods.
|
|
7
|
+
|
|
8
|
+
For more awesome packages, check out [my homepage💛](https://baendlorel.github.io/?repoType=npm)
|
|
9
|
+
|
|
10
|
+
## Features
|
|
11
|
+
|
|
12
|
+
- 🔍 **Bidirectional Search**: Find keys by values and values by keys
|
|
13
|
+
- 📦 **Serializable**: Easy JSON serialization/deserialization
|
|
14
|
+
- 🛡️ **Type Safe**: Full TypeScript support with generic types
|
|
15
|
+
- 🎯 **Zero Cost**: Static methods available for minimal overhead
|
|
16
|
+
- ⚡ **Lightweight**: No dependencies, minimal bundle size
|
|
17
|
+
|
|
18
|
+
## Installation
|
|
19
|
+
|
|
20
|
+
```bash
|
|
21
|
+
npm install flat-pair
|
|
22
|
+
# or
|
|
23
|
+
pnpm install flat-pair
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
## Quick Start
|
|
27
|
+
|
|
28
|
+
### Using the FlatPair Class
|
|
29
|
+
|
|
30
|
+
```typescript
|
|
31
|
+
import { FlatPair } from 'flat-pair';
|
|
32
|
+
|
|
33
|
+
// Create from Map
|
|
34
|
+
const map = new Map([
|
|
35
|
+
['name', 'John'],
|
|
36
|
+
['age', 25],
|
|
37
|
+
]);
|
|
38
|
+
const flatPair = FlatPair.from(map);
|
|
39
|
+
|
|
40
|
+
// Or create directly
|
|
41
|
+
const pair = new FlatPair(['name', 'John', 'age', 25]);
|
|
42
|
+
|
|
43
|
+
// Add key-value pairs (won't add duplicates)
|
|
44
|
+
pair.add('city', 'New York');
|
|
45
|
+
pair.add('name', 'Jane'); // Won't override existing key
|
|
46
|
+
|
|
47
|
+
// Find by key
|
|
48
|
+
console.log(pair.find('name')); // 'John'
|
|
49
|
+
|
|
50
|
+
// Find by value
|
|
51
|
+
console.log(pair.findByValue('New York')); // 'city'
|
|
52
|
+
|
|
53
|
+
// Remove pairs
|
|
54
|
+
pair.remove('age'); // returns true
|
|
55
|
+
pair.remove('nonexistent'); // returns false
|
|
56
|
+
|
|
57
|
+
// Get size
|
|
58
|
+
console.log(pair.size); // 2
|
|
59
|
+
|
|
60
|
+
// Clear all
|
|
61
|
+
pair.clear();
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
### Iteration and at()
|
|
65
|
+
|
|
66
|
+
FlatPair implements iterator helpers similar to `Map` and arrays:
|
|
67
|
+
|
|
68
|
+
- `forEach()` - like normal `forEach` from Array
|
|
69
|
+
- `keys()` - returns an iterator over keys
|
|
70
|
+
- `values()` - returns an iterator over values
|
|
71
|
+
- `entries()` - returns an iterator over [key, value] pairs
|
|
72
|
+
- `Symbol.iterator` - the default iterator, same as `entries()`
|
|
73
|
+
- `at(index)` - returns the [key, value] pair at zero-based index or `undefined` if out of range
|
|
74
|
+
|
|
75
|
+
```typescript
|
|
76
|
+
// keys / values / entries
|
|
77
|
+
console.log([...fp.keys()]); // ['a','b']
|
|
78
|
+
console.log([...fp.values()]); // [1,2]
|
|
79
|
+
console.log([...fp.entries()]); // [['a',1], ['b',2]]
|
|
80
|
+
|
|
81
|
+
// default iterator
|
|
82
|
+
for (const [k, v] of fp) {
|
|
83
|
+
console.log(k, v);
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
// at
|
|
87
|
+
console.log(fp.at(0)); // ['a', 1]
|
|
88
|
+
console.log(fp.at(2)); // undefined
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
### forEach
|
|
92
|
+
|
|
93
|
+
`forEach` iterates pairs and follows the callback signature `(value, key, index, arr)` and accepts an optional `thisArg`.
|
|
94
|
+
|
|
95
|
+
```typescript
|
|
96
|
+
fp.forEach(
|
|
97
|
+
function (value, key, index, arr) {
|
|
98
|
+
console.log(index, key, value, arr === (fp as any).items);
|
|
99
|
+
},
|
|
100
|
+
{ myThis: true }
|
|
101
|
+
);
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
### Using Static Functions (Zero Cost)
|
|
105
|
+
|
|
106
|
+
```typescript
|
|
107
|
+
import { add, find, findByValue, remove, size, clear } from 'flat-pair';
|
|
108
|
+
|
|
109
|
+
const items: any[] = [];
|
|
110
|
+
|
|
111
|
+
// Add items
|
|
112
|
+
add(items, 'name', 'John');
|
|
113
|
+
add(items, 'age', 25);
|
|
114
|
+
|
|
115
|
+
// Find operations
|
|
116
|
+
const name = find(items, 'name'); // 'John'
|
|
117
|
+
const ageKey = findByValue(items, 25); // 'age'
|
|
118
|
+
|
|
119
|
+
// Remove and other operations
|
|
120
|
+
remove(items, 'age'); // returns true
|
|
121
|
+
console.log(size(items)); // 1
|
|
122
|
+
clear(items); // empties the array
|
|
123
|
+
```
|
|
124
|
+
|
|
125
|
+
### Using FlatPairOperator Class (For fixed type hint)
|
|
126
|
+
|
|
127
|
+
```typescript
|
|
128
|
+
import { FlatPairOperator } from 'flat-pair';
|
|
129
|
+
|
|
130
|
+
const operator = new FlatPairOperator<string, number>();
|
|
131
|
+
const items: any[] = [];
|
|
132
|
+
|
|
133
|
+
operator.add(items, 'score', 100);
|
|
134
|
+
operator.add(items, 'level', 5);
|
|
135
|
+
|
|
136
|
+
console.log(operator.find(items, 'score')); // 100
|
|
137
|
+
console.log(operator.findByValue(items, 5)); // 'level'
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
## Performance
|
|
141
|
+
|
|
142
|
+
FlatPair uses a simple array structure `[key1, value1, key2, value2, ...]` which provides:
|
|
143
|
+
|
|
144
|
+
- **Memory Efficiency**: No object overhead per pair
|
|
145
|
+
- **Serialization**: Direct JSON support
|
|
146
|
+
- **Cache Friendly**: Contiguous memory layout
|
|
147
|
+
- **Predictable**: O(n) operations with low constant factors
|
|
148
|
+
|
|
149
|
+
> Note: For large datasets, consider using a Map or Object for O(1) lookups instead of this package.
|
|
150
|
+
|
|
151
|
+
## License
|
|
152
|
+
|
|
153
|
+
MIT © Kasukabe Tsumugi
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
declare class FlatPair<K, V> {
|
|
2
|
+
static from<T extends Map<any, any>>(map: T): T extends Map<infer K, infer V> ? FlatPair<K, V> : never;
|
|
3
|
+
private readonly items;
|
|
4
|
+
constructor(items: any[]);
|
|
5
|
+
get size(): number;
|
|
6
|
+
/**
|
|
7
|
+
* Will check if the key already exists, if so then do nothing.
|
|
8
|
+
*/
|
|
9
|
+
add(key: K, value: V): this;
|
|
10
|
+
remove(key: K): boolean;
|
|
11
|
+
removeByValue(value: V): boolean;
|
|
12
|
+
find(key: K): V | undefined;
|
|
13
|
+
findByValue(value: V): K | undefined;
|
|
14
|
+
at(index: number): [K, V] | undefined;
|
|
15
|
+
clear(): void;
|
|
16
|
+
forEach(callback: (value: V, key: K, index: number, arr: any[]) => void, thisArg?: any): void;
|
|
17
|
+
keys(): IterableIterator<K>;
|
|
18
|
+
values(): IterableIterator<V>;
|
|
19
|
+
entries(): IterableIterator<[K, V]>;
|
|
20
|
+
[Symbol.iterator](): IterableIterator<[K, V]>;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* Creates an static operator
|
|
25
|
+
*/
|
|
26
|
+
declare class FlatPairOperator<K, V> {
|
|
27
|
+
add(items: any[], key: K, value: V): void;
|
|
28
|
+
remove(items: any[], key: K): boolean;
|
|
29
|
+
find(items: any[], key: K): V | undefined;
|
|
30
|
+
findByValue(items: any[], value: V): K | undefined;
|
|
31
|
+
removeByValue(items: any[], value: V): boolean;
|
|
32
|
+
forEach(items: any[], callback: (value: V, key: K, index: number, arr: any[]) => void, thisArg?: any): void;
|
|
33
|
+
at(items: any[], index: number): [K, V] | undefined;
|
|
34
|
+
keys(items: any[]): IterableIterator<K>;
|
|
35
|
+
values(items: any[]): IterableIterator<V>;
|
|
36
|
+
entries(items: any[]): IterableIterator<[K, V]>;
|
|
37
|
+
clear(items: any[]): void;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
declare function add<K, V>(items: any[], key: K, value: V): void;
|
|
41
|
+
declare function size(items: any[]): number;
|
|
42
|
+
declare function find<K, V>(items: any[], key: K): V | undefined;
|
|
43
|
+
declare function findByValue<K, V>(items: any[], value: V): K | undefined;
|
|
44
|
+
declare function remove<K>(items: any[], key: K): boolean;
|
|
45
|
+
declare function removeByValue<K, V>(items: any[], value: V): boolean;
|
|
46
|
+
declare function forEach<K, V>(items: any[], callback: (value: V, key: K, index: number, arr: any[]) => void, thisArg?: any): void;
|
|
47
|
+
declare function at<K, V>(items: any[], index: number): [K, V] | undefined;
|
|
48
|
+
declare function clear(items: any[]): void;
|
|
49
|
+
|
|
50
|
+
export { FlatPair, FlatPairOperator, add, at, clear, find, findByValue, forEach, remove, removeByValue, size };
|
package/dist/index.mjs
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
function t(t,r,e){for(let e=0;e<t.length;e+=2)if(t[e]===r)return;t.push(r,e)}function r(t){if(t.length%2!=0)throw new Error("Invalid items length, must be even number");return t.length/2}function e(t,r){for(let e=0;e<t.length;e+=2)if(t[e]===r)return t[e+1]}function n(t,r){for(let e=1;e<t.length;e+=2)if(t[e]===r)return t[e-1]}function i(t,r){for(let e=0;e<t.length;e+=2)if(t[e]===r)return t.splice(e,2),!0;return!1}function u(t,r){for(let e=1;e<t.length;e+=2)if(t[e]===r)return t.splice(e-1,2),!0;return!1}function o(t,r,e){let n=0;for(let i=0;i<t.length;i+=2)r.call(e,t[i+1],t[i],n,t),n++}function s(t,r){if(r<0)return;const e=2*r;return e+1>=t.length?void 0:[t[e],t[e+1]]}function f(t){t.length=0}class l{static from(t){if("[object Map]"!==Object.prototype.toString.call(t))throw new TypeError("[FlatPair: __func__] Argument must be a Map");const r=[];return t.forEach((t,e)=>r.push(e,t)),new l(r)}items=[];constructor(t){if(t.length%2!=0)throw new TypeError("FlatPair items length must be even");this.items=t}get size(){return this.items.length/2}add(r,e){return t(this.items,r,e),this}remove(t){return i(this.items,t)}removeByValue(t){return u(this.items,t)}find(t){return e(this.items,t)}findByValue(t){return n(this.items,t)}at(t){return s(this.items,t)}clear(){this.items.length=0}forEach(t,r){o(this.items,t,r)}*keys(){for(let t=0;t<this.items.length;t+=2)yield this.items[t]}*values(){for(let t=1;t<this.items.length;t+=2)yield this.items[t]}*entries(){for(let t=0;t<this.items.length;t+=2)yield[this.items[t],this.items[t+1]]}[Symbol.iterator](){return this.entries()}}class h{add(r,e,n){t(r,e,n)}remove(t,r){return i(t,r)}find(t,r){return e(t,r)}findByValue(t,r){return n(t,r)}removeByValue(t,r){return u(t,r)}forEach(t,r,e){return o(t,r,e)}at(t,r){return s(t,r)}*keys(t){for(let r=0;r<t.length;r+=2)yield t[r]}*values(t){for(let r=1;r<t.length;r+=2)yield t[r]}*entries(t){for(let r=0;r<t.length;r+=2)yield[t[r],t[r+1]]}clear(t){t.length=0}}export{l as FlatPair,h as FlatPairOperator,t as add,s as at,f as clear,e as find,n as findByValue,o as forEach,i as remove,u as removeByValue,r as size};
|
package/package.json
ADDED
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "flat-pair",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"author": {
|
|
5
|
+
"name": "Kasukabe Tsumugi",
|
|
6
|
+
"email": "futami16237@gmail.com"
|
|
7
|
+
},
|
|
8
|
+
"purpose": "npm",
|
|
9
|
+
"description": "Using array to save pairs. Serializable and easier to find, locate by value. Provide static methods, use it at 0 cost!",
|
|
10
|
+
"description_zh": "用数组来保存键值对。可序列化且更容易通过值查找、定位。提供静态方法,0成本使用!",
|
|
11
|
+
"type": "module",
|
|
12
|
+
"module": "./dist/index.mjs",
|
|
13
|
+
"types": "./dist/index.d.ts",
|
|
14
|
+
"exports": {
|
|
15
|
+
"types": "./dist/index.d.ts",
|
|
16
|
+
"import": "./dist/index.mjs",
|
|
17
|
+
"default": "./dist/index.mjs"
|
|
18
|
+
},
|
|
19
|
+
"files": [
|
|
20
|
+
"dist"
|
|
21
|
+
],
|
|
22
|
+
"homepage": "https://github.com/baendlorel/flat-pair#readme",
|
|
23
|
+
"repository": {
|
|
24
|
+
"type": "git",
|
|
25
|
+
"url": "https://github.com/baendlorel/flat-pair"
|
|
26
|
+
},
|
|
27
|
+
"keywords": [
|
|
28
|
+
"typescript",
|
|
29
|
+
"javascript"
|
|
30
|
+
],
|
|
31
|
+
"scripts": {
|
|
32
|
+
"test": "clear & vitest",
|
|
33
|
+
"lint": "oxlint .",
|
|
34
|
+
"cover": "clear & vitest --coverage",
|
|
35
|
+
"build": "node ./.scripts/rollup.mjs"
|
|
36
|
+
},
|
|
37
|
+
"license": "MIT",
|
|
38
|
+
"devDependencies": {
|
|
39
|
+
"@rollup/plugin-alias": "^5.1.1",
|
|
40
|
+
"@rollup/plugin-commonjs": "^28.0.6",
|
|
41
|
+
"@rollup/plugin-node-resolve": "^16.0.1",
|
|
42
|
+
"@rollup/plugin-replace": "^6.0.2",
|
|
43
|
+
"@rollup/plugin-terser": "^0.4.4",
|
|
44
|
+
"@rollup/plugin-typescript": "^12.1.4",
|
|
45
|
+
"@types/node": "^24.6.2",
|
|
46
|
+
"@vitest/coverage-v8": "^3.2.4",
|
|
47
|
+
"oxlint": "^1.19.0",
|
|
48
|
+
"prettier": "^3.6.2",
|
|
49
|
+
"rimraf": "^6.0.1",
|
|
50
|
+
"rollup": "^4.52.4",
|
|
51
|
+
"rollup-plugin-dts": "^6.2.3",
|
|
52
|
+
"rollup-plugin-func-macro": "^1.1.0",
|
|
53
|
+
"tslib": "^2.8.1",
|
|
54
|
+
"typescript": "^5.9.3",
|
|
55
|
+
"vitest": "^3.2.4"
|
|
56
|
+
}
|
|
57
|
+
}
|