如果声明参数类型

时间:2016-10-31 21:09:31

标签: typescript

我有一个这样的功能界面:

interface Callback {
  (a: string, b: number): void;
}

我可以在不声明参数类型的情况下实现它:

const callback: Callback = (a, b) => { }

在这种情况下,TypeScript了解callback的参数类型实际上是(a: string, b: number)

但是,如果我使用一个参数声明它,例如b: number

const callback: Callback = (a, b: number) => { }

其他参数a的类型变为anyExample in the Playground。奇怪的是,编译器确实知道a应该是什么类型,因为它不会让你错误地定义它,例如(a: boolean, b: number)会说参数不兼容。为什么它不会推断出a的参数类型?

以上是一个微不足道的例子,但在尝试生成类型安全Redux reducer map时,它给了我一些头痛:

interface IReducer<TState> {
  (state: TState, action: IAction): TState;
}

interface IReducerMap<TState> {
  [actionType: string]: IReducer<TState>;
}

interface MyState { hello: string; }

interface MyAction extends IAction { say: string; }

const myReducerMap: IReducerMap<MyState> = {
  // Result: `(state: MyState, action: IAction) => MyState`
  // But I get an error on `action.say` not defined in `IAction`
  reducer1: (state, action) => {
    return { hello: action.say };
  },

  // Result: `(state: any, action: MyAction) => computed`
  reducer2: (state, action: MyAction) => {
    return { hello: action.say + state.this_should_be_an_error };
  },

  // Works but relies on you to correctly defining state
  reducer3: (state: MyState, action: MyAction) => {
    return { hello: action.say };
  }
}

由于每个函数都将IAction的子类型作为其action参数(在本例中为MyAction),因此我必须在callback参数中声明其类型。但是一旦我声明它的类型,我就失去了state的类型,我必须声明它。当我每次回调都有几十个回调和一个真实的州名如DataImportMappingState时,这非常烦人。

1 个答案:

答案 0 :(得分:4)

ab的推断来自上下文输入。以前,如果所有参数未注释,参数仅在上下文中键入。

This behavior has changed in the latest build of the TypeScript compiler因为它似乎不直观。现在,上下文输入将应用于所有不具有显式类型注释的参数。