a-js-tools 1.0.3 → 1.0.5
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/index.cjs +2 -0
- package/index.d.ts +3 -0
- package/index.mjs +1 -0
- package/package.json +1 -1
- package/src/array/difference.cjs +2 -4
- package/src/array/difference.mjs +3 -5
- package/src/array/intersection.cjs +2 -4
- package/src/array/intersection.mjs +3 -5
- package/src/array/symmetricDifference.cjs +3 -6
- package/src/array/symmetricDifference.mjs +4 -7
- package/src/array/union.cjs +4 -8
- package/src/array/union.mjs +5 -9
- package/src/className.cjs +3 -3
- package/src/className.mjs +3 -3
- package/src/getRandomString.cjs +9 -17
- package/src/getRandomString.mjs +10 -18
- package/src/object/createConstructor.cjs +44 -0
- package/src/object/createConstructor.d.ts +47 -0
- package/src/object/createConstructor.mjs +42 -0
- package/src/performance.cjs +36 -23
- package/src/performance.d.ts +9 -4
- package/src/performance.mjs +36 -23
- package/src/regexp/autoEscapedRegExp.cjs +2 -4
- package/src/regexp/autoEscapedRegExp.mjs +2 -4
- package/src/regexp/parse.cjs +3 -6
- package/src/regexp/parse.mjs +3 -6
- package/src/sleep.cjs +3 -1
- package/src/sleep.mjs +3 -1
package/index.cjs
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
+
var createConstructor = require('./src/object/createConstructor.cjs');
|
|
3
4
|
var getRandomNumber = require('./src/getRandomNumber.cjs');
|
|
4
5
|
var className = require('./src/className.cjs');
|
|
5
6
|
var getRandomString = require('./src/getRandomString.cjs');
|
|
@@ -16,6 +17,7 @@ var symmetricDifference = require('./src/array/symmetricDifference.cjs');
|
|
|
16
17
|
|
|
17
18
|
|
|
18
19
|
|
|
20
|
+
exports.createConstructor = createConstructor.createConstructor;
|
|
19
21
|
exports.getRandomFloat = getRandomNumber.getRandomFloat;
|
|
20
22
|
exports.getRandomInt = getRandomNumber.getRandomInt;
|
|
21
23
|
exports.toLowerCamelCase = className.toLowerCamelCase;
|
package/index.d.ts
CHANGED
|
@@ -1,7 +1,10 @@
|
|
|
1
|
+
import { CreateConstructor, createConstructor } from 'src/object/createConstructor';
|
|
1
2
|
export { toLowerCamelCase, toSplitCase, getRandomFloat, getRandomInt, getRandomString, } from './src/index';
|
|
2
3
|
export { throttle, debounce } from './src/performance';
|
|
3
4
|
export type { DebounceAndThrottleReturnType } from './src/performance';
|
|
4
5
|
export { escapeRegExp, autoEscapedRegExp } from './src/regexp';
|
|
5
6
|
export { isBrowser, isNode } from './src/isNode';
|
|
6
7
|
export { intersection, enArr, union, difference, symmetricDifference, } from './src/array/';
|
|
8
|
+
export { createConstructor };
|
|
9
|
+
export type { CreateConstructor };
|
|
7
10
|
export { sleep } from './src/sleep';
|
package/index.mjs
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
export { createConstructor } from './src/object/createConstructor.mjs';
|
|
1
2
|
export { getRandomFloat, getRandomInt } from './src/getRandomNumber.mjs';
|
|
2
3
|
export { toLowerCamelCase, toSplitCase } from './src/className.mjs';
|
|
3
4
|
export { getRandomString } from './src/getRandomString.mjs';
|
package/package.json
CHANGED
package/src/array/difference.cjs
CHANGED
|
@@ -34,12 +34,10 @@ var aTypeOfJs = require('a-type-of-js');
|
|
|
34
34
|
*
|
|
35
35
|
*/
|
|
36
36
|
function difference(a, b) {
|
|
37
|
-
if (!aTypeOfJs.isArray(a) || !aTypeOfJs.isArray(b))
|
|
37
|
+
if (!aTypeOfJs.isArray(a) || !aTypeOfJs.isArray(b))
|
|
38
38
|
throw new TypeError('参数需为数组');
|
|
39
|
-
|
|
40
|
-
if (a.length === 0 || b.length === 0) {
|
|
39
|
+
if (aTypeOfJs.isEmptyArray(a) || aTypeOfJs.isEmptyArray(b))
|
|
41
40
|
return a;
|
|
42
|
-
}
|
|
43
41
|
/** 获取两个数组中长度较小的 */
|
|
44
42
|
// 参数有顺序要求
|
|
45
43
|
// const [shorter, longer] = a.length > b.length ? [b, a] : [a, b];
|
package/src/array/difference.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { isArray } from 'a-type-of-js';
|
|
1
|
+
import { isArray, isEmptyArray } from 'a-type-of-js';
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* 求给出的两个数组的差值(A - B)
|
|
@@ -32,12 +32,10 @@ import { isArray } from 'a-type-of-js';
|
|
|
32
32
|
*
|
|
33
33
|
*/
|
|
34
34
|
function difference(a, b) {
|
|
35
|
-
if (!isArray(a) || !isArray(b))
|
|
35
|
+
if (!isArray(a) || !isArray(b))
|
|
36
36
|
throw new TypeError('参数需为数组');
|
|
37
|
-
|
|
38
|
-
if (a.length === 0 || b.length === 0) {
|
|
37
|
+
if (isEmptyArray(a) || isEmptyArray(b))
|
|
39
38
|
return a;
|
|
40
|
-
}
|
|
41
39
|
/** 获取两个数组中长度较小的 */
|
|
42
40
|
// 参数有顺序要求
|
|
43
41
|
// const [shorter, longer] = a.length > b.length ? [b, a] : [a, b];
|
|
@@ -24,13 +24,11 @@ var aTypeOfJs = require('a-type-of-js');
|
|
|
24
24
|
*
|
|
25
25
|
*/
|
|
26
26
|
function intersection(a, b) {
|
|
27
|
-
if (!aTypeOfJs.isArray(a) || !aTypeOfJs.isArray(b))
|
|
27
|
+
if (!aTypeOfJs.isArray(a) || !aTypeOfJs.isArray(b))
|
|
28
28
|
throw new TypeError('参数必须是数组类型数据');
|
|
29
|
-
}
|
|
30
29
|
// 任意数组为空,则返回空数组
|
|
31
|
-
if (a
|
|
30
|
+
if (aTypeOfJs.isEmptyArray(a) || aTypeOfJs.isEmptyArray(b))
|
|
32
31
|
return [];
|
|
33
|
-
}
|
|
34
32
|
/**
|
|
35
33
|
* 在实际运算中, new Set() 的 开销为 O(n) ,filter 的开销也为 O(n)
|
|
36
34
|
*
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { isArray } from 'a-type-of-js';
|
|
1
|
+
import { isArray, isEmptyArray } from 'a-type-of-js';
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
*
|
|
@@ -22,13 +22,11 @@ import { isArray } from 'a-type-of-js';
|
|
|
22
22
|
*
|
|
23
23
|
*/
|
|
24
24
|
function intersection(a, b) {
|
|
25
|
-
if (!isArray(a) || !isArray(b))
|
|
25
|
+
if (!isArray(a) || !isArray(b))
|
|
26
26
|
throw new TypeError('参数必须是数组类型数据');
|
|
27
|
-
}
|
|
28
27
|
// 任意数组为空,则返回空数组
|
|
29
|
-
if (a
|
|
28
|
+
if (isEmptyArray(a) || isEmptyArray(b))
|
|
30
29
|
return [];
|
|
31
|
-
}
|
|
32
30
|
/**
|
|
33
31
|
* 在实际运算中, new Set() 的 开销为 O(n) ,filter 的开销也为 O(n)
|
|
34
32
|
*
|
|
@@ -36,15 +36,12 @@ var difference = require('./difference.cjs');
|
|
|
36
36
|
*
|
|
37
37
|
*/
|
|
38
38
|
function symmetricDifference(a, b) {
|
|
39
|
-
if (!aTypeOfJs.isArray(a) || !aTypeOfJs.isArray(b))
|
|
39
|
+
if (!aTypeOfJs.isArray(a) || !aTypeOfJs.isArray(b))
|
|
40
40
|
throw new TypeError('参数必须是数组');
|
|
41
|
-
|
|
42
|
-
if (a.length === 0) {
|
|
41
|
+
if (aTypeOfJs.isEmptyArray(a))
|
|
43
42
|
return [...b];
|
|
44
|
-
|
|
45
|
-
if (b.length === 0) {
|
|
43
|
+
if (aTypeOfJs.isEmptyArray(b))
|
|
46
44
|
return [...a];
|
|
47
|
-
}
|
|
48
45
|
return [...difference.difference(a, b), ...difference.difference(b, a)];
|
|
49
46
|
}
|
|
50
47
|
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { isArray } from 'a-type-of-js';
|
|
1
|
+
import { isArray, isEmptyArray } from 'a-type-of-js';
|
|
2
2
|
import { difference } from './difference.mjs';
|
|
3
3
|
|
|
4
4
|
/**
|
|
@@ -34,15 +34,12 @@ import { difference } from './difference.mjs';
|
|
|
34
34
|
*
|
|
35
35
|
*/
|
|
36
36
|
function symmetricDifference(a, b) {
|
|
37
|
-
if (!isArray(a) || !isArray(b))
|
|
37
|
+
if (!isArray(a) || !isArray(b))
|
|
38
38
|
throw new TypeError('参数必须是数组');
|
|
39
|
-
|
|
40
|
-
if (a.length === 0) {
|
|
39
|
+
if (isEmptyArray(a))
|
|
41
40
|
return [...b];
|
|
42
|
-
|
|
43
|
-
if (b.length === 0) {
|
|
41
|
+
if (isEmptyArray(b))
|
|
44
42
|
return [...a];
|
|
45
|
-
}
|
|
46
43
|
return [...difference(a, b), ...difference(b, a)];
|
|
47
44
|
}
|
|
48
45
|
|
package/src/array/union.cjs
CHANGED
|
@@ -44,20 +44,16 @@ var aTypeOfJs = require('a-type-of-js');
|
|
|
44
44
|
*
|
|
45
45
|
*/
|
|
46
46
|
function union(...arrays) {
|
|
47
|
-
if (arrays
|
|
47
|
+
if (aTypeOfJs.isEmptyArray(arrays))
|
|
48
48
|
return [];
|
|
49
|
-
|
|
50
|
-
if (arrays.some(i => !aTypeOfJs.isArray(i))) {
|
|
49
|
+
if (arrays.some(i => !aTypeOfJs.isArray(i)))
|
|
51
50
|
throw new TypeError('参数必须都是数组形式的元素');
|
|
52
|
-
|
|
53
|
-
if (arrays.length === 1) {
|
|
51
|
+
if (arrays.length === 1)
|
|
54
52
|
return [...arrays[0]];
|
|
55
|
-
}
|
|
56
53
|
const resultSet = new Set();
|
|
57
54
|
for (const array of arrays) {
|
|
58
|
-
for (const item of array)
|
|
55
|
+
for (const item of array)
|
|
59
56
|
resultSet.add(item);
|
|
60
|
-
}
|
|
61
57
|
}
|
|
62
58
|
return Array.from(resultSet);
|
|
63
59
|
}
|
package/src/array/union.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { isArray } from 'a-type-of-js';
|
|
1
|
+
import { isEmptyArray, isArray } from 'a-type-of-js';
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
*
|
|
@@ -42,20 +42,16 @@ import { isArray } from 'a-type-of-js';
|
|
|
42
42
|
*
|
|
43
43
|
*/
|
|
44
44
|
function union(...arrays) {
|
|
45
|
-
if (arrays
|
|
45
|
+
if (isEmptyArray(arrays))
|
|
46
46
|
return [];
|
|
47
|
-
|
|
48
|
-
if (arrays.some(i => !isArray(i))) {
|
|
47
|
+
if (arrays.some(i => !isArray(i)))
|
|
49
48
|
throw new TypeError('参数必须都是数组形式的元素');
|
|
50
|
-
|
|
51
|
-
if (arrays.length === 1) {
|
|
49
|
+
if (arrays.length === 1)
|
|
52
50
|
return [...arrays[0]];
|
|
53
|
-
}
|
|
54
51
|
const resultSet = new Set();
|
|
55
52
|
for (const array of arrays) {
|
|
56
|
-
for (const item of array)
|
|
53
|
+
for (const item of array)
|
|
57
54
|
resultSet.add(item);
|
|
58
|
-
}
|
|
59
55
|
}
|
|
60
56
|
return Array.from(resultSet);
|
|
61
57
|
}
|
package/src/className.cjs
CHANGED
|
@@ -34,9 +34,9 @@ initial = false) {
|
|
|
34
34
|
/** 转化首字符 */
|
|
35
35
|
const toTransform = (_str, _dividingType) => _str.replace(new RegExp(`${template.test(_dividingType) ? `\\${_dividingType}` : _dividingType}([a-zA-Z])`, 'g'), (match, p1) => p1.toUpperCase());
|
|
36
36
|
// 多分隔符转化
|
|
37
|
-
dividingType
|
|
38
|
-
|
|
39
|
-
|
|
37
|
+
dividingType
|
|
38
|
+
.split('')
|
|
39
|
+
.forEach((item) => (result = toTransform(result, item)));
|
|
40
40
|
return initial
|
|
41
41
|
? result.replace(/^./, (match) => match.toUpperCase())
|
|
42
42
|
: result;
|
package/src/className.mjs
CHANGED
|
@@ -32,9 +32,9 @@ initial = false) {
|
|
|
32
32
|
/** 转化首字符 */
|
|
33
33
|
const toTransform = (_str, _dividingType) => _str.replace(new RegExp(`${template.test(_dividingType) ? `\\${_dividingType}` : _dividingType}([a-zA-Z])`, 'g'), (match, p1) => p1.toUpperCase());
|
|
34
34
|
// 多分隔符转化
|
|
35
|
-
dividingType
|
|
36
|
-
|
|
37
|
-
|
|
35
|
+
dividingType
|
|
36
|
+
.split('')
|
|
37
|
+
.forEach((item) => (result = toTransform(result, item)));
|
|
38
38
|
return initial
|
|
39
39
|
? result.replace(/^./, (match) => match.toUpperCase())
|
|
40
40
|
: result;
|
package/src/getRandomString.cjs
CHANGED
|
@@ -38,9 +38,8 @@ function getRandomString(options) {
|
|
|
38
38
|
(aTypeOfJs.isPlainObject(options) &&
|
|
39
39
|
(!aTypeOfJs.isNumber(options.length) ||
|
|
40
40
|
options.length < 1 ||
|
|
41
|
-
!Number.isInteger(options.length))))
|
|
41
|
+
!Number.isInteger(options.length))))
|
|
42
42
|
throw new TypeError('参数类型错误 ❌ (getRandomString)');
|
|
43
|
-
}
|
|
44
43
|
const initOptions = {
|
|
45
44
|
length: 32,
|
|
46
45
|
chars: 'abcdefghijklmnopqrstuvwxyz',
|
|
@@ -52,13 +51,11 @@ function getRandomString(options) {
|
|
|
52
51
|
includeSpecial: false,
|
|
53
52
|
};
|
|
54
53
|
/// 生成 UUID
|
|
55
|
-
if (initOptions.type === 'uuid')
|
|
54
|
+
if (initOptions.type === 'uuid')
|
|
56
55
|
return crypto.randomUUID();
|
|
57
|
-
|
|
58
|
-
if (aTypeOfJs.isNumber(options) && Number.isInteger(options) && options > 0)
|
|
59
|
-
// 验证输入参数
|
|
56
|
+
// 验证输入参数
|
|
57
|
+
if (aTypeOfJs.isNumber(options) && Number.isInteger(options) && options > 0)
|
|
60
58
|
Object.assign(initOptions, { length: options });
|
|
61
|
-
}
|
|
62
59
|
if (aTypeOfJs.isPlainObject(options)) {
|
|
63
60
|
Object.assign(initOptions, options);
|
|
64
61
|
initOptions.length = initOptions.length < 1 ? 32 : initOptions.length;
|
|
@@ -66,17 +63,14 @@ function getRandomString(options) {
|
|
|
66
63
|
/** 生成随机字符串 */
|
|
67
64
|
const templateCharsArr = initOptions.chars.split('');
|
|
68
65
|
// 添加大写字母
|
|
69
|
-
if (initOptions.includeUppercaseLetters)
|
|
66
|
+
if (initOptions.includeUppercaseLetters)
|
|
70
67
|
interleaveString(templateCharsArr, initOptions.chars.toUpperCase());
|
|
71
|
-
}
|
|
72
68
|
// 添加数字
|
|
73
|
-
if (initOptions.includeNumbers)
|
|
69
|
+
if (initOptions.includeNumbers)
|
|
74
70
|
interleaveString(templateCharsArr, initOptions.chars2);
|
|
75
|
-
}
|
|
76
71
|
// 添加特殊字符
|
|
77
|
-
if (initOptions.includeSpecial)
|
|
72
|
+
if (initOptions.includeSpecial)
|
|
78
73
|
interleaveString(templateCharsArr, initOptions.chars3);
|
|
79
|
-
}
|
|
80
74
|
// 使用密码学安全的随机数生成器
|
|
81
75
|
const bytes = isNode.isBrowser() && window.crypto
|
|
82
76
|
? window.crypto.getRandomValues(new Uint8Array(initOptions.length))
|
|
@@ -104,12 +98,10 @@ function getRandomString(options) {
|
|
|
104
98
|
const str1Length = str1.length, str2Length = str2.length;
|
|
105
99
|
const maxLength = Math.max(str1Length, str2Length);
|
|
106
100
|
for (let i = 0; i < maxLength; i++) {
|
|
107
|
-
if (i < str1Length && str2[i]
|
|
101
|
+
if (i < str1Length && !aTypeOfJs.isUndefined(str2[i]))
|
|
108
102
|
str1[i] += str2[i];
|
|
109
|
-
|
|
110
|
-
else if (i < str2Length) {
|
|
103
|
+
else if (i < str2Length)
|
|
111
104
|
str1[i] = str2[i];
|
|
112
|
-
}
|
|
113
105
|
}
|
|
114
106
|
}
|
|
115
107
|
return result;
|
package/src/getRandomString.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { isPlainObject, isNumber, isNaN } from 'a-type-of-js';
|
|
1
|
+
import { isPlainObject, isNumber, isNaN, isUndefined } from 'a-type-of-js';
|
|
2
2
|
import { isBrowser } from './isNode.mjs';
|
|
3
3
|
|
|
4
4
|
/**
|
|
@@ -36,9 +36,8 @@ function getRandomString(options) {
|
|
|
36
36
|
(isPlainObject(options) &&
|
|
37
37
|
(!isNumber(options.length) ||
|
|
38
38
|
options.length < 1 ||
|
|
39
|
-
!Number.isInteger(options.length))))
|
|
39
|
+
!Number.isInteger(options.length))))
|
|
40
40
|
throw new TypeError('参数类型错误 ❌ (getRandomString)');
|
|
41
|
-
}
|
|
42
41
|
const initOptions = {
|
|
43
42
|
length: 32,
|
|
44
43
|
chars: 'abcdefghijklmnopqrstuvwxyz',
|
|
@@ -50,13 +49,11 @@ function getRandomString(options) {
|
|
|
50
49
|
includeSpecial: false,
|
|
51
50
|
};
|
|
52
51
|
/// 生成 UUID
|
|
53
|
-
if (initOptions.type === 'uuid')
|
|
52
|
+
if (initOptions.type === 'uuid')
|
|
54
53
|
return crypto.randomUUID();
|
|
55
|
-
|
|
56
|
-
if (isNumber(options) && Number.isInteger(options) && options > 0)
|
|
57
|
-
// 验证输入参数
|
|
54
|
+
// 验证输入参数
|
|
55
|
+
if (isNumber(options) && Number.isInteger(options) && options > 0)
|
|
58
56
|
Object.assign(initOptions, { length: options });
|
|
59
|
-
}
|
|
60
57
|
if (isPlainObject(options)) {
|
|
61
58
|
Object.assign(initOptions, options);
|
|
62
59
|
initOptions.length = initOptions.length < 1 ? 32 : initOptions.length;
|
|
@@ -64,17 +61,14 @@ function getRandomString(options) {
|
|
|
64
61
|
/** 生成随机字符串 */
|
|
65
62
|
const templateCharsArr = initOptions.chars.split('');
|
|
66
63
|
// 添加大写字母
|
|
67
|
-
if (initOptions.includeUppercaseLetters)
|
|
64
|
+
if (initOptions.includeUppercaseLetters)
|
|
68
65
|
interleaveString(templateCharsArr, initOptions.chars.toUpperCase());
|
|
69
|
-
}
|
|
70
66
|
// 添加数字
|
|
71
|
-
if (initOptions.includeNumbers)
|
|
67
|
+
if (initOptions.includeNumbers)
|
|
72
68
|
interleaveString(templateCharsArr, initOptions.chars2);
|
|
73
|
-
}
|
|
74
69
|
// 添加特殊字符
|
|
75
|
-
if (initOptions.includeSpecial)
|
|
70
|
+
if (initOptions.includeSpecial)
|
|
76
71
|
interleaveString(templateCharsArr, initOptions.chars3);
|
|
77
|
-
}
|
|
78
72
|
// 使用密码学安全的随机数生成器
|
|
79
73
|
const bytes = isBrowser() && window.crypto
|
|
80
74
|
? window.crypto.getRandomValues(new Uint8Array(initOptions.length))
|
|
@@ -102,12 +96,10 @@ function getRandomString(options) {
|
|
|
102
96
|
const str1Length = str1.length, str2Length = str2.length;
|
|
103
97
|
const maxLength = Math.max(str1Length, str2Length);
|
|
104
98
|
for (let i = 0; i < maxLength; i++) {
|
|
105
|
-
if (i < str1Length && str2[i]
|
|
99
|
+
if (i < str1Length && !isUndefined(str2[i]))
|
|
106
100
|
str1[i] += str2[i];
|
|
107
|
-
|
|
108
|
-
else if (i < str2Length) {
|
|
101
|
+
else if (i < str2Length)
|
|
109
102
|
str1[i] = str2[i];
|
|
110
|
-
}
|
|
111
103
|
}
|
|
112
104
|
}
|
|
113
105
|
return result;
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
*
|
|
5
|
+
* 构建一个 Constructor 构造函数
|
|
6
|
+
*
|
|
7
|
+
* 接收一个构造函数,然后返回 TS 能识别的构造函数自身
|
|
8
|
+
*
|
|
9
|
+
* 函数本身并没有执行任何逻辑,仅是简单的返回了实参自身
|
|
10
|
+
*
|
|
11
|
+
* 而经过该函数的包装,构造函数成了能够被 TS 识别为可用 new 实例的构造函数
|
|
12
|
+
*
|
|
13
|
+
* @param constructor - 传入一个构造函数
|
|
14
|
+
* @returns 返回传入的构造函数
|
|
15
|
+
*
|
|
16
|
+
* ```ts
|
|
17
|
+
* import { createConstructor } from "a-js-tools";
|
|
18
|
+
*
|
|
19
|
+
* type Tom = {
|
|
20
|
+
* a: number
|
|
21
|
+
* }
|
|
22
|
+
*
|
|
23
|
+
* function _Tom (this: TomType): Tom {
|
|
24
|
+
* this.a = 1;
|
|
25
|
+
*
|
|
26
|
+
* return this;
|
|
27
|
+
* }
|
|
28
|
+
*
|
|
29
|
+
* // 逻辑上没有错,但是会造成 ts 显示
|
|
30
|
+
* // 其目标缺少构造签名的 "new" 表达式隐式具有 "any" 类型。ts(7009)
|
|
31
|
+
* const a = new _Tom();
|
|
32
|
+
*
|
|
33
|
+
* const tomConstructor = createConstructor(_tom);
|
|
34
|
+
*
|
|
35
|
+
* const b = new tomConstructor(); // 这时就不会显示错误
|
|
36
|
+
*
|
|
37
|
+
* ```
|
|
38
|
+
*
|
|
39
|
+
*/
|
|
40
|
+
function createConstructor(constructor) {
|
|
41
|
+
return constructor;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
exports.createConstructor = createConstructor;
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
/**
|
|
2
|
+
*
|
|
3
|
+
* 构建构建的构建函数
|
|
4
|
+
*
|
|
5
|
+
*
|
|
6
|
+
*/
|
|
7
|
+
export interface CreateConstructor<T, Args extends unknown[] = unknown[]> {
|
|
8
|
+
new (...args: Args): T;
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
*
|
|
12
|
+
* 构建一个 Constructor 构造函数
|
|
13
|
+
*
|
|
14
|
+
* 接收一个构造函数,然后返回 TS 能识别的构造函数自身
|
|
15
|
+
*
|
|
16
|
+
* 函数本身并没有执行任何逻辑,仅是简单的返回了实参自身
|
|
17
|
+
*
|
|
18
|
+
* 而经过该函数的包装,构造函数成了能够被 TS 识别为可用 new 实例的构造函数
|
|
19
|
+
*
|
|
20
|
+
* @param constructor - 传入一个构造函数
|
|
21
|
+
* @returns 返回传入的构造函数
|
|
22
|
+
*
|
|
23
|
+
* ```ts
|
|
24
|
+
* import { createConstructor } from "a-js-tools";
|
|
25
|
+
*
|
|
26
|
+
* type Tom = {
|
|
27
|
+
* a: number
|
|
28
|
+
* }
|
|
29
|
+
*
|
|
30
|
+
* function _Tom (this: TomType): Tom {
|
|
31
|
+
* this.a = 1;
|
|
32
|
+
*
|
|
33
|
+
* return this;
|
|
34
|
+
* }
|
|
35
|
+
*
|
|
36
|
+
* // 逻辑上没有错,但是会造成 ts 显示
|
|
37
|
+
* // 其目标缺少构造签名的 "new" 表达式隐式具有 "any" 类型。ts(7009)
|
|
38
|
+
* const a = new _Tom();
|
|
39
|
+
*
|
|
40
|
+
* const tomConstructor = createConstructor(_tom);
|
|
41
|
+
*
|
|
42
|
+
* const b = new tomConstructor(); // 这时就不会显示错误
|
|
43
|
+
*
|
|
44
|
+
* ```
|
|
45
|
+
*
|
|
46
|
+
*/
|
|
47
|
+
export declare function createConstructor<T, Args extends unknown[] = unknown[]>(constructor: (...argumentList: Args) => T): CreateConstructor<T, Args>;
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
/**
|
|
2
|
+
*
|
|
3
|
+
* 构建一个 Constructor 构造函数
|
|
4
|
+
*
|
|
5
|
+
* 接收一个构造函数,然后返回 TS 能识别的构造函数自身
|
|
6
|
+
*
|
|
7
|
+
* 函数本身并没有执行任何逻辑,仅是简单的返回了实参自身
|
|
8
|
+
*
|
|
9
|
+
* 而经过该函数的包装,构造函数成了能够被 TS 识别为可用 new 实例的构造函数
|
|
10
|
+
*
|
|
11
|
+
* @param constructor - 传入一个构造函数
|
|
12
|
+
* @returns 返回传入的构造函数
|
|
13
|
+
*
|
|
14
|
+
* ```ts
|
|
15
|
+
* import { createConstructor } from "a-js-tools";
|
|
16
|
+
*
|
|
17
|
+
* type Tom = {
|
|
18
|
+
* a: number
|
|
19
|
+
* }
|
|
20
|
+
*
|
|
21
|
+
* function _Tom (this: TomType): Tom {
|
|
22
|
+
* this.a = 1;
|
|
23
|
+
*
|
|
24
|
+
* return this;
|
|
25
|
+
* }
|
|
26
|
+
*
|
|
27
|
+
* // 逻辑上没有错,但是会造成 ts 显示
|
|
28
|
+
* // 其目标缺少构造签名的 "new" 表达式隐式具有 "any" 类型。ts(7009)
|
|
29
|
+
* const a = new _Tom();
|
|
30
|
+
*
|
|
31
|
+
* const tomConstructor = createConstructor(_tom);
|
|
32
|
+
*
|
|
33
|
+
* const b = new tomConstructor(); // 这时就不会显示错误
|
|
34
|
+
*
|
|
35
|
+
* ```
|
|
36
|
+
*
|
|
37
|
+
*/
|
|
38
|
+
function createConstructor(constructor) {
|
|
39
|
+
return constructor;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
export { createConstructor };
|
package/src/performance.cjs
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
+
var aTypeOfJs = require('a-type-of-js');
|
|
4
|
+
|
|
3
5
|
/**
|
|
4
6
|
* 防抖和节流
|
|
5
7
|
*
|
|
@@ -12,7 +14,7 @@
|
|
|
12
14
|
* 防抖
|
|
13
15
|
*
|
|
14
16
|
* @param callback 回调函数
|
|
15
|
-
* @param
|
|
17
|
+
* @param options 延迟时间(毫秒),默认 200 (ms) 或包含 this 的配置
|
|
16
18
|
* @returns 返回的闭包函数
|
|
17
19
|
* @example
|
|
18
20
|
*
|
|
@@ -25,13 +27,19 @@
|
|
|
25
27
|
* }
|
|
26
28
|
*
|
|
27
29
|
*/
|
|
28
|
-
function debounce(callback,
|
|
29
|
-
if (
|
|
30
|
+
function debounce(callback, options = 200) {
|
|
31
|
+
if (!aTypeOfJs.isFunction(callback))
|
|
30
32
|
throw new TypeError('callback must be a function');
|
|
31
|
-
|
|
32
|
-
|
|
33
|
+
if (aTypeOfJs.isNumber(options))
|
|
34
|
+
options = {
|
|
35
|
+
delay: options,
|
|
36
|
+
this: null,
|
|
37
|
+
};
|
|
38
|
+
if (aTypeOfJs.isUndefined(options.delay) ||
|
|
39
|
+
!isFinite(options.delay) ||
|
|
40
|
+
options.delay < 0)
|
|
33
41
|
// 强制转换非数值
|
|
34
|
-
delay = 200;
|
|
42
|
+
options.delay = 200;
|
|
35
43
|
/** 定时器返回的 id */
|
|
36
44
|
let timeoutId;
|
|
37
45
|
const clear = () => {
|
|
@@ -44,29 +52,36 @@ function debounce(callback, delay = 200) {
|
|
|
44
52
|
clear();
|
|
45
53
|
timeoutId = setTimeout(() => {
|
|
46
54
|
try {
|
|
47
|
-
Reflect.apply(callback, null, args);
|
|
55
|
+
Reflect.apply(callback, options?.this ?? null, args);
|
|
48
56
|
}
|
|
49
57
|
catch (error) {
|
|
50
58
|
console.log('Debounce callback throw an error', error);
|
|
51
59
|
}
|
|
52
|
-
}, Math.max(delay, 5));
|
|
53
|
-
};
|
|
54
|
-
result.cancel = () => {
|
|
55
|
-
clear();
|
|
60
|
+
}, Math.max(options?.delay ?? 5, 5));
|
|
56
61
|
};
|
|
62
|
+
result.cancel = () => clear();
|
|
57
63
|
return result;
|
|
58
64
|
}
|
|
59
65
|
/**
|
|
60
66
|
* 节流
|
|
61
67
|
*
|
|
62
68
|
* @param callback 回调函数
|
|
63
|
-
* @param
|
|
69
|
+
* @param options 延迟时间(毫秒),默认 200 (ms) 或设置 this
|
|
64
70
|
* @returns 返回的闭包函数
|
|
65
71
|
*/
|
|
66
|
-
function throttle(callback,
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
72
|
+
function throttle(callback, options = 200) {
|
|
73
|
+
if (!aTypeOfJs.isFunction(callback))
|
|
74
|
+
throw new TypeError('callback must be a function');
|
|
75
|
+
if (aTypeOfJs.isNumber(options))
|
|
76
|
+
options = {
|
|
77
|
+
delay: options,
|
|
78
|
+
this: null,
|
|
79
|
+
};
|
|
80
|
+
if (aTypeOfJs.isUndefined(options.delay) ||
|
|
81
|
+
!isFinite(options.delay) ||
|
|
82
|
+
options.delay < 0)
|
|
83
|
+
// 强制转换非数值
|
|
84
|
+
options.delay = 200;
|
|
70
85
|
/** 延迟控制插销 */
|
|
71
86
|
let inThrottle = false;
|
|
72
87
|
/** 延迟控制 */
|
|
@@ -75,24 +90,22 @@ function throttle(callback, delay = 200) {
|
|
|
75
90
|
if (inThrottle)
|
|
76
91
|
return;
|
|
77
92
|
try {
|
|
78
|
-
Reflect.apply(callback, null, args);
|
|
93
|
+
Reflect.apply(callback, options?.this ?? null, args);
|
|
79
94
|
}
|
|
80
95
|
catch (error) {
|
|
81
|
-
console.error('Throttle
|
|
96
|
+
console.error('Throttle 执行回调抛出问题', error);
|
|
82
97
|
}
|
|
83
98
|
inThrottle = true;
|
|
84
|
-
if (timeoutId
|
|
99
|
+
if (!aTypeOfJs.isNull(timeoutId))
|
|
85
100
|
clearTimeout(timeoutId);
|
|
86
|
-
}
|
|
87
101
|
timeoutId = setTimeout(() => {
|
|
88
102
|
inThrottle = false;
|
|
89
103
|
timeoutId = null;
|
|
90
|
-
}, delay);
|
|
104
|
+
}, Math.max(options?.delay ?? 5, 5));
|
|
91
105
|
};
|
|
92
106
|
throttled.cancel = () => {
|
|
93
|
-
if (timeoutId
|
|
107
|
+
if (!aTypeOfJs.isNull(timeoutId))
|
|
94
108
|
clearTimeout(timeoutId);
|
|
95
|
-
}
|
|
96
109
|
inThrottle = false;
|
|
97
110
|
timeoutId = null;
|
|
98
111
|
};
|
package/src/performance.d.ts
CHANGED
|
@@ -15,12 +15,17 @@ export interface DebounceAndThrottleReturnType<F extends Callback> {
|
|
|
15
15
|
(...args: Parameters<F>): void;
|
|
16
16
|
cancel(): void;
|
|
17
17
|
}
|
|
18
|
+
/** 第二参数 */
|
|
19
|
+
export type debounce_throttle_options = {
|
|
20
|
+
delay?: number;
|
|
21
|
+
this?: null | unknown;
|
|
22
|
+
} | number;
|
|
18
23
|
/**
|
|
19
24
|
*
|
|
20
25
|
* 防抖
|
|
21
26
|
*
|
|
22
27
|
* @param callback 回调函数
|
|
23
|
-
* @param
|
|
28
|
+
* @param options 延迟时间(毫秒),默认 200 (ms) 或包含 this 的配置
|
|
24
29
|
* @returns 返回的闭包函数
|
|
25
30
|
* @example
|
|
26
31
|
*
|
|
@@ -33,13 +38,13 @@ export interface DebounceAndThrottleReturnType<F extends Callback> {
|
|
|
33
38
|
* }
|
|
34
39
|
*
|
|
35
40
|
*/
|
|
36
|
-
export declare function debounce<F extends (...args: unknown[]) => void>(callback: F,
|
|
41
|
+
export declare function debounce<F extends (...args: unknown[]) => void>(callback: F, options?: debounce_throttle_options): DebounceAndThrottleReturnType<F>;
|
|
37
42
|
/**
|
|
38
43
|
* 节流
|
|
39
44
|
*
|
|
40
45
|
* @param callback 回调函数
|
|
41
|
-
* @param
|
|
46
|
+
* @param options 延迟时间(毫秒),默认 200 (ms) 或设置 this
|
|
42
47
|
* @returns 返回的闭包函数
|
|
43
48
|
*/
|
|
44
|
-
export declare function throttle<F extends (...args: unknown[]) => void>(callback: F,
|
|
49
|
+
export declare function throttle<F extends (...args: unknown[]) => void>(callback: F, options?: debounce_throttle_options): DebounceAndThrottleReturnType<F>;
|
|
45
50
|
export {};
|
package/src/performance.mjs
CHANGED
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { isFunction, isNumber, isUndefined, isNull } from 'a-type-of-js';
|
|
2
|
+
|
|
1
3
|
/**
|
|
2
4
|
* 防抖和节流
|
|
3
5
|
*
|
|
@@ -10,7 +12,7 @@
|
|
|
10
12
|
* 防抖
|
|
11
13
|
*
|
|
12
14
|
* @param callback 回调函数
|
|
13
|
-
* @param
|
|
15
|
+
* @param options 延迟时间(毫秒),默认 200 (ms) 或包含 this 的配置
|
|
14
16
|
* @returns 返回的闭包函数
|
|
15
17
|
* @example
|
|
16
18
|
*
|
|
@@ -23,13 +25,19 @@
|
|
|
23
25
|
* }
|
|
24
26
|
*
|
|
25
27
|
*/
|
|
26
|
-
function debounce(callback,
|
|
27
|
-
if (
|
|
28
|
+
function debounce(callback, options = 200) {
|
|
29
|
+
if (!isFunction(callback))
|
|
28
30
|
throw new TypeError('callback must be a function');
|
|
29
|
-
|
|
30
|
-
|
|
31
|
+
if (isNumber(options))
|
|
32
|
+
options = {
|
|
33
|
+
delay: options,
|
|
34
|
+
this: null,
|
|
35
|
+
};
|
|
36
|
+
if (isUndefined(options.delay) ||
|
|
37
|
+
!isFinite(options.delay) ||
|
|
38
|
+
options.delay < 0)
|
|
31
39
|
// 强制转换非数值
|
|
32
|
-
delay = 200;
|
|
40
|
+
options.delay = 200;
|
|
33
41
|
/** 定时器返回的 id */
|
|
34
42
|
let timeoutId;
|
|
35
43
|
const clear = () => {
|
|
@@ -42,29 +50,36 @@ function debounce(callback, delay = 200) {
|
|
|
42
50
|
clear();
|
|
43
51
|
timeoutId = setTimeout(() => {
|
|
44
52
|
try {
|
|
45
|
-
Reflect.apply(callback, null, args);
|
|
53
|
+
Reflect.apply(callback, options?.this ?? null, args);
|
|
46
54
|
}
|
|
47
55
|
catch (error) {
|
|
48
56
|
console.log('Debounce callback throw an error', error);
|
|
49
57
|
}
|
|
50
|
-
}, Math.max(delay, 5));
|
|
51
|
-
};
|
|
52
|
-
result.cancel = () => {
|
|
53
|
-
clear();
|
|
58
|
+
}, Math.max(options?.delay ?? 5, 5));
|
|
54
59
|
};
|
|
60
|
+
result.cancel = () => clear();
|
|
55
61
|
return result;
|
|
56
62
|
}
|
|
57
63
|
/**
|
|
58
64
|
* 节流
|
|
59
65
|
*
|
|
60
66
|
* @param callback 回调函数
|
|
61
|
-
* @param
|
|
67
|
+
* @param options 延迟时间(毫秒),默认 200 (ms) 或设置 this
|
|
62
68
|
* @returns 返回的闭包函数
|
|
63
69
|
*/
|
|
64
|
-
function throttle(callback,
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
70
|
+
function throttle(callback, options = 200) {
|
|
71
|
+
if (!isFunction(callback))
|
|
72
|
+
throw new TypeError('callback must be a function');
|
|
73
|
+
if (isNumber(options))
|
|
74
|
+
options = {
|
|
75
|
+
delay: options,
|
|
76
|
+
this: null,
|
|
77
|
+
};
|
|
78
|
+
if (isUndefined(options.delay) ||
|
|
79
|
+
!isFinite(options.delay) ||
|
|
80
|
+
options.delay < 0)
|
|
81
|
+
// 强制转换非数值
|
|
82
|
+
options.delay = 200;
|
|
68
83
|
/** 延迟控制插销 */
|
|
69
84
|
let inThrottle = false;
|
|
70
85
|
/** 延迟控制 */
|
|
@@ -73,24 +88,22 @@ function throttle(callback, delay = 200) {
|
|
|
73
88
|
if (inThrottle)
|
|
74
89
|
return;
|
|
75
90
|
try {
|
|
76
|
-
Reflect.apply(callback, null, args);
|
|
91
|
+
Reflect.apply(callback, options?.this ?? null, args);
|
|
77
92
|
}
|
|
78
93
|
catch (error) {
|
|
79
|
-
console.error('Throttle
|
|
94
|
+
console.error('Throttle 执行回调抛出问题', error);
|
|
80
95
|
}
|
|
81
96
|
inThrottle = true;
|
|
82
|
-
if (timeoutId
|
|
97
|
+
if (!isNull(timeoutId))
|
|
83
98
|
clearTimeout(timeoutId);
|
|
84
|
-
}
|
|
85
99
|
timeoutId = setTimeout(() => {
|
|
86
100
|
inThrottle = false;
|
|
87
101
|
timeoutId = null;
|
|
88
|
-
}, delay);
|
|
102
|
+
}, Math.max(options?.delay ?? 5, 5));
|
|
89
103
|
};
|
|
90
104
|
throttled.cancel = () => {
|
|
91
|
-
if (timeoutId
|
|
105
|
+
if (!isNull(timeoutId))
|
|
92
106
|
clearTimeout(timeoutId);
|
|
93
|
-
}
|
|
94
107
|
inThrottle = false;
|
|
95
108
|
timeoutId = null;
|
|
96
109
|
};
|
|
@@ -35,14 +35,12 @@ var parse = require('./parse.cjs');
|
|
|
35
35
|
*
|
|
36
36
|
*/
|
|
37
37
|
function autoEscapedRegExp(pattern, options) {
|
|
38
|
-
if (!aTypeOfJs.isString(pattern))
|
|
38
|
+
if (!aTypeOfJs.isString(pattern))
|
|
39
39
|
throw new TypeError('pattern must be a 字符串');
|
|
40
|
-
}
|
|
41
40
|
pattern = escapeRegExp.escapeRegExp(pattern);
|
|
42
41
|
/** 简单转化 */
|
|
43
|
-
if (aTypeOfJs.isUndefined(options))
|
|
42
|
+
if (aTypeOfJs.isUndefined(options))
|
|
44
43
|
return new RegExp(pattern);
|
|
45
|
-
}
|
|
46
44
|
options = parse.parse(options);
|
|
47
45
|
return new RegExp(`${options.start ? '^' : ''}${pattern}${options.end ? '$' : ''}`, options.flags);
|
|
48
46
|
}
|
|
@@ -33,14 +33,12 @@ import { parse } from './parse.mjs';
|
|
|
33
33
|
*
|
|
34
34
|
*/
|
|
35
35
|
function autoEscapedRegExp(pattern, options) {
|
|
36
|
-
if (!isString(pattern))
|
|
36
|
+
if (!isString(pattern))
|
|
37
37
|
throw new TypeError('pattern must be a 字符串');
|
|
38
|
-
}
|
|
39
38
|
pattern = escapeRegExp(pattern);
|
|
40
39
|
/** 简单转化 */
|
|
41
|
-
if (isUndefined(options))
|
|
40
|
+
if (isUndefined(options))
|
|
42
41
|
return new RegExp(pattern);
|
|
43
|
-
}
|
|
44
42
|
options = parse(options);
|
|
45
43
|
return new RegExp(`${options.start ? '^' : ''}${pattern}${options.end ? '$' : ''}`, options.flags);
|
|
46
44
|
}
|
package/src/regexp/parse.cjs
CHANGED
|
@@ -15,19 +15,16 @@ function parse(options) {
|
|
|
15
15
|
};
|
|
16
16
|
}
|
|
17
17
|
// 处理 flags
|
|
18
|
-
if (!aTypeOfJs.isString(options.flags))
|
|
18
|
+
if (!aTypeOfJs.isString(options.flags))
|
|
19
19
|
options.flags = '';
|
|
20
|
-
}
|
|
21
20
|
else {
|
|
22
21
|
// 需求是保留字符串中的某一部分,使用
|
|
23
22
|
const regexp = /[migsuy]/g;
|
|
24
23
|
const matchResult = options.flags.match(regexp);
|
|
25
|
-
if (aTypeOfJs.isNull(matchResult))
|
|
24
|
+
if (aTypeOfJs.isNull(matchResult))
|
|
26
25
|
options.flags = '';
|
|
27
|
-
|
|
28
|
-
else {
|
|
26
|
+
else
|
|
29
27
|
options.flags = [...new Set(matchResult)].join('');
|
|
30
|
-
}
|
|
31
28
|
}
|
|
32
29
|
return options;
|
|
33
30
|
}
|
package/src/regexp/parse.mjs
CHANGED
|
@@ -13,19 +13,16 @@ function parse(options) {
|
|
|
13
13
|
};
|
|
14
14
|
}
|
|
15
15
|
// 处理 flags
|
|
16
|
-
if (!isString(options.flags))
|
|
16
|
+
if (!isString(options.flags))
|
|
17
17
|
options.flags = '';
|
|
18
|
-
}
|
|
19
18
|
else {
|
|
20
19
|
// 需求是保留字符串中的某一部分,使用
|
|
21
20
|
const regexp = /[migsuy]/g;
|
|
22
21
|
const matchResult = options.flags.match(regexp);
|
|
23
|
-
if (isNull(matchResult))
|
|
22
|
+
if (isNull(matchResult))
|
|
24
23
|
options.flags = '';
|
|
25
|
-
|
|
26
|
-
else {
|
|
24
|
+
else
|
|
27
25
|
options.flags = [...new Set(matchResult)].join('');
|
|
28
|
-
}
|
|
29
26
|
}
|
|
30
27
|
return options;
|
|
31
28
|
}
|
package/src/sleep.cjs
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
+
var aTypeOfJs = require('a-type-of-js');
|
|
4
|
+
|
|
3
5
|
/**
|
|
4
6
|
*
|
|
5
7
|
* ## 线程休息
|
|
@@ -28,7 +30,7 @@
|
|
|
28
30
|
async function sleep(delay = 1000) {
|
|
29
31
|
if (!isFinite(delay) || delay < 0)
|
|
30
32
|
throw new TypeError('delay 应该是一个正常的数值');
|
|
31
|
-
if (delay
|
|
33
|
+
if (aTypeOfJs.isZero(delay))
|
|
32
34
|
return Promise.resolve();
|
|
33
35
|
return new Promise(resolve => setTimeout(resolve, delay));
|
|
34
36
|
}
|
package/src/sleep.mjs
CHANGED
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { isZero } from 'a-type-of-js';
|
|
2
|
+
|
|
1
3
|
/**
|
|
2
4
|
*
|
|
3
5
|
* ## 线程休息
|
|
@@ -26,7 +28,7 @@
|
|
|
26
28
|
async function sleep(delay = 1000) {
|
|
27
29
|
if (!isFinite(delay) || delay < 0)
|
|
28
30
|
throw new TypeError('delay 应该是一个正常的数值');
|
|
29
|
-
if (delay
|
|
31
|
+
if (isZero(delay))
|
|
30
32
|
return Promise.resolve();
|
|
31
33
|
return new Promise(resolve => setTimeout(resolve, delay));
|
|
32
34
|
}
|