Skip to content

deepConvert

deepConvert方法可以深度遍历一个对象,根据你设计的规则进行一些数据处理。 与独立的递归处理 treeForEach 或者 treeMap 不同的是,这个方法通常用于一个规模更大,且更复杂,更频繁的处理策略。 比如我曾将它用于构造一个超json翻译器,用于存储低代码配置。

语法

javascript
deepConvert(data, scope, convertFunc, isTerminator)

参数

data any

  需要深度遍历处理的数据,通常是大型对象或数组,也可以是任意类型的值。

scope object

  一个数据暂存区域,用于在递归过程中保存数据。 我一般把这里的数据分为两种,一种类似 keyparent,每次递归都会变化。 另一种则只会增加,可以保留整个对象的特征。

  deepConvert 在遍历时会自动向 scope 注入以下属性:

  • scope.key — 当前正在处理的键名
  • scope.parent — 当前层级的容器对象(对象或数组)

convertFunc function

  转换函数,当终止条件满足时被调用,接收当前值和 scope 作为参数,返回转换后的结果。

  参数

  • data — 当前正在处理的值
  • scope — 当前作用域对象

  返回值:转换后的值,将作为该位置的新值。

isTerminator function

  终止符判断函数,用于决定是否停止对当前分支的深度遍历。接收当前值和 scope 作为参数。

  参数

  • data — 当前正在处理的值
  • scope — 当前作用域对象

  返回值

  • 返回 true:终止当前分支遍历,调用 convertFunc 转换后返回
  • 返回 'deep':调用 convertFunc 转换后,对转换结果继续深度遍历(支持链式转换)
  • 返回其他假值:继续深度遍历当前值

返回值

any

  返回处理后的数据,结构与输入数据对应。如果是对象/数组则返回新的容器,基本类型值直接返回。

描述

deepConvert 是一个通用的深度遍历转换函数,它的工作流程如下:

  1. 终止符检查:首先调用 isTerminator(data, scope),如果返回 'deep',则先调用 convertFunc 转换数据,再对转换结果继续递归处理;如果返回 true,则调用 convertFunc 转换数据并直接返回结果。
  2. 容器遍历:如果数据是对象或数组,创建对应类型的新容器,然后遍历每个属性。遍历时自动更新 scope.keyscope.parent
  3. 数组处理:对于数组容器,convertFunc 返回 undefined 的项会被跳过(不加入新数组)。
  4. 基本类型:如果数据不是对象或数组,且未触发终止条件,直接返回原值。

重要特性

  • 支持链式转换:当 isTerminator 返回 'deep' 时,转换后的结果会继续被深度遍历
  • 数组中返回 undefined 的项会被自动过滤
  • scope 对象在遍历过程中会被复用和修改,实现数据在递归层级间的传递

注意事项

  • scope 对象在递归过程中会被修改(scope.keyscope.parent),不要在 convertFuncisTerminator 中依赖 scope 的快照
  • isTerminator 必须正确设置终止条件,否则可能导致无限递归
  • 该函数不使用 treeSafe,传入的 data 如果是单个对象会正常处理(作为对象容器遍历)
  • convertFunc 对于数组项返回 undefined 时,该项会被跳过

示例

基础用法 — 字符串值转换

使用 'deep' 实现链式转换

过滤数组项

浏览器兼容

此功能在所有现代浏览器和 Node.js 环境中均受支持,不依赖任何浏览器特定 API。

性能考虑

  • 时间复杂度:O(n) — 其中 n 是数据中所有节点(包括嵌套节点)的总数,每个节点访问一次
  • 空间复杂度:O(d) — 其中 d 是数据的最大嵌套深度,用于递归调用栈
  • 对于超大型对象,注意递归深度可能导致的栈溢出问题
  • scope 对象在递归中复用,不会产生额外的内存开销

相关函数

  • createMyTrans — 基于 deepConvert 构建的翻译器,预设了丰富的转换规则
  • dlsjsTrans — dlsjs 预设翻译器实例
  • treeForEach — 简单的树形遍历,不涉及转换
  • treeMap — 树形映射,返回新树
  • RW — 高级读写代理,与 deepConvert 配合可实现复杂的数据访问