对象扁平化

其中objectDit表示的是对象的分割符

/**
 * @description: 对象扁平化
 * @param {object} data
 * @Date: 2022-06-01 17:41:13
 * @Author: mulingyuer
 */
export function objectFlat(data: object, options = { objectDit: "." }): object {
  let newObj = {};

  let process = (key: string, value: any) => {
    if (Object(value) !== value) {
      //普通类型、null、undefind
      newObj[key] = value;
    } else {
      //引用类型
      if (Array.isArray(value)) {
        value.forEach((childVal, childIndex) => {
          process(`${key}[${childIndex}]`, childVal);
        });

        //空数组赋值空数组
        if (value.length === 0) newObj[key] = [];
      } else {
        const keyArr = Object.keys(value);
        keyArr.forEach((childKey) => {
          process(`${key}${options.objectDit}${childKey}`, value[childKey]);
        });

        //为空赋值空对象
        if (keyArr.length === 0) newObj[key] = {};
      }
    }
  };

  Object.keys(data).forEach((key) => process(key, data[key]));
  return newObj;
}

对象反扁平化

/**
 * @description: 对象反扁平化
 * @param {array} data
 * @Date: 2022-06-01 19:47:52
 * @Author: mulingyuer
 */
export function objectUnflat(data: object, options = { objectDit: "." }): object {
  const result = {};

  let transformKey = function (key: string, value: any, originData: object) {
    const keyArr = key.split(options.objectDit);
    let cacheData = originData;

    keyArr.forEach((key, index) => {
      const nextKey = keyArr[index + 1];

      if (/\[(.+?)\]/g.test(key)) {
        //是数组
        //多维数组拆分成[[0],[1],[2]]
        const indexArr = key.match(/\[(.+?)\]/g) as RegExpMatchArray;
        const firstKey = (key.match(/^(.+?)\[/) as RegExpMatchArray).pop() as string;
        //如果首次进入没有容器数组时赋值空数组
        if (!cacheData[firstKey]) {
          cacheData[firstKey] = [];
        }
        cacheData = cacheData[firstKey];

        //遍历多维数组
        indexArr.forEach((j, i) => {
          const jndex = j.replace(/\[|\]/g, "");
          const nextJndex = indexArr[i + 1];

          if (nextJndex) {
            cacheData[jndex] = cacheData[jndex] ? cacheData[jndex] : [];
            cacheData = cacheData[jndex];
          } else {
            if (nextKey) {
              cacheData[jndex] = cacheData[jndex] ? cacheData[jndex] : {};
              cacheData = cacheData[jndex];
            } else {
              cacheData[jndex] = numberAsString(value);
            }
          }
        });
      } else {
        //不是数组
        if (nextKey) {
          cacheData[key] = cacheData[key] ? cacheData[key] : {};
          cacheData = cacheData[key];
        } else {
          cacheData[key] = numberAsString(value);
        }
      }
    });
  };

  Object.keys(data).forEach((key) => {
    transformKey(key, data[key], result);
  });

  return result;
}

/**
 * @description: 数字转字符
 * @param {number} val
 * @Date: 2022-06-09 14:11:29
 * @Author: mulingyuer
 */
export function numberAsString(val: number | string): string {
  return "" + val;
}

由于我的这个反扁平化用在了excel与json互转上,并且是给i18n多语言使用的,i18n有个要求,就是所有的value值它必须是string类型,如果你用其他类型,会当做无值处理,所以我在value赋值时调用了numberAsString方法进行转换,如果不需要可以去除。

分类: vue 项目实战 标签: 对象扁平化对象反扁平化

评论

暂无评论数据

暂无评论数据

目录