打字稿中函数的操作

时间:2019-04-15 02:45:50

标签: typescript functional-programming

export const wrapCountable = (func: Function): Function => {
    let result: Function & { __times?: number } = () => {
        //result.__times = result.__times || 0
        result.__times++
        let value = null
        try {
            value = func()
        } catch (e) {
            throw e
        }
        return value
    }
    result.__times = 0
    return result
}

此函数将包装另一个作为参数传入的函数。

问题在于,当strictNullChecks模式设置为true时,IDE中将出现错误。

enter image description here

我可以提出的唯一解决此错误的方法是添加以下行:

result.__times = result.__times || 0

但是,我认为这不是一个完美的解决方案。那么正确的方法是什么?

1 个答案:

答案 0 :(得分:2)

编译器没有意识到result.__times肯定会在调用result中的箭头函数时定义。如果您不想更改发出的JavaScript,则可以使用non-null assertion operator !告诉编译器您比它聪明,并且将定义result.__times

export const wrapCountable = (func: Function): Function => {
    let result: Function & { __times?: number } = () => {
        result.__times!++ // notice the ! here
        let value = null
        try {
            value = func()
        } catch (e) {
            throw e
        }
        return value
    }
    result.__times = 0
    return result
}

这将消除错误。但是,它不是类型安全的...您可以注释掉result.__times = 0行,并且该错误仍将得到抑制。包括!在内的类型断言可以使编译器说谎。不过,我希望在这种情况下,您可以做出明智的决定来使用断言。

话虽这么说,我可能会将您的函数折叠成类似的内容

const wrapCountable = <T>(func: () => T) => {
    const result = Object.assign(() => {
        result.__times++;
        return func();
    }, { __times: 0 });
    return result;
}

const eighteen = wrapCountable(() => 18);
// const eighteen: (() => number) & {__times: number}
console.log(eighteen()); // 18
console.log(eighteen()); // 18
console.log(eighteen.__times); // 2

使用通用T,因此您不会丢失返回值的类型,而使用Object.assign()则不必使__times成为{{1} },并且没有该undefined / try块,它似乎什么也没做(重新{catch-同样的例外是无操作,对吗?)。

无论如何,希望能有所帮助。祝你好运!