打字稿中的Scala下划线-已实现但无法打字

时间:2018-12-20 22:14:35

标签: typescript typescript-typings

可以肯定的是,这是我的一个宠物项目,已经有2年的时间了,它无法在Typescript中实现Scalas下划线,但不能完全实现,这就是实现和效果。

我唯一关心的类型是“下划线”,其他所有内容都将忽略。

const buildUnderscore = (f: any) => (path: any[]): any => new Proxy(f, handler(path));
const handler = (path: any[]) => ({
    get: function(obj: any, prop: any, value: any) {
        return buildUnderscore((a: any) => getAtPath(a, path.concat(prop)))(path.concat(prop));
    }
})
/* takes object A and key path ["a", "b", "c"] -> returns A["a"]["b"]["c"] */
const getAtPath = (obj: any, [head, ...tail]: string[]): any => {
    if(head === undefined) return obj;
    return getAtPath(obj[head], tail);
}


/* Ignore all implementation above i don't care if its typed this is the only thing i care that's typed */
const _: Underscore = buildUnderscore((a: any) => a)([]);


// ConvertKeysToFunctions<GetArgs<Array<T>["map"]>[0]> is what i need
// but there's no way to infer T
// where GetArgs gets the first argument of Array["map"]
// and ConvertKeysToFunctions converts that types keys to function types
type Underscore = <T>(a: T) => T

const data =  [
        {
            child: {
                name: "bob",
                children: ["sue", "john"]
            }
        },
        {
            child: {
                name: "catness",
                children: ["rue", "hew"]
            }
        },
    ]
console.log(data.map(_))  // converts to data.map((a) => a)
console.log(data.map(_.child.children[0]))// converts to: data.map((a) => a["child"]["children"][0])
console.log(data.map(_.child))  // converts to data.map((a) => a["child"])

1 个答案:

答案 0 :(得分:0)

不幸的是,TypeScript当前缺少引用对象属性动态名称的功能,这使得代理无法使用TypeScript进行输入/键入。

您可能拥有的最接近的功能就是使用lambda:

_ => _.foo.bar

如果路径上的任何属性都是可选的,则您必须像在my library for similar purpose中那样使用深色魔法。请注意,尽管使用类似方法可能会大大减慢编译过程。