在肝电商后台管理系统的项目时,希望对提交到表单对象做一个深拷贝从而对新对象中的数据进行后台数据匹配,教程中的方法是安装lodash
依赖,其中提供了深拷贝的方法,一搜发现这个依赖居然有180M!不就是实现一个深拷贝嘛,于是我就想在methods
中自己定义了一个深拷贝函数:
methods: {
//深拷贝
deepClone(obj) {
if (typeof obj !== 'object' || obj == null) {
// obj 是 null ,或者不是对象和数组,直接返回
return obj
}
// 初始化返回结果
let result
if (obj instanceof Array) {
result = []
} else {
result = {}
}
for (let key in obj) {
// 保证 key 不是原型的属性
if (obj.hasOwnProperty(key)) {
// 递归调用!!!
result[key] = deepClone(obj[key])
}
}
// 返回结果
return result
},
// 获取分类列表
//点击添加按钮添加商品到数据库
addGoods(){
this.$refs.addRefs.validate((valid)=>{
console.log(this.deepClone);
if(!valid){
return this.$message.error('请填写必要的表单项')
}
console.log(this.addForm);
// const form = JSON.parse(JSON.stringify(this.addForm))
const form = this.deepClone(this.addForm)
form.goods_cate = form.goods_cate.join(',')
console.log(form);
})
}
},
点击添加按钮后,好家伙报错了:
但是我发现在addGoods
函数中打印this.deepClone
是可以拿到deepClone
这个方法的,仔细回过头去看deepClone
发现使用递归时用的是result[key] = deepClone(obj[key])
! 这就导致了在第二次“递归”时,vue就不认得deepClone
这个东西了,后来我想着将递归项换成result[key] = arguments.callee(obj[key])
,运行代码后又会报错:
这好像是因为caller
callee
arguments
无法在严格模式下使用。当我想用JSON
方法进行深拷贝的时候(const form = JSON.parse(JSON.stringify(this.addForm))
事实证明是有效的~~),我发现好像可以在将递归项的deepClone前加上this
:
for (let key in obj) {
// 保证 key 不是原型的属性
if (obj.hasOwnProperty(key)) {
// 递归调用!!!
result[key] = this.deepClone(obj[key])
}
}
这样每次“递归”,Vue
都拿到这个deepClone,问题圆满解决。
总结来说就是,在vue
中使用递归函数时,一定要注意递归项的写法。但其实在vue中不管是调用methods
中的方法还是data
中的数据,this
是一个经常被忽略的问题,一定要仔细对待,多码多码。
更多推荐
在vue方法中要谨慎定义递归函数
发布评论