安全的读写深层对象

安全的读写深层对象

JavaScript中越界访问会出错:

> const a = {};
> console.log(a);
{}
> console.log(a.b.c);
Thrown:
TypeError: Cannot read property 'c' of undefined

所以一般情况下,访问深层对象时,需要这样操作:

console.log(a && a.b && a.b.c);

当深层变量名比较长时,这样访问就显得很累了。使用Ramda的Path函数可以解决这个问题:

R.path(['a', 'b'], {a: {b: 2}}) // 2

这个方法的实现思路也很简单

const get = (p, o) =>  p.reduce((xs, x)  => (xs && xs[x]) ? xs[x] : null, o);

通过递归不断使用reduce访问深层对象,如果没有找到,则返回null。

但是Ramda并没有提供一个写入深层对象的方法,原因可能是深层对象可能不仅仅是Object,也有可能是Array。

在某些特殊场景下,可能需要深层写入对象,这里提供自己写的一种方法(TypeScript):

const deepCreate = (obj:object) => function (...args:string[]) {
    return (key: string, value:number) => {
        let current = obj;
        args.forEach(path => {
            if (!current[path]) {
                current[path] = {};
            }
            current = current[path];
        })
        current[key] = value;
    }
}

调用方式deepCreate(obj1)('path1','path2')('key1', 1);

> const a = {};
> deepCreate(a)('x', 'y', 'z')('num', 2);
> console.log(a)
{
    x: {
        y: {
            z: {
                num: 2
            }
        }
    }
}