2017-06-22 51 views
0

我有一个更高级的函数,用一个在线检查来封装一个函数,我正在尝试写一个类型签名,但我无法弄清楚。这是我到目前为止有:如何键入一个函数将任何函数作为参数?

const preventOffline = <T extends Function>(fn: T): T => 
    function() { // Error: Type '() => any' is not assignable to type 'T'. 
    if (!window.navigator.onLine) { 
     alert("Sorry, please retry when you're online."); 
     return undefined; 
    } 
    return fn.apply(this, arguments); 
    }; 

我也试过这样,由于某种原因给了我一个错误说T声明,但从未使用过。

export const preventOfflineHOF = <T, U>(fn: (T) => U): ((T) => U | undefined) => 

我该如何对此进行正确的注释?

回答

1

签名表示应该返回传入的相同类型的函数,但编译器无法断言情况如此。

如果你有一个特定的函数签名,你是期待,那么你可以这样做,例如:

const preventOffline = (fn: (p1: string, p2: number) => boolean): (p1: string, p2: number) => boolean => 
    function (p1: string, p2: number) { 
     return false; 
} 

,编译器不会抱怨。
但是,因为你要允许所有的功能,你只需要告诉你知道你通过铸造在做什么any编译:

const preventOffline = <T extends Function>(fn: T): T => 
    function() { 
     if (!window.navigator.onLine) { 
      alert("Sorry, please retry when you're online."); 
      return undefined; 
     } 
     return fn.apply(this, arguments); 
} as any; 

另一种选择是,除去仿制药和接受只是一个Function

const preventOffline = (fn: Function): Function => 
    ... 
}; 

但随后就失去了传递的类型,功能和preventOffline将只是一个Function

-2
const preventOffline = <T extends Function>(fn:() => T): T => 
    function() { 
    if (!window.navigator.onLine) { 
     alert("Sorry, please retry when you're online."); 
     return undefined; 
    } 
    return fn.apply(this, arguments); 
}; 
+0

我可能知道为什么我的答案被降低了吗? – rainerhahnekamp

+1

可能是因为类型签名与功能不匹配。 'T'不是传入的函数的返回值,而是传入的函数的类型。 – ahstro

+0

另外,好像你的代码产生了相同的确切错误:“Type'()=> any'不能分配给类型'T'”。你在发布它作为答案之前是否还检查过你的代码? –

相关问题