@yh-kit/utils 1.17.0 → 1.18.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/README.md CHANGED
@@ -1,3 +1,12 @@
1
+ <!--
2
+ * @Description: 实用程序合集文档
3
+ * @Author: YH
4
+ * @Date: 2026-04-16 22:56:51
5
+ * @LastEditors: YH
6
+ * @LastEditTime: 2026-06-18 18:31:01
7
+ * @FilePath: /vite-project/packages/utils/README.md
8
+ -->
9
+
1
10
  # 实用程序合集
2
11
 
3
12
  实用程序合集
@@ -12,29 +21,30 @@
12
21
 
13
22
  此库包含以下工具函数,及其函数名如下:
14
23
 
15
- | 函数对象名 | 描述 | 函数实现方式 |
16
- | :------ | :------ | :------ |
17
- | arrayUtils | 数组相关操作工具函数 | js对象函数 |
18
- | Base64Utils | Base64 相关操作工具函数 | class类 |
19
- | booleanUtils | 布尔值相关操作工具函数 | js对象函数 |
20
- | cookieUtils | Cookie 相关操作工具函数 | js对象函数 |
21
- | dateUtils | 日期相关操作工具函数 | js对象函数 |
22
- | documentUtils | 文档相关操作工具函数 | js对象函数 |
23
- | downloadUtils | 下载相关操作工具函数 | js对象函数 |
24
- | echartsUtils | Echarts 相关操作工具函数 | js对象函数 |
25
- | letterUtils | 字母相关操作工具函数 | js对象函数 |
26
- | mapUtils | 地图相关操作工具函数 | js对象函数 |
27
- | MoneyFormatter | 金额格式化工具函数 | class类 |
28
- | nameUtils | 姓名相关操作工具函数 | namespace |
29
- | numberUtils | 数字相关操作工具函数 | js对象函数 |
30
- | objectUtils | 对象相关操作工具函数 | js对象函数 |
31
- | phoneUtils | 手机号相关操作工具函数 | js对象函数 |
32
- | randomUtils | 随机数相关操作工具函数 | js对象函数 |
33
- | regexpUtils | 常用正则表达式 | js对象函数 |
34
- | storageUtils | 本地存储相关操作工具函数 | js对象函数 |
35
- | stringUtils | 字符串相关操作工具函数 | js对象函数 |
36
- | urlUtils | URL 相关操作工具函数 | js对象函数 |
37
- | waterfallUtils | 瀑布流相关操作工具函数 | js对象函数 |
24
+ | 函数对象名 | 描述 | 函数实现方式 | 备注 |
25
+ | :------ | :------ | :------ | :------ |
26
+ | arrayUtils | 数组相关操作工具函数 | js对象函数 | -- |
27
+ | Base64Utils | Base64 相关操作工具函数 | class类 | -- |
28
+ | booleanUtils | 布尔值相关操作工具函数 | js对象函数 | -- |
29
+ | commonUtils | 公用工具函数 | js对象函数 | -- |
30
+ | cookieUtils | Cookie 相关操作工具函数 | js对象函数 | -- |
31
+ | dateUtils | 日期相关操作工具函数 | js对象函数 | -- |
32
+ | documentUtils | 文档相关操作工具函数 | js对象函数 | -- |
33
+ | downloadUtils | 下载相关操作工具函数 | js对象函数 | -- |
34
+ | echartsUtils | Echarts 相关操作工具函数 | js对象函数 | -- |
35
+ | letterUtils | 字母相关操作工具函数 | js对象函数 | -- |
36
+ | mapUtils | 地图相关操作工具函数 | js对象函数 | -- |
37
+ | MoneyFormatter | 金额格式化工具函数 | class类 | -- |
38
+ | nameUtils | 姓名相关操作工具函数 | namespace | -- |
39
+ | numberUtils | 数字相关操作工具函数 | js对象函数 | -- |
40
+ | objectUtils | 对象相关操作工具函数 | js对象函数 | -- |
41
+ | phoneUtils | 手机号相关操作工具函数 | js对象函数 | -- |
42
+ | randomUtils | 随机数相关操作工具函数 | js对象函数 | -- |
43
+ | regexpUtils | 常用正则表达式 | js对象函数 | -- |
44
+ | storageUtils | 本地存储相关操作工具函数 | js对象函数 | -- |
45
+ | stringUtils | 字符串相关操作工具函数 | js对象函数 | -- |
46
+ | urlUtils | URL 相关操作工具函数 | js对象函数 | -- |
47
+ | waterfallUtils | 瀑布流相关操作工具函数 | js对象函数 | -- |
38
48
 
39
49
  ## 使用
40
50
 
package/dist/utils.js CHANGED
@@ -336,7 +336,7 @@ const b = {
336
336
  // 数组随机打乱-Fisher-Yates算法
337
337
  ...E
338
338
  };
339
- class N {
339
+ class F {
340
340
  /** Base64 编码表 */
341
341
  static BASE64_CHARS = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
342
342
  /**
@@ -709,7 +709,7 @@ const R = {
709
709
  throw new Error("空对象不能进行深拷贝");
710
710
  if (n.has(e))
711
711
  return n.get(e);
712
- const t = U.getType(e);
712
+ const t = T.getType(e);
713
713
  let r;
714
714
  switch (t) {
715
715
  case "object":
@@ -742,6 +742,55 @@ const R = {
742
742
  );
743
743
  }), r);
744
744
  }
745
+ }, U = {
746
+ /**
747
+ * 函数柯里化
748
+ * 定义:把一个多参数的函数,转换为一系列的单参数函数,每个函数只处理一个参数。
749
+ * 方向:多参数函数 -> 单参数函数链
750
+ * 核心:参数复用、延迟执行。
751
+ * 实现思路:参数收集、直到参数够了,再执行函数。
752
+ * 例如:
753
+ * ```ts
754
+ * const add = (a: number, b: number) => a + b;
755
+ * const add1 = curry(add)(1);
756
+ * const result = add1(2); // 3
757
+ * console.log(result); // 正确答案 3
758
+ * ```
759
+ * @param fn 要柯里化的函数
760
+ * @returns 柯里化后的函数
761
+ */
762
+ curry(e) {
763
+ if (typeof e != "function")
764
+ throw new TypeError("curry: fn must be a function, but got " + typeof e);
765
+ const n = e.length;
766
+ return function t(...r) {
767
+ return r.length >= n ? e.apply(this, r) : function(...o) {
768
+ return t.apply(this, [...r, ...o]);
769
+ };
770
+ };
771
+ },
772
+ /**
773
+ * 反柯里化
774
+ * 定义:让一个“只能被特定对象调用”的方法,变成一个“可以接受任何对象作为第一个参数”的通用函数。
775
+ * 方向:对象方法 -> 通用函数
776
+ * 核心:将对象方法转换为通用函数,允许在不同对象上调用。
777
+ * 实现思路:将对象方法绑定到通用函数上,返回通用函数。
778
+ * 例如:
779
+ * ```ts
780
+ * const push = uncurry(Array.prototype.push);
781
+ * const obj = {};
782
+ * const result = push(obj, 1, 2);
783
+ * console.log(result); // 正确答案 返回长度为 2
784
+ * console.log(obj); // 正确答案 {0: 1, 1: 2, length: 2}
785
+ * ```
786
+ * @param fn 要反柯里化的函数
787
+ * @returns 反柯里化后的函数
788
+ */
789
+ uncurry(e) {
790
+ return function(n, ...t) {
791
+ return e.call(n, ...t);
792
+ };
793
+ }
745
794
  }, O = {
746
795
  /**
747
796
  * 获取变量的类型
@@ -751,10 +800,11 @@ const R = {
751
800
  getType(e) {
752
801
  return Object.prototype.toString.call(e).replace(/\[object\s(\w+)\]/, "$1");
753
802
  }
754
- }, U = {
803
+ }, T = {
755
804
  ...O,
756
- ...D
757
- }, F = {
805
+ ...D,
806
+ ...U
807
+ }, P = {
758
808
  /**
759
809
  * 通过传入的name获取cookie的值
760
810
  * @param name cookie的name
@@ -784,7 +834,7 @@ const R = {
784
834
  deleteCookie(e) {
785
835
  this.setCookie(e, "", -1);
786
836
  }
787
- }, P = {
837
+ }, q = {
788
838
  /**
789
839
  * 获取当前时间字符串
790
840
  * @param locales 区域设置。如:'zh-CN','en-US',"chinese"。默认'zh-CN'。
@@ -899,7 +949,7 @@ const R = {
899
949
  new RegExp("(" + r + ")").test(n) && (n = n.replace(RegExp.$1, RegExp.$1.length === 1 ? t[r] : ("00" + t[r]).substr(("" + t[r]).length)));
900
950
  return n;
901
951
  }
902
- }, q = {
952
+ }, V = {
903
953
  /**
904
954
  * 获取元素相对于文档顶部的偏移量(距离)
905
955
  * 处理了SVG元素的特殊情况。
@@ -970,7 +1020,7 @@ const R = {
970
1020
  getViewportHeight() {
971
1021
  return window.innerHeight || document.documentElement.clientHeight || document.body.clientHeight;
972
1022
  }
973
- }, V = {
1023
+ }, W = {
974
1024
  /**
975
1025
  * 将blob对象转化成文件并导出到本地
976
1026
  * @param blob blob对象
@@ -989,7 +1039,7 @@ const R = {
989
1039
  const t = document.createElement("a");
990
1040
  t.href = e, t.download = n, document.body.appendChild(t), t.click(), URL.revokeObjectURL(e), document.body.removeChild(t);
991
1041
  }
992
- }, W = {
1042
+ }, Y = {
993
1043
  /**
994
1044
  * echarts动画函数
995
1045
  * @param option echarts配置
@@ -1021,7 +1071,7 @@ const R = {
1021
1071
  });
1022
1072
  });
1023
1073
  }
1024
- }, Y = {
1074
+ }, z = {
1025
1075
  /**
1026
1076
  * 将选中的字母数组从A-Z排序:用于试题选择答案的排序实例
1027
1077
  * @param arr 字母数组
@@ -1033,7 +1083,7 @@ const R = {
1033
1083
  return o < s ? -1 : o > s ? 1 : 0;
1034
1084
  }) : void 0;
1035
1085
  }
1036
- }, z = {
1086
+ }, J = {
1037
1087
  /**
1038
1088
  * 角度(度数)转弧度
1039
1089
  * 在数学和编程里,角度有两种常用单位,分别是度(°)和弧度(rad)。
@@ -1119,7 +1169,7 @@ const R = {
1119
1169
  return { segments: r, total: o };
1120
1170
  }
1121
1171
  };
1122
- class J {
1172
+ class Z {
1123
1173
  /**
1124
1174
  * 转换为标准金额格式(带千分位和两位小数)
1125
1175
  * @param num 要转换的数字
@@ -1174,7 +1224,7 @@ class J {
1174
1224
  }
1175
1225
  }
1176
1226
  }
1177
- const Z = {
1227
+ const K = {
1178
1228
  /**
1179
1229
  * 中文姓名脱敏
1180
1230
  * @param name 姓名
@@ -1217,15 +1267,15 @@ const Z = {
1217
1267
  }
1218
1268
  return `${e.slice(0, c)}${"*".repeat(e.length - c)}`;
1219
1269
  }
1220
- }, v = (e) => e > 25 || e < 0 ? "" : "ABCDEFGHIJKLMNOPQRSTUVWXYZ"[e], T = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
1270
+ }, v = (e) => e > 25 || e < 0 ? "" : "ABCDEFGHIJKLMNOPQRSTUVWXYZ"[e], j = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
1221
1271
  __proto__: null,
1222
1272
  toLetter: v
1223
- }, Symbol.toStringTag, { value: "Module" })), j = (e) => e.toFixed(2).toString().replace(/\B(?=(\d{3})+(?!\d))/g, ","), L = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
1273
+ }, Symbol.toStringTag, { value: "Module" })), L = (e) => e.toFixed(2).toString().replace(/\B(?=(\d{3})+(?!\d))/g, ","), I = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
1224
1274
  __proto__: null,
1225
- toMoney: j
1226
- }, Symbol.toStringTag, { value: "Module" })), K = {
1227
- ...T,
1228
- ...L,
1275
+ toMoney: L
1276
+ }, Symbol.toStringTag, { value: "Module" })), X = {
1277
+ ...j,
1278
+ ...I,
1229
1279
  /**
1230
1280
  * 判断是否为数字
1231
1281
  * @param val 待判断的值
@@ -1234,7 +1284,7 @@ const Z = {
1234
1284
  isNumber(e) {
1235
1285
  return typeof e == "number" && !isNaN(e);
1236
1286
  }
1237
- }, X = {
1287
+ }, G = {
1238
1288
  /**
1239
1289
  * 脱敏
1240
1290
  * @param phone 电话号码/手机号码
@@ -1243,7 +1293,7 @@ const Z = {
1243
1293
  desensitize(e) {
1244
1294
  return e ? e.replace(/^(\d{3})\d{4}(\d{4})$/, "$1****$2") || e.slice(0, 3) + "****" + e.slice(7) : "";
1245
1295
  }
1246
- }, G = {
1296
+ }, Q = {
1247
1297
  /**
1248
1298
  * 生成随机颜色
1249
1299
  * @returns 随机颜色值
@@ -1267,7 +1317,7 @@ const Z = {
1267
1317
  uniqueId() {
1268
1318
  return Date.now().toString(36) + Math.random().toString(36).substr(2, 5);
1269
1319
  }
1270
- }, Q = {
1320
+ }, ee = {
1271
1321
  /**
1272
1322
  * 验证手机号
1273
1323
  */
@@ -1304,7 +1354,7 @@ const Z = {
1304
1354
  * 验证0.01~0.99正则:最多两位小数。0.1、0.10、0.9、0.90
1305
1355
  */
1306
1356
  decimal: /^0\.(0[1-9]|[1-9][0-9]*)$/
1307
- }, ee = {
1357
+ }, te = {
1308
1358
  /**
1309
1359
  * 通过key值获取 localStorage 中存储的某个值
1310
1360
  * @param key 获取的key
@@ -1351,7 +1401,7 @@ const Z = {
1351
1401
  removeSession(e) {
1352
1402
  sessionStorage.removeItem(e);
1353
1403
  }
1354
- }, te = {
1404
+ }, ne = {
1355
1405
  /**
1356
1406
  * 判断某元素是否在字符串中-比includes()方法更兼容,includes为ES6新增方法,IE不支持。小程序也不支持
1357
1407
  * @param str 字符串
@@ -1434,19 +1484,19 @@ const Z = {
1434
1484
  throw new Error("开始位置小于0或结束位置超出字符串长度或开始位置大于结束位置");
1435
1485
  return e.slice(0, n) + "*".repeat(t - n + 1) + e.slice(t);
1436
1486
  }
1437
- }, I = (e) => {
1487
+ }, _ = (e) => {
1438
1488
  const t = new RegExp("[?&]" + e + "=([^&#]*)", "gi").exec(window.location.href);
1439
1489
  return t ? decodeURIComponent(t[1]) : null;
1440
1490
  };
1441
- function _(e) {
1491
+ function H(e) {
1442
1492
  return new URLSearchParams(window.location.search).get(e);
1443
1493
  }
1444
- const H = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
1494
+ const $ = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
1445
1495
  __proto__: null,
1446
- getQueryInfoByName: I,
1447
- getQueryParam: _
1448
- }, Symbol.toStringTag, { value: "Module" })), ne = {
1449
- ...H,
1496
+ getQueryInfoByName: _,
1497
+ getQueryParam: H
1498
+ }, Symbol.toStringTag, { value: "Module" })), re = {
1499
+ ...$,
1450
1500
  /**
1451
1501
  * 获取当前域名
1452
1502
  * @returns 当前url链接的host信息
@@ -1461,7 +1511,7 @@ const H = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
1461
1511
  getPath() {
1462
1512
  return window.location.pathname;
1463
1513
  }
1464
- }, re = {
1514
+ }, oe = {
1465
1515
  /**
1466
1516
  * 处理瀑布流数据,使其竖向瀑布流布局呈现横向瀑布流的展现形式。适用于 column-gap: 20rpx; column-count: 2; 布局的瀑布流
1467
1517
  * @param list 瀑布流数据-数组
@@ -1499,26 +1549,26 @@ const H = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
1499
1549
  }
1500
1550
  };
1501
1551
  export {
1502
- N as Base64Utils,
1503
- J as MoneyFormatter,
1552
+ F as Base64Utils,
1553
+ Z as MoneyFormatter,
1504
1554
  C as arrayUtils,
1505
1555
  R as booleanUtils,
1506
- U as commonUtils,
1507
- F as cookieUtils,
1508
- P as dateUtils,
1509
- q as documentUtils,
1510
- V as downloadUtils,
1511
- W as echartsUtils,
1512
- Y as letterUtils,
1513
- z as mapUtils,
1514
- Z as nameUtils,
1515
- K as numberUtils,
1556
+ T as commonUtils,
1557
+ P as cookieUtils,
1558
+ q as dateUtils,
1559
+ V as documentUtils,
1560
+ W as downloadUtils,
1561
+ Y as echartsUtils,
1562
+ z as letterUtils,
1563
+ J as mapUtils,
1564
+ K as nameUtils,
1565
+ X as numberUtils,
1516
1566
  m as objectUtils,
1517
- X as phoneUtils,
1518
- G as randomUtils,
1519
- Q as regexpUtils,
1520
- ee as storageUtils,
1521
- te as stringUtils,
1522
- ne as urlUtils,
1523
- re as waterfallUtils
1567
+ G as phoneUtils,
1568
+ Q as randomUtils,
1569
+ ee as regexpUtils,
1570
+ te as storageUtils,
1571
+ ne as stringUtils,
1572
+ re as urlUtils,
1573
+ oe as waterfallUtils
1524
1574
  };
@@ -1 +1 @@
1
- (function(f,m){typeof exports=="object"&&typeof module<"u"?m(exports):typeof define=="function"&&define.amd?define(["exports"],m):(f=typeof globalThis<"u"?globalThis:f||self,m(f.yhkitUtils={}))})(this,function(f){"use strict";const M={...{toEnumObj(e,n="value"){if(!e||!e.length)return{};const t={};return e.forEach(r=>{const o=Object.assign({label:r.label,text:r.label},r);t[r[n]]=o}),t}},...{uniqueBySet(e){if(!e)throw new Error("数组不能为空");const n=e;return Array.from(new Set(n))},uniqueByFilter(e){if(!e)throw new Error("数组不能为空");return e.filter((t,r,o)=>r===o.indexOf(t))},uniqueByReduce(e){if(!e)throw new Error("数组不能为空");return e.reduce((t,r)=>(t.includes(r)||t.push(r),t),[])},uniqueByIncludes(e){if(!e)throw new Error("数组不能为空");const n=e,t=[];return n.forEach(r=>{t.includes(r)||t.push(r)}),t},uniqueByFor(e){if(!e)throw new Error("数组不能为空");const n=e,t=[];for(let r=0;r<n.length;r++)t.includes(n[r])||t.push(n[r]);return t},uniqueByKey(e,n){if(!e||!n)throw new Error("数组不能为空或键名不能为空");const t=e,r=new Map;return t.filter(o=>r.has(o[n])?!1:(r.set(o[n],!0),!0))},unique(e,n={}){const{keys:t,compareFn:r}=n;if(!e)throw new Error("数组不能为空");const o=e;if(!t&&!r)return this.uniqueBySet(o);if(t){const s=new Map;return o.filter(a=>{const l=t.map(i=>a[i]).join("|");return s.has(l)?!1:(s.set(l,!0),!0)})}if(r)return o.filter((s,a,l)=>a===l.findIndex(i=>r(s,i)))}},...{isExistByIndexOf(e,n){return!e||!n?!1:e.indexOf(n)!==-1},isExistByIncludes(e,n){return!e||!n?!1:e.includes(n)}},...{sort(e,n="asc"){return e?e.sort((t,r)=>n==="asc"?t>r?1:-1:t<r?1:-1):[]}},...{getMaxValue(e){return e?Math.max(...e):0},getMinValue(e){return e?Math.min(...e):0},getMinValueAndIndex(e){if(e.length===0)return{value:0,index:0};const n={value:e[0],index:0};for(let t=1,r=e.length;t<r;t++){const o=e[t];n.value>o&&(n.value=o,n.index=t)}return n},getMaxValueAndIndex(e){return e.length===0?{value:0,index:0}:e.reduce((n,t,r)=>t<n.value?{value:t,index:r}:n,{value:e[0],index:0})}},...{countOfAppear(e,n){let t=0;for(const r of e)r===n&&t++;return t},indexsOfAppear(e,n){let t=-1;const r=[];do t=e.indexOf(n,t+1),t!==-1&&r.push(t);while(t!==-1);return r}},...{shuffle(e){if(!e)return[];const n=[...e];for(let t=n.length-1;t>0;t--){const r=Math.floor(Math.random()*(t+1));[n[t],n[r]]=[n[r],n[t]]}return n},sample(e,n){if(!e)return[];if(n<=0||n>e.length)throw new Error("抽样次数必须在1次到数组长度之间");const t=[...e];for(let r=0;r<n;r++){const o=Math.floor(Math.random()*(e.length-r))+r;[t[r],t[o]]=[t[o],t[r]]}return t.slice(0,n)},sampleByStart(e,n){if(!e)return[];if(n<=0||n>e.length)throw new Error("抽样次数必须在1次到数组长度之间");const t=[...e];for(let r=n-1;r>=0;r--){const o=Math.floor(Math.random()*(e.length-r))+r;[t[r],t[o]]=[t[o],t[r]]}return t.slice(0,n)},sampleByEnd(e,n){if(!e)return[];if(n<=0||n>e.length)throw new Error("抽样次数必须在1次到数组长度之间");const t=[...e];for(let r=e.length-1;r>=e.length-n;r--){const o=Math.floor(Math.random()*(r+1));[t[r],t[o]]=[t[o],t[r]]}return t.slice(e.length-n)}}};class U{static BASE64_CHARS="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";static toBlob(n,t="",r=512){const s=(n.split(",")[1]||n).replace(/-/g,"+").replace(/_/g,"/"),a="=".repeat((4-s.length%4)%4),l=s+a;try{const i=atob(l),h=[];for(let c=0;c<i.length;c+=r){const u=i.slice(c,c+r),d=new Array(u.length);for(let g=0;g<u.length;g++)d[g]=u.charCodeAt(g);const y=new Uint8Array(d);h.push(y)}return new Blob(h,{type:t})}catch(i){return console.error("Failed to convert base64 to blob:",i),null}}static toFile(n,t="file.txt",r="text/plain"){const s=n.replace(/^data:.+;base64,/,"").replace(/-/g,"+").replace(/_/g,"/"),a="=".repeat((4-s.length%4)%4),l=s+a,i=atob(l),h=[];for(let u=0;u<i.length;u+=512){const d=i.slice(u,u+512),y=new Array(d.length);for(let g=0;g<d.length;g++)y[g]=d.charCodeAt(g);h.push(new Uint8Array(y))}const c=new Blob(h,{type:r});return new File([c],t,{type:r})}static encode(n){if(!n)return"";const t=this._stringToUtf8Bytes(n);return this._bytesToBase64(t)}static decode(n){if(!n)return"";n=n.replace(/\s/g,"");const t=this._base64ToBytes(n);return this._utf8BytesToString(t)}static _stringToUtf8Bytes(n){const t=[];for(let r=0;r<n.length;r++){let o=n.charCodeAt(r);if(o<128)t.push(o);else if(o<2048)t.push(192|o>>6),t.push(128|o&63);else if(o<55296||o>=57344)t.push(224|o>>12),t.push(128|o>>6&63),t.push(128|o&63);else{r++;const s=o,a=n.charCodeAt(r);if(isNaN(a))throw new Error("代理对不完整");o=65536+((s&1023)<<10)+(a&1023),t.push(240|o>>18),t.push(128|o>>12&63),t.push(128|o>>6&63),t.push(128|o&63)}}return t}static _utf8BytesToString(n){let t="",r=0;for(;r<n.length;){const o=n[r++];if(o<128)t+=String.fromCharCode(o);else if(o>=192&&o<224){const s=n[r++]&63;t+=String.fromCharCode((o&31)<<6|s)}else if(o>=224&&o<240){const s=n[r++]&63,a=n[r++]&63;t+=String.fromCharCode((o&15)<<12|s<<6|a)}else if(o>=240&&o<248){const s=n[r++]&63,a=n[r++]&63,l=n[r++]&63,i=(o&7)<<18|s<<12|a<<6|l,h=Math.floor((i-65536)/1024)+55296,c=(i-65536)%1024+56320;t+=String.fromCharCode(h,c)}else t+="�"}return t}static _bytesToBase64(n){let t="",r=0;for(;r<n.length;){const o=n[r++],s=r<n.length,a=s?n[r++]:0,l=r<n.length,i=l?n[r++]:0,h=o>>2,c=(o&3)<<4|a>>4,u=(a&15)<<2|i>>6,d=i&63;s?l?t+=this.BASE64_CHARS.charAt(h)+this.BASE64_CHARS.charAt(c)+this.BASE64_CHARS.charAt(u)+this.BASE64_CHARS.charAt(d):t+=this.BASE64_CHARS.charAt(h)+this.BASE64_CHARS.charAt(c)+this.BASE64_CHARS.charAt(u)+"=":t+=this.BASE64_CHARS.charAt(h)+this.BASE64_CHARS.charAt(c)+"=="}return t}static _base64ToBytes(n){const t=n.length;let r=0;t>=2&&(n[t-1]==="="&&r++,n[t-2]==="="&&r++);const o=Math.floor(t*3/4)-r,s=new Array(o),a=new Array(256).fill(-1);for(let h=0;h<this.BASE64_CHARS.length;h++)a[this.BASE64_CHARS.charCodeAt(h)]=h;let l=0,i=0;for(;i<t;){const h=a[n.charCodeAt(i++)],c=a[n.charCodeAt(i++)],u=i<t?a[n.charCodeAt(i++)]:-1,d=i<t?a[n.charCodeAt(i++)]:-1;if(h===-1||c===-1)throw new Error("无效的 Base64 字符");const y=h<<2|c>>4;if(s[l++]=y,u!==-1){const g=(c&15)<<4|u>>2;if(s[l++]=g,d!==-1){const p=(u&3)<<6|d;s[l++]=p}}}return s}}const S={isEmptyString(e){return typeof e=="string"&&e.trim()===""},isNumber(e){return typeof e=="number"&&!isNaN(e)},isObject(e){return e!==null&&typeof e=="object"&&!Array.isArray(e)},isEmptyObject(e){return e?Object.keys(e).length===0&&e.constructor===Object:!0},isBoolean(e){return typeof e=="boolean"},isArray(e){return Array.isArray(e)},isFunction(e){return typeof e=="function"},isPromise(e){return!!e&&(typeof e=="object"||typeof e=="function")&&typeof e.then=="function"},isElement(e){return e instanceof Element},isPhone(e){return/^1[3-9]\d{9}$/.test(e)},isEmail(e){return/^[\w.-]+@[\w.-]+\.\w+$/.test(e)},isJSON(e){try{return JSON.parse(e),!0}catch{return!1}},isImageLoaded(e){return e.complete&&e.naturalWidth!==0},isInViewport(e){const n=e.getBoundingClientRect();return n.top>=0&&n.left>=0&&n.bottom<=window.innerHeight&&n.right<=window.innerWidth},isLeapYear(e){return e%4===0&&e%100!==0||e%400===0},isMobile(){return/Mobi|Android|iPhone/i.test(navigator.userAgent)}},b={isEmptyObject(e){return e?Object.keys(e).length===0&&e.constructor===Object:!0},copy(e,n){for(const t in e)n[t]=e[t]},deepCopy(e,n){for(const t in e){const r=e[t];r instanceof Object?(n[t]={},this.deepCopy(r,n[t])):r instanceof Array?(n[t]=[],this.deepCopy(r,n[t])):n[t]=e[t]}}},E={...{getType(e){return Object.prototype.toString.call(e).replace(/\[object\s(\w+)\]/,"$1")}},...{shallowClone(e){if(e===null||typeof e!="object")return e;if(b.isEmptyObject(e))return{};const n={};for(const t in e)n[t]=e[t];return n},deepCloneByJSON(e){return e===null||typeof e!="object"?e:b.isEmptyObject(e)?{}:JSON.parse(JSON.stringify(e))},deepCloneByMap(e,n=new WeakMap){if(e===null||typeof e!="object")return e;if(b.isEmptyObject(e))throw new Error("空对象不能进行深拷贝");if(n.has(e))return n.get(e);const t=E.getType(e);let r;switch(t){case"object":case"array":r=Array.isArray(e)?[]:{};break;case"Date":r=new Date(e);break;case"RegExp":r=new RegExp(e);break;case"Map":r=new Map(e);break;case"Set":r=new Set(e);break;default:return e}return n.set(e,r),t==="Map"?(e.forEach((o,s)=>{r.set(this.deepCloneByMap(s,n),this.deepCloneByMap(o,n))}),r):t==="Set"?(e.forEach(o=>{r.add(this.deepCloneByMap(o,n))}),r):(Reflect.ownKeys(e).forEach(o=>{r[o]=this.deepCloneByMap(e[o],n)}),r)}}},B={getCookie(e){if(!e)return;const n=document.cookie.match(new RegExp("(^| )"+e+"=([^;]+)"));return n?decodeURIComponent(n[2]):null},setCookie(e,n,t=7){const r=new Date;r.setTime(r.getTime()+t*24*60*60*1e3),document.cookie=`${e}=${encodeURIComponent(n)};expires=${r.toUTCString()};path=/`},deleteCookie(e){this.setCookie(e,"",-1)}},C={getTimeString(e,n=!1){return n?new Date().toLocaleString(e,{hour12:!0}):new Date().toLocaleString("chinese",{hour12:!1})},diffDays(e,n){const t=new Date(e).getTime(),r=new Date(n).getTime();return t>r?Math.abs(Math.floor((t-r)/(24*3600*1e3))):Math.abs(Math.floor((r-t)/(24*3600*1e3)))},uniqueId(){return Date.now().toString(36)+Math.random().toString(36).substr(2,5)},getWhichDays(e,n,t){let r=t;for(let o=1;o<n;o++)switch(o){case 1:case 3:case 5:case 7:case 8:case 10:case 12:r+=31;break;case 2:S.isLeapYear(e)?r+=29:r+=28;break;default:r+=30;break}return r},getTimeStringAutoShort2(e,n){const t=new Date,r=new Date(e),o=t.getFullYear(),s=t.getMonth()+1,a=t.getDate(),l=r.getFullYear(),i=r.getMonth()+1,h=r.getDate();let c="";const u=n?" "+this.formatDate(r,"hh:mm"):"";if(o===l){const g=t.getTime()-e;if(s===i&&a===h)g<60*1e3?c="刚刚":c=this.formatDate(r,"hh:mm");else{const p=new Date;p.setDate(p.getDate()-1);const A=new Date;if(A.setDate(A.getDate()-2),i===p.getMonth()+1&&h===p.getDate())c="昨天"+u;else if(i===A.getMonth()+1&&h===A.getDate())c="前天"+u;else if(g/36e5<=7*24){const w=new Array(7);w[0]="星期日",w[1]="星期一",w[2]="星期二",w[3]="星期三",w[4]="星期四",w[5]="星期五",w[6]="星期六",c=w[r.getDay()]+u}else c=this.formatDate(r,"yyyy/M/d")+u}}else c=this.formatDate(r,"yyyy/M/d")+u;return c},formatDate(e,n){const t={"M+":e.getMonth()+1,"d+":e.getDate(),"h+":e.getHours(),"m+":e.getMinutes(),"s+":e.getSeconds(),"q+":Math.floor((e.getMonth()+3)/3),S:e.getMilliseconds()};/(y+)/.test(n)&&(n=n.replace(RegExp.$1,(e.getFullYear()+"").substr(4-RegExp.$1.length)));for(const r in t)new RegExp("("+r+")").test(n)&&(n=n.replace(RegExp.$1,RegExp.$1.length===1?t[r]:("00"+t[r]).substr((""+t[r]).length)));return n}},x={getOffsetTop(e){if(!e)throw new Error("Element is not provided");if(e instanceof SVGElement){const t=e.getBoundingClientRect(),r=window.pageYOffset||document.documentElement.scrollTop;return t.top+r}let n=0;for(;e;)n+=e.offsetTop,e=e.offsetParent;return n},getScrollValue(){const e={scrollLeft:0,scrollTop:0};return e.scrollLeft=document.body.scrollLeft||document.documentElement.scrollLeft,e.scrollTop=document.body.scrollTop||document.documentElement.scrollTop,e},getPageValue(e){e=e||window.event;const n=e.pageX||e.clientX+this.getScrollValue().scrollLeft,t=e.pageY||e.clientY+this.getScrollValue().scrollTop;return{pageX:n,pageY:t}},addEventListener(e,n,t){e.addEventListener?e.addEventListener(n,t):e.attachEvent?e.attachEvent("on"+n,t):e["on"+n]=t},getViewportWidth(){return window.innerWidth||document.documentElement.clientWidth||document.body.clientWidth},getViewportHeight(){return window.innerHeight||document.documentElement.clientHeight||document.body.clientHeight}},R={saveAsBlob(e,n){const t=document.createElement("a"),r=window.URL.createObjectURL(e);t.href=r,t.download=n,document.body.appendChild(t),t.click(),URL.revokeObjectURL(r),document.body.removeChild(t)},saveAsUrl(e,n){const t=document.createElement("a");t.href=e,t.download=n,document.body.appendChild(t),t.click(),URL.revokeObjectURL(e),document.body.removeChild(t)}},D={animate(e,n){let t=-1;const r=e.series[0].data.length;let o;o=setInterval(()=>{n.dispatchAction({type:"downplay",seriesIndex:0,dataIndex:t}),t=(t+1)%r,n.dispatchAction({type:"highlight",seriesIndex:0,dataIndex:t}),n.dispatchAction({type:"showTip",seriesIndex:0,dataIndex:t}),t>r&&(t=0)},2e3),n.on("mouseover",()=>{clearInterval(o),n.dispatchAction({type:"downplay",seriesIndex:0,dataIndex:t})})}},O={sortFromA2Z(e){return e?.length?e.sort((t,r)=>{const o=t.toUpperCase(),s=r.toUpperCase();return o<s?-1:o>s?1:0}):void 0}},T={degrees2Radians(e){return e*Math.PI/180},getDistance(e,n,t,r){const o=this.degrees2Radians(e),s=this.degrees2Radians(t),a=o-s,l=this.degrees2Radians(n)-this.degrees2Radians(r);let i=2*Math.asin(Math.sqrt(Math.pow(Math.sin(a/2),2)+Math.cos(o)*Math.cos(s)*Math.pow(Math.sin(l/2),2)));return i=i*6378.137,i=Math.round(i*1e4)/1e4,i=+i.toFixed(2),console.log("经纬度计算的距离为:"+i),i},calculateDistanceByHaversine(e,n,t="km"){const r=this,o=e.longitude??e.lng,s=e.latitude??e.lat,a=n.longitude??n.lng,l=n.latitude??n.lat;if(o===void 0||s===void 0||a===void 0||l===void 0)throw new Error("无效的坐标格式,缺少经纬度信息");const i=6371,h=r.degrees2Radians(s),c=r.degrees2Radians(l),u=r.degrees2Radians(l-s),d=r.degrees2Radians(a-o),y=Math.sin(u/2)*Math.sin(u/2)+Math.cos(h)*Math.cos(c)*Math.sin(d/2)*Math.sin(d/2),g=2*Math.atan2(Math.sqrt(y),Math.sqrt(1-y)),p=i*g;switch(t){case"m":return p*1e3;case"mi":return p*.621371;case"nmi":return p*.539957;default:return p}},calculateDistancesByHaversine(e,n="km",t=!1){if(e.length<2)return{segments:[],total:0};const r=[];let o=0;for(let s=0;s<e.length-1;s++){const a=this.calculateDistanceByHaversine(e[s],e[s+1],n);r.push(a),o+=a}if(t&&e.length>2){const s=this.calculateDistanceByHaversine(e[e.length-1],e[0],n);r.push(s),o+=s}return{segments:r,total:o}}};class j{static toStandardFormat(n){try{const t=typeof n=="string"?parseFloat(n):n;if(isNaN(t))throw new Error("输入不是有效的数字");if(!isFinite(t))throw new Error("输入是无穷大");return t.toFixed(2).toString().replace(/\B(?=(\d{3})+(?!\d))/g,",")}catch(t){return console.error("格式化失败:",t),"格式错误"}}static toChineseFormat(n){try{const t=typeof n=="string"?parseFloat(n):n;if(isNaN(t))throw new Error("输入不是有效的数字");if(t>9999999999999e-2||t<-9999999999999e-2)throw new Error("输入数字超出范围");const r=t<0,o=Math.abs(t),s=Math.floor(o),a=Math.round((o-s)*100),l=["零","壹","贰","叁","肆","伍","陆","柒","捌","玖"],i=["","拾","佰","仟","万","拾","佰","仟","亿","拾","佰","仟"],h=["角","分"];let c="",u=s;if(u===0)c=l[0];else{let g=0;for(;u>0;){const p=u%10;p!==0?c=l[p]+i[g]+c:c.charAt(0)!==l[0]&&(c=l[p]+c),u=Math.floor(u/10),g++}c=c.replace(/零+/g,"零"),c=c.replace(/零+$/,"")}let d="";if(a>0){const g=Math.floor(a/10),p=a%10;g>0&&(d+=l[g]+h[0]),p>0&&(d+=l[p]+h[1])}else d="整";let y=(r?"负":"")+c+"圆"+d;return y==="零圆整"&&(y="零圆"),y}catch(t){return console.error("转换失败:",t),"格式错误"}}}const v={desensitizeChineseName(e,n={}){const{keepLength:t=1,keepLast:r=!1}=n;if(!e||e.length===0||e.trim().length===0)throw new Error("姓名不能为空");if(typeof e!="string")throw new Error("姓名必须是字符串");if(e.length<=1)return e;const o=["欧阳","司马","上官","东方","独孤","南宫","闻人","夏侯","诸葛","尉迟","公孙","长孙","宇文","司徒","慕容"];n.compoundSurname&&n.compoundSurname.trim().length>0&&!o.includes(n.compoundSurname)&&o.push(n.compoundSurname);let s="";o.some(l=>e.startsWith(l))?s=o.find(l=>e.startsWith(l))||"":s=e[0]||"";const a=Math.max(t,s.length);if(a>=e.length)return e;if(r&&e.length>2){const l=e.slice(0,a),i=e.slice(-1),h=e.length-a-1;return`${l}${"*".repeat(h)}${i}`}return`${e.slice(0,a)}${"*".repeat(e.length-a)}`}},L={...Object.freeze(Object.defineProperty({__proto__:null,toLetter:e=>e>25||e<0?"":"ABCDEFGHIJKLMNOPQRSTUVWXYZ"[e]},Symbol.toStringTag,{value:"Module"})),...Object.freeze(Object.defineProperty({__proto__:null,toMoney:e=>e.toFixed(2).toString().replace(/\B(?=(\d{3})+(?!\d))/g,",")},Symbol.toStringTag,{value:"Module"})),isNumber(e){return typeof e=="number"&&!isNaN(e)}},I={desensitize(e){return e?e.replace(/^(\d{3})\d{4}(\d{4})$/,"$1****$2")||e.slice(0,3)+"****"+e.slice(7):""}},_={color:function(){return`#${Math.random().toString(16).slice(2,8)}`},int(e,n){return Math.floor(Math.random()*(n-e+1))+e},uniqueId(){return Date.now().toString(36)+Math.random().toString(36).substr(2,5)}},k={mobile:/^1[3-9]\d{9}$/,email:/^[A-Za-z0-9\u4e00-\u9fa5]+@[a-zA-Z0-9_-]+(\.[a-zA-Z0-9_-]+)+$/,chinese:/^[\u4e00-\u9fa5]+$/,english:/^[a-zA-Z]+$/,chineseStart:/^[\u4e00-\u9fa5]+\w*$/,integer:/^\d+$/,integerAndzero:/^(0|[1-9]+[0-9]*)$/,strongPassword:/^(?!.*[\s\p{C}])(?:(?=.*[A-Z])(?=.*[a-z])(?=.*[\d\W])|(?=.*\d)(?=.*[^\w\s])).{8,}$/u,decimal:/^0\.(0[1-9]|[1-9][0-9]*)$/},H={getLocal(e){return localStorage.getItem(e)},setLocal(e,n){localStorage.setItem(e,n)},removeLocal(e){localStorage.removeItem(e)},getSession(e){return sessionStorage.getItem(e)},setSession(e,n){sessionStorage.setItem(e,n)},removeSession(e){sessionStorage.removeItem(e)}},$={isExist(e,n){if(!e||!n)return!1;const t=e.split(",");return console.log("判断某元素是否在字符串中",t.indexOf(n)===-1),t.indexOf(n)!==-1},includes(e,n){return!e||!n?!1:e.includes(n)},isJSON(e){try{return JSON.parse(e),!0}catch{return!1}},indexsOfAppear(e,n){let t=-1;const r=[];do t=e.indexOf(n,t+1),t!==-1&&r.push(t);while(t!==-1);return r},getMaxTimesAndVal(e){const n=[0,""],t={};for(let s=0;s<e.length;s++){const a=e.charAt(s);t[a]?t[a]++:t[a]=1}let r=1;for(const s in t)r<t[s]&&(r=t[s]);const o=[];for(const s in t)r==t[s]&&o.push(s);return n[0]=r,n[1]=o.join(),n},mask(e,n,t){if(!e)throw new Error("字符串为空");if(typeof n!="number"||typeof t!="number")throw new Error("开始位置或结束位置为空");if(n<0||t>e.length||n>t)throw new Error("开始位置小于0或结束位置超出字符串长度或开始位置大于结束位置");return e.slice(0,n)+"*".repeat(t-n+1)+e.slice(t)}},N=e=>{const t=new RegExp("[?&]"+e+"=([^&#]*)","gi").exec(window.location.href);return t?decodeURIComponent(t[1]):null};function F(e){return new URLSearchParams(window.location.search).get(e)}const q={...Object.freeze(Object.defineProperty({__proto__:null,getQueryInfoByName:N,getQueryParam:F},Symbol.toStringTag,{value:"Module"})),getHost(){return window.location.host},getPath(){return window.location.pathname}},P={toList(e,n=2){console.log(e,n);const t={};for(let o=0;o<n;o++)t[o]=[];e.forEach((o,s)=>t[s%n].push(o));const r=[];for(const o in t)r.push(...t[o]);return r},jsLayout(e,n,t){const r=e.offsetWidth,o=n[0].offsetWidth,s=parseInt((r/o).toString()),a=(r-o*s)/(s-1),l=[];for(let i=0,h=n.length;i<h;i++){const c=n[i];if(i<s)c.style.left=(o+a)*i+"px",l[i]=c.offsetHeight;else{const{index:u,value:d}=M.getMinValueAndIndex(l);c.style.left=(o+a)*u+"px",c.style.top=d+t+"px",l[u]=c.offsetHeight+t+d}}}};f.Base64Utils=U,f.MoneyFormatter=j,f.arrayUtils=M,f.booleanUtils=S,f.commonUtils=E,f.cookieUtils=B,f.dateUtils=C,f.documentUtils=x,f.downloadUtils=R,f.echartsUtils=D,f.letterUtils=O,f.mapUtils=T,f.nameUtils=v,f.numberUtils=L,f.objectUtils=b,f.phoneUtils=I,f.randomUtils=_,f.regexpUtils=k,f.storageUtils=H,f.stringUtils=$,f.urlUtils=q,f.waterfallUtils=P,Object.defineProperty(f,Symbol.toStringTag,{value:"Module"})});
1
+ (function(f,m){typeof exports=="object"&&typeof module<"u"?m(exports):typeof define=="function"&&define.amd?define(["exports"],m):(f=typeof globalThis<"u"?globalThis:f||self,m(f.yhkitUtils={}))})(this,function(f){"use strict";const M={...{toEnumObj(e,n="value"){if(!e||!e.length)return{};const t={};return e.forEach(r=>{const o=Object.assign({label:r.label,text:r.label},r);t[r[n]]=o}),t}},...{uniqueBySet(e){if(!e)throw new Error("数组不能为空");const n=e;return Array.from(new Set(n))},uniqueByFilter(e){if(!e)throw new Error("数组不能为空");return e.filter((t,r,o)=>r===o.indexOf(t))},uniqueByReduce(e){if(!e)throw new Error("数组不能为空");return e.reduce((t,r)=>(t.includes(r)||t.push(r),t),[])},uniqueByIncludes(e){if(!e)throw new Error("数组不能为空");const n=e,t=[];return n.forEach(r=>{t.includes(r)||t.push(r)}),t},uniqueByFor(e){if(!e)throw new Error("数组不能为空");const n=e,t=[];for(let r=0;r<n.length;r++)t.includes(n[r])||t.push(n[r]);return t},uniqueByKey(e,n){if(!e||!n)throw new Error("数组不能为空或键名不能为空");const t=e,r=new Map;return t.filter(o=>r.has(o[n])?!1:(r.set(o[n],!0),!0))},unique(e,n={}){const{keys:t,compareFn:r}=n;if(!e)throw new Error("数组不能为空");const o=e;if(!t&&!r)return this.uniqueBySet(o);if(t){const s=new Map;return o.filter(c=>{const l=t.map(i=>c[i]).join("|");return s.has(l)?!1:(s.set(l,!0),!0)})}if(r)return o.filter((s,c,l)=>c===l.findIndex(i=>r(s,i)))}},...{isExistByIndexOf(e,n){return!e||!n?!1:e.indexOf(n)!==-1},isExistByIncludes(e,n){return!e||!n?!1:e.includes(n)}},...{sort(e,n="asc"){return e?e.sort((t,r)=>n==="asc"?t>r?1:-1:t<r?1:-1):[]}},...{getMaxValue(e){return e?Math.max(...e):0},getMinValue(e){return e?Math.min(...e):0},getMinValueAndIndex(e){if(e.length===0)return{value:0,index:0};const n={value:e[0],index:0};for(let t=1,r=e.length;t<r;t++){const o=e[t];n.value>o&&(n.value=o,n.index=t)}return n},getMaxValueAndIndex(e){return e.length===0?{value:0,index:0}:e.reduce((n,t,r)=>t<n.value?{value:t,index:r}:n,{value:e[0],index:0})}},...{countOfAppear(e,n){let t=0;for(const r of e)r===n&&t++;return t},indexsOfAppear(e,n){let t=-1;const r=[];do t=e.indexOf(n,t+1),t!==-1&&r.push(t);while(t!==-1);return r}},...{shuffle(e){if(!e)return[];const n=[...e];for(let t=n.length-1;t>0;t--){const r=Math.floor(Math.random()*(t+1));[n[t],n[r]]=[n[r],n[t]]}return n},sample(e,n){if(!e)return[];if(n<=0||n>e.length)throw new Error("抽样次数必须在1次到数组长度之间");const t=[...e];for(let r=0;r<n;r++){const o=Math.floor(Math.random()*(e.length-r))+r;[t[r],t[o]]=[t[o],t[r]]}return t.slice(0,n)},sampleByStart(e,n){if(!e)return[];if(n<=0||n>e.length)throw new Error("抽样次数必须在1次到数组长度之间");const t=[...e];for(let r=n-1;r>=0;r--){const o=Math.floor(Math.random()*(e.length-r))+r;[t[r],t[o]]=[t[o],t[r]]}return t.slice(0,n)},sampleByEnd(e,n){if(!e)return[];if(n<=0||n>e.length)throw new Error("抽样次数必须在1次到数组长度之间");const t=[...e];for(let r=e.length-1;r>=e.length-n;r--){const o=Math.floor(Math.random()*(r+1));[t[r],t[o]]=[t[o],t[r]]}return t.slice(e.length-n)}}};class U{static BASE64_CHARS="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";static toBlob(n,t="",r=512){const s=(n.split(",")[1]||n).replace(/-/g,"+").replace(/_/g,"/"),c="=".repeat((4-s.length%4)%4),l=s+c;try{const i=atob(l),h=[];for(let a=0;a<i.length;a+=r){const u=i.slice(a,a+r),d=new Array(u.length);for(let g=0;g<u.length;g++)d[g]=u.charCodeAt(g);const y=new Uint8Array(d);h.push(y)}return new Blob(h,{type:t})}catch(i){return console.error("Failed to convert base64 to blob:",i),null}}static toFile(n,t="file.txt",r="text/plain"){const s=n.replace(/^data:.+;base64,/,"").replace(/-/g,"+").replace(/_/g,"/"),c="=".repeat((4-s.length%4)%4),l=s+c,i=atob(l),h=[];for(let u=0;u<i.length;u+=512){const d=i.slice(u,u+512),y=new Array(d.length);for(let g=0;g<d.length;g++)y[g]=d.charCodeAt(g);h.push(new Uint8Array(y))}const a=new Blob(h,{type:r});return new File([a],t,{type:r})}static encode(n){if(!n)return"";const t=this._stringToUtf8Bytes(n);return this._bytesToBase64(t)}static decode(n){if(!n)return"";n=n.replace(/\s/g,"");const t=this._base64ToBytes(n);return this._utf8BytesToString(t)}static _stringToUtf8Bytes(n){const t=[];for(let r=0;r<n.length;r++){let o=n.charCodeAt(r);if(o<128)t.push(o);else if(o<2048)t.push(192|o>>6),t.push(128|o&63);else if(o<55296||o>=57344)t.push(224|o>>12),t.push(128|o>>6&63),t.push(128|o&63);else{r++;const s=o,c=n.charCodeAt(r);if(isNaN(c))throw new Error("代理对不完整");o=65536+((s&1023)<<10)+(c&1023),t.push(240|o>>18),t.push(128|o>>12&63),t.push(128|o>>6&63),t.push(128|o&63)}}return t}static _utf8BytesToString(n){let t="",r=0;for(;r<n.length;){const o=n[r++];if(o<128)t+=String.fromCharCode(o);else if(o>=192&&o<224){const s=n[r++]&63;t+=String.fromCharCode((o&31)<<6|s)}else if(o>=224&&o<240){const s=n[r++]&63,c=n[r++]&63;t+=String.fromCharCode((o&15)<<12|s<<6|c)}else if(o>=240&&o<248){const s=n[r++]&63,c=n[r++]&63,l=n[r++]&63,i=(o&7)<<18|s<<12|c<<6|l,h=Math.floor((i-65536)/1024)+55296,a=(i-65536)%1024+56320;t+=String.fromCharCode(h,a)}else t+="�"}return t}static _bytesToBase64(n){let t="",r=0;for(;r<n.length;){const o=n[r++],s=r<n.length,c=s?n[r++]:0,l=r<n.length,i=l?n[r++]:0,h=o>>2,a=(o&3)<<4|c>>4,u=(c&15)<<2|i>>6,d=i&63;s?l?t+=this.BASE64_CHARS.charAt(h)+this.BASE64_CHARS.charAt(a)+this.BASE64_CHARS.charAt(u)+this.BASE64_CHARS.charAt(d):t+=this.BASE64_CHARS.charAt(h)+this.BASE64_CHARS.charAt(a)+this.BASE64_CHARS.charAt(u)+"=":t+=this.BASE64_CHARS.charAt(h)+this.BASE64_CHARS.charAt(a)+"=="}return t}static _base64ToBytes(n){const t=n.length;let r=0;t>=2&&(n[t-1]==="="&&r++,n[t-2]==="="&&r++);const o=Math.floor(t*3/4)-r,s=new Array(o),c=new Array(256).fill(-1);for(let h=0;h<this.BASE64_CHARS.length;h++)c[this.BASE64_CHARS.charCodeAt(h)]=h;let l=0,i=0;for(;i<t;){const h=c[n.charCodeAt(i++)],a=c[n.charCodeAt(i++)],u=i<t?c[n.charCodeAt(i++)]:-1,d=i<t?c[n.charCodeAt(i++)]:-1;if(h===-1||a===-1)throw new Error("无效的 Base64 字符");const y=h<<2|a>>4;if(s[l++]=y,u!==-1){const g=(a&15)<<4|u>>2;if(s[l++]=g,d!==-1){const p=(u&3)<<6|d;s[l++]=p}}}return s}}const S={isEmptyString(e){return typeof e=="string"&&e.trim()===""},isNumber(e){return typeof e=="number"&&!isNaN(e)},isObject(e){return e!==null&&typeof e=="object"&&!Array.isArray(e)},isEmptyObject(e){return e?Object.keys(e).length===0&&e.constructor===Object:!0},isBoolean(e){return typeof e=="boolean"},isArray(e){return Array.isArray(e)},isFunction(e){return typeof e=="function"},isPromise(e){return!!e&&(typeof e=="object"||typeof e=="function")&&typeof e.then=="function"},isElement(e){return e instanceof Element},isPhone(e){return/^1[3-9]\d{9}$/.test(e)},isEmail(e){return/^[\w.-]+@[\w.-]+\.\w+$/.test(e)},isJSON(e){try{return JSON.parse(e),!0}catch{return!1}},isImageLoaded(e){return e.complete&&e.naturalWidth!==0},isInViewport(e){const n=e.getBoundingClientRect();return n.top>=0&&n.left>=0&&n.bottom<=window.innerHeight&&n.right<=window.innerWidth},isLeapYear(e){return e%4===0&&e%100!==0||e%400===0},isMobile(){return/Mobi|Android|iPhone/i.test(navigator.userAgent)}},b={isEmptyObject(e){return e?Object.keys(e).length===0&&e.constructor===Object:!0},copy(e,n){for(const t in e)n[t]=e[t]},deepCopy(e,n){for(const t in e){const r=e[t];r instanceof Object?(n[t]={},this.deepCopy(r,n[t])):r instanceof Array?(n[t]=[],this.deepCopy(r,n[t])):n[t]=e[t]}}},E={...{getType(e){return Object.prototype.toString.call(e).replace(/\[object\s(\w+)\]/,"$1")}},...{shallowClone(e){if(e===null||typeof e!="object")return e;if(b.isEmptyObject(e))return{};const n={};for(const t in e)n[t]=e[t];return n},deepCloneByJSON(e){return e===null||typeof e!="object"?e:b.isEmptyObject(e)?{}:JSON.parse(JSON.stringify(e))},deepCloneByMap(e,n=new WeakMap){if(e===null||typeof e!="object")return e;if(b.isEmptyObject(e))throw new Error("空对象不能进行深拷贝");if(n.has(e))return n.get(e);const t=E.getType(e);let r;switch(t){case"object":case"array":r=Array.isArray(e)?[]:{};break;case"Date":r=new Date(e);break;case"RegExp":r=new RegExp(e);break;case"Map":r=new Map(e);break;case"Set":r=new Set(e);break;default:return e}return n.set(e,r),t==="Map"?(e.forEach((o,s)=>{r.set(this.deepCloneByMap(s,n),this.deepCloneByMap(o,n))}),r):t==="Set"?(e.forEach(o=>{r.add(this.deepCloneByMap(o,n))}),r):(Reflect.ownKeys(e).forEach(o=>{r[o]=this.deepCloneByMap(e[o],n)}),r)}},...{curry(e){if(typeof e!="function")throw new TypeError("curry: fn must be a function, but got "+typeof e);const n=e.length;return function t(...r){return r.length>=n?e.apply(this,r):function(...o){return t.apply(this,[...r,...o])}}},uncurry(e){return function(n,...t){return e.call(n,...t)}}}},B={getCookie(e){if(!e)return;const n=document.cookie.match(new RegExp("(^| )"+e+"=([^;]+)"));return n?decodeURIComponent(n[2]):null},setCookie(e,n,t=7){const r=new Date;r.setTime(r.getTime()+t*24*60*60*1e3),document.cookie=`${e}=${encodeURIComponent(n)};expires=${r.toUTCString()};path=/`},deleteCookie(e){this.setCookie(e,"",-1)}},C={getTimeString(e,n=!1){return n?new Date().toLocaleString(e,{hour12:!0}):new Date().toLocaleString("chinese",{hour12:!1})},diffDays(e,n){const t=new Date(e).getTime(),r=new Date(n).getTime();return t>r?Math.abs(Math.floor((t-r)/(24*3600*1e3))):Math.abs(Math.floor((r-t)/(24*3600*1e3)))},uniqueId(){return Date.now().toString(36)+Math.random().toString(36).substr(2,5)},getWhichDays(e,n,t){let r=t;for(let o=1;o<n;o++)switch(o){case 1:case 3:case 5:case 7:case 8:case 10:case 12:r+=31;break;case 2:S.isLeapYear(e)?r+=29:r+=28;break;default:r+=30;break}return r},getTimeStringAutoShort2(e,n){const t=new Date,r=new Date(e),o=t.getFullYear(),s=t.getMonth()+1,c=t.getDate(),l=r.getFullYear(),i=r.getMonth()+1,h=r.getDate();let a="";const u=n?" "+this.formatDate(r,"hh:mm"):"";if(o===l){const g=t.getTime()-e;if(s===i&&c===h)g<60*1e3?a="刚刚":a=this.formatDate(r,"hh:mm");else{const p=new Date;p.setDate(p.getDate()-1);const A=new Date;if(A.setDate(A.getDate()-2),i===p.getMonth()+1&&h===p.getDate())a="昨天"+u;else if(i===A.getMonth()+1&&h===A.getDate())a="前天"+u;else if(g/36e5<=7*24){const w=new Array(7);w[0]="星期日",w[1]="星期一",w[2]="星期二",w[3]="星期三",w[4]="星期四",w[5]="星期五",w[6]="星期六",a=w[r.getDay()]+u}else a=this.formatDate(r,"yyyy/M/d")+u}}else a=this.formatDate(r,"yyyy/M/d")+u;return a},formatDate(e,n){const t={"M+":e.getMonth()+1,"d+":e.getDate(),"h+":e.getHours(),"m+":e.getMinutes(),"s+":e.getSeconds(),"q+":Math.floor((e.getMonth()+3)/3),S:e.getMilliseconds()};/(y+)/.test(n)&&(n=n.replace(RegExp.$1,(e.getFullYear()+"").substr(4-RegExp.$1.length)));for(const r in t)new RegExp("("+r+")").test(n)&&(n=n.replace(RegExp.$1,RegExp.$1.length===1?t[r]:("00"+t[r]).substr((""+t[r]).length)));return n}},x={getOffsetTop(e){if(!e)throw new Error("Element is not provided");if(e instanceof SVGElement){const t=e.getBoundingClientRect(),r=window.pageYOffset||document.documentElement.scrollTop;return t.top+r}let n=0;for(;e;)n+=e.offsetTop,e=e.offsetParent;return n},getScrollValue(){const e={scrollLeft:0,scrollTop:0};return e.scrollLeft=document.body.scrollLeft||document.documentElement.scrollLeft,e.scrollTop=document.body.scrollTop||document.documentElement.scrollTop,e},getPageValue(e){e=e||window.event;const n=e.pageX||e.clientX+this.getScrollValue().scrollLeft,t=e.pageY||e.clientY+this.getScrollValue().scrollTop;return{pageX:n,pageY:t}},addEventListener(e,n,t){e.addEventListener?e.addEventListener(n,t):e.attachEvent?e.attachEvent("on"+n,t):e["on"+n]=t},getViewportWidth(){return window.innerWidth||document.documentElement.clientWidth||document.body.clientWidth},getViewportHeight(){return window.innerHeight||document.documentElement.clientHeight||document.body.clientHeight}},R={saveAsBlob(e,n){const t=document.createElement("a"),r=window.URL.createObjectURL(e);t.href=r,t.download=n,document.body.appendChild(t),t.click(),URL.revokeObjectURL(r),document.body.removeChild(t)},saveAsUrl(e,n){const t=document.createElement("a");t.href=e,t.download=n,document.body.appendChild(t),t.click(),URL.revokeObjectURL(e),document.body.removeChild(t)}},D={animate(e,n){let t=-1;const r=e.series[0].data.length;let o;o=setInterval(()=>{n.dispatchAction({type:"downplay",seriesIndex:0,dataIndex:t}),t=(t+1)%r,n.dispatchAction({type:"highlight",seriesIndex:0,dataIndex:t}),n.dispatchAction({type:"showTip",seriesIndex:0,dataIndex:t}),t>r&&(t=0)},2e3),n.on("mouseover",()=>{clearInterval(o),n.dispatchAction({type:"downplay",seriesIndex:0,dataIndex:t})})}},O={sortFromA2Z(e){return e?.length?e.sort((t,r)=>{const o=t.toUpperCase(),s=r.toUpperCase();return o<s?-1:o>s?1:0}):void 0}},T={degrees2Radians(e){return e*Math.PI/180},getDistance(e,n,t,r){const o=this.degrees2Radians(e),s=this.degrees2Radians(t),c=o-s,l=this.degrees2Radians(n)-this.degrees2Radians(r);let i=2*Math.asin(Math.sqrt(Math.pow(Math.sin(c/2),2)+Math.cos(o)*Math.cos(s)*Math.pow(Math.sin(l/2),2)));return i=i*6378.137,i=Math.round(i*1e4)/1e4,i=+i.toFixed(2),console.log("经纬度计算的距离为:"+i),i},calculateDistanceByHaversine(e,n,t="km"){const r=this,o=e.longitude??e.lng,s=e.latitude??e.lat,c=n.longitude??n.lng,l=n.latitude??n.lat;if(o===void 0||s===void 0||c===void 0||l===void 0)throw new Error("无效的坐标格式,缺少经纬度信息");const i=6371,h=r.degrees2Radians(s),a=r.degrees2Radians(l),u=r.degrees2Radians(l-s),d=r.degrees2Radians(c-o),y=Math.sin(u/2)*Math.sin(u/2)+Math.cos(h)*Math.cos(a)*Math.sin(d/2)*Math.sin(d/2),g=2*Math.atan2(Math.sqrt(y),Math.sqrt(1-y)),p=i*g;switch(t){case"m":return p*1e3;case"mi":return p*.621371;case"nmi":return p*.539957;default:return p}},calculateDistancesByHaversine(e,n="km",t=!1){if(e.length<2)return{segments:[],total:0};const r=[];let o=0;for(let s=0;s<e.length-1;s++){const c=this.calculateDistanceByHaversine(e[s],e[s+1],n);r.push(c),o+=c}if(t&&e.length>2){const s=this.calculateDistanceByHaversine(e[e.length-1],e[0],n);r.push(s),o+=s}return{segments:r,total:o}}};class j{static toStandardFormat(n){try{const t=typeof n=="string"?parseFloat(n):n;if(isNaN(t))throw new Error("输入不是有效的数字");if(!isFinite(t))throw new Error("输入是无穷大");return t.toFixed(2).toString().replace(/\B(?=(\d{3})+(?!\d))/g,",")}catch(t){return console.error("格式化失败:",t),"格式错误"}}static toChineseFormat(n){try{const t=typeof n=="string"?parseFloat(n):n;if(isNaN(t))throw new Error("输入不是有效的数字");if(t>9999999999999e-2||t<-9999999999999e-2)throw new Error("输入数字超出范围");const r=t<0,o=Math.abs(t),s=Math.floor(o),c=Math.round((o-s)*100),l=["零","壹","贰","叁","肆","伍","陆","柒","捌","玖"],i=["","拾","佰","仟","万","拾","佰","仟","亿","拾","佰","仟"],h=["角","分"];let a="",u=s;if(u===0)a=l[0];else{let g=0;for(;u>0;){const p=u%10;p!==0?a=l[p]+i[g]+a:a.charAt(0)!==l[0]&&(a=l[p]+a),u=Math.floor(u/10),g++}a=a.replace(/零+/g,"零"),a=a.replace(/零+$/,"")}let d="";if(c>0){const g=Math.floor(c/10),p=c%10;g>0&&(d+=l[g]+h[0]),p>0&&(d+=l[p]+h[1])}else d="整";let y=(r?"负":"")+a+"圆"+d;return y==="零圆整"&&(y="零圆"),y}catch(t){return console.error("转换失败:",t),"格式错误"}}}const v={desensitizeChineseName(e,n={}){const{keepLength:t=1,keepLast:r=!1}=n;if(!e||e.length===0||e.trim().length===0)throw new Error("姓名不能为空");if(typeof e!="string")throw new Error("姓名必须是字符串");if(e.length<=1)return e;const o=["欧阳","司马","上官","东方","独孤","南宫","闻人","夏侯","诸葛","尉迟","公孙","长孙","宇文","司徒","慕容"];n.compoundSurname&&n.compoundSurname.trim().length>0&&!o.includes(n.compoundSurname)&&o.push(n.compoundSurname);let s="";o.some(l=>e.startsWith(l))?s=o.find(l=>e.startsWith(l))||"":s=e[0]||"";const c=Math.max(t,s.length);if(c>=e.length)return e;if(r&&e.length>2){const l=e.slice(0,c),i=e.slice(-1),h=e.length-c-1;return`${l}${"*".repeat(h)}${i}`}return`${e.slice(0,c)}${"*".repeat(e.length-c)}`}},L={...Object.freeze(Object.defineProperty({__proto__:null,toLetter:e=>e>25||e<0?"":"ABCDEFGHIJKLMNOPQRSTUVWXYZ"[e]},Symbol.toStringTag,{value:"Module"})),...Object.freeze(Object.defineProperty({__proto__:null,toMoney:e=>e.toFixed(2).toString().replace(/\B(?=(\d{3})+(?!\d))/g,",")},Symbol.toStringTag,{value:"Module"})),isNumber(e){return typeof e=="number"&&!isNaN(e)}},I={desensitize(e){return e?e.replace(/^(\d{3})\d{4}(\d{4})$/,"$1****$2")||e.slice(0,3)+"****"+e.slice(7):""}},_={color:function(){return`#${Math.random().toString(16).slice(2,8)}`},int(e,n){return Math.floor(Math.random()*(n-e+1))+e},uniqueId(){return Date.now().toString(36)+Math.random().toString(36).substr(2,5)}},k={mobile:/^1[3-9]\d{9}$/,email:/^[A-Za-z0-9\u4e00-\u9fa5]+@[a-zA-Z0-9_-]+(\.[a-zA-Z0-9_-]+)+$/,chinese:/^[\u4e00-\u9fa5]+$/,english:/^[a-zA-Z]+$/,chineseStart:/^[\u4e00-\u9fa5]+\w*$/,integer:/^\d+$/,integerAndzero:/^(0|[1-9]+[0-9]*)$/,strongPassword:/^(?!.*[\s\p{C}])(?:(?=.*[A-Z])(?=.*[a-z])(?=.*[\d\W])|(?=.*\d)(?=.*[^\w\s])).{8,}$/u,decimal:/^0\.(0[1-9]|[1-9][0-9]*)$/},H={getLocal(e){return localStorage.getItem(e)},setLocal(e,n){localStorage.setItem(e,n)},removeLocal(e){localStorage.removeItem(e)},getSession(e){return sessionStorage.getItem(e)},setSession(e,n){sessionStorage.setItem(e,n)},removeSession(e){sessionStorage.removeItem(e)}},$={isExist(e,n){if(!e||!n)return!1;const t=e.split(",");return console.log("判断某元素是否在字符串中",t.indexOf(n)===-1),t.indexOf(n)!==-1},includes(e,n){return!e||!n?!1:e.includes(n)},isJSON(e){try{return JSON.parse(e),!0}catch{return!1}},indexsOfAppear(e,n){let t=-1;const r=[];do t=e.indexOf(n,t+1),t!==-1&&r.push(t);while(t!==-1);return r},getMaxTimesAndVal(e){const n=[0,""],t={};for(let s=0;s<e.length;s++){const c=e.charAt(s);t[c]?t[c]++:t[c]=1}let r=1;for(const s in t)r<t[s]&&(r=t[s]);const o=[];for(const s in t)r==t[s]&&o.push(s);return n[0]=r,n[1]=o.join(),n},mask(e,n,t){if(!e)throw new Error("字符串为空");if(typeof n!="number"||typeof t!="number")throw new Error("开始位置或结束位置为空");if(n<0||t>e.length||n>t)throw new Error("开始位置小于0或结束位置超出字符串长度或开始位置大于结束位置");return e.slice(0,n)+"*".repeat(t-n+1)+e.slice(t)}},N=e=>{const t=new RegExp("[?&]"+e+"=([^&#]*)","gi").exec(window.location.href);return t?decodeURIComponent(t[1]):null};function F(e){return new URLSearchParams(window.location.search).get(e)}const q={...Object.freeze(Object.defineProperty({__proto__:null,getQueryInfoByName:N,getQueryParam:F},Symbol.toStringTag,{value:"Module"})),getHost(){return window.location.host},getPath(){return window.location.pathname}},P={toList(e,n=2){console.log(e,n);const t={};for(let o=0;o<n;o++)t[o]=[];e.forEach((o,s)=>t[s%n].push(o));const r=[];for(const o in t)r.push(...t[o]);return r},jsLayout(e,n,t){const r=e.offsetWidth,o=n[0].offsetWidth,s=parseInt((r/o).toString()),c=(r-o*s)/(s-1),l=[];for(let i=0,h=n.length;i<h;i++){const a=n[i];if(i<s)a.style.left=(o+c)*i+"px",l[i]=a.offsetHeight;else{const{index:u,value:d}=M.getMinValueAndIndex(l);a.style.left=(o+c)*u+"px",a.style.top=d+t+"px",l[u]=a.offsetHeight+t+d}}}};f.Base64Utils=U,f.MoneyFormatter=j,f.arrayUtils=M,f.booleanUtils=S,f.commonUtils=E,f.cookieUtils=B,f.dateUtils=C,f.documentUtils=x,f.downloadUtils=R,f.echartsUtils=D,f.letterUtils=O,f.mapUtils=T,f.nameUtils=v,f.numberUtils=L,f.objectUtils=b,f.phoneUtils=I,f.randomUtils=_,f.regexpUtils=k,f.storageUtils=H,f.stringUtils=$,f.urlUtils=q,f.waterfallUtils=P,Object.defineProperty(f,Symbol.toStringTag,{value:"Module"})});
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@yh-kit/utils",
3
3
  "private": false,
4
- "version": "1.17.0",
4
+ "version": "1.18.0",
5
5
  "type": "module",
6
6
  "files": [
7
7
  "dist",
@@ -0,0 +1,38 @@
1
+ declare const _default: {
2
+ /**
3
+ * 函数柯里化
4
+ * 定义:把一个多参数的函数,转换为一系列的单参数函数,每个函数只处理一个参数。
5
+ * 方向:多参数函数 -> 单参数函数链
6
+ * 核心:参数复用、延迟执行。
7
+ * 实现思路:参数收集、直到参数够了,再执行函数。
8
+ * 例如:
9
+ * ```ts
10
+ * const add = (a: number, b: number) => a + b;
11
+ * const add1 = curry(add)(1);
12
+ * const result = add1(2); // 3
13
+ * console.log(result); // 正确答案 3
14
+ * ```
15
+ * @param fn 要柯里化的函数
16
+ * @returns 柯里化后的函数
17
+ */
18
+ curry(fn: Function): (this: unknown, ...args: unknown[]) => any;
19
+ /**
20
+ * 反柯里化
21
+ * 定义:让一个“只能被特定对象调用”的方法,变成一个“可以接受任何对象作为第一个参数”的通用函数。
22
+ * 方向:对象方法 -> 通用函数
23
+ * 核心:将对象方法转换为通用函数,允许在不同对象上调用。
24
+ * 实现思路:将对象方法绑定到通用函数上,返回通用函数。
25
+ * 例如:
26
+ * ```ts
27
+ * const push = uncurry(Array.prototype.push);
28
+ * const obj = {};
29
+ * const result = push(obj, 1, 2);
30
+ * console.log(result); // 正确答案 返回长度为 2
31
+ * console.log(obj); // 正确答案 {0: 1, 1: 2, length: 2}
32
+ * ```
33
+ * @param fn 要反柯里化的函数
34
+ * @returns 反柯里化后的函数
35
+ */
36
+ uncurry(fn: Function): (context: unknown, ...args: unknown[]) => any;
37
+ };
38
+ export default _default;
@@ -2,6 +2,8 @@
2
2
  * 通用工具函数
3
3
  */
4
4
  export declare const commonUtils: {
5
+ readonly curry: (fn: Function) => (this: unknown, ...args: unknown[]) => any;
6
+ readonly uncurry: (fn: Function) => (context: unknown, ...args: unknown[]) => any;
5
7
  readonly shallowClone: (source: object) => object;
6
8
  readonly deepCloneByJSON: (source: unknown) => any;
7
9
  readonly deepCloneByMap: <T>(source: T, map?: WeakMap<object, unknown>) => unknown;