带约束的通用类型通用不能分配给通用接口

时间:2017-08-31 10:10:25

标签: typescript generics

我在TypeScript 2.4.2中的泛型类中出现错误,其约束与不太严格的接口不兼容。我收到以下错误:

  

ts / components / Schedule.ts(37,13):错误TS2322:输入' {personWeekView:PlanItemScheduleView; projectWeekView:PlanItemScheduleView; [R ...'不能分配类型' Map'。     物业' personWeekView'与索引签名不兼容。       输入' PlanItemScheduleView'不能分配类型' IPlanItemScheduleView'。         财产类型' onAddedItem'是不相容的。           输入'(item:T,initial:boolean)=>空隙'不能分配类型'(item:T,initial:boolean)=>无效&#39 ;.             参数类型'项目'和'项目'是不相容的。               输入' T'不能分配给' PlanItem'。

     

ts / views / PlanItemScheduleView.ts(2,18):错误TS2420:Class' PlanItemScheduleView'错误地实现了界面' IPlanItemScheduleView'。     财产类型' onAddedItem'是不相容的。       输入'(item:T,initial:boolean)=>空隙'不能分配类型'(item:T,initial:boolean)=>无效&#39 ;.         参数类型'项目'和'项目'是不相容的。           输入' T'不能分配给' PlanItem'。

     

ts / views / PlanItemScheduleView.ts(99,79):错误TS2345:类型的参数' this'不能分配给' IControllerListener'类型的参数。     输入' PlanItemScheduleView'不能分配给类型' IControllerListener'。       财产类型' onAddedItem'是不相容的。         输入'(item:T,initial:boolean)=>空隙'不能分配类型'(item:T,initial:boolean)=>无效&#39 ;.           参数类型'项目'和'项目'是不相容的。             输入' T'不能分配给' PlanItem'。

接口

namespace Planning {
    export interface IPlanItemScheduleView extends IView, IControllerListener<IPlanItem> {
        setTimespan(timespan: Timespan): void;
        getName(): string;
    }
}
namespace Planning {
    export interface IControllerListener<T> {
    /**
     * Notifies the listener that an item is added to the cache so it can add it to its view.
     * 
     * @template T
     * @param {T} item
     * @param {boolean} initial
     * 
     * @memberOf IControllerListener
     */
    onAddedItem<T>(item: T, initial: boolean): void;
    }
}

namespace Planning {
    export class PlanItemScheduleView<T extends PlanItem> implements IPlanItemScheduleView {

        public onAddedItem<T extends PlanItem>(item: T, initial: boolean): void {
            // implementation that needs properties on PlanItem
        }
    }
}

PlanItem是一个抽象的基类,由一些实际的实现继承。我有一些不同类型的viwes,我这样构建:

  // Create the different views
  this._views = {
            personWeekView: new PlanItemScheduleView<Person>(this._options, this._logger, this),
            projectWeekView: new PlanItemScheduleView<Project>(this._options, this._logger, this),
            resourceWeekView: new PlanItemScheduleView<Resource>(this._options, this._logger, this),
        };

我以为我之前在另一个版本的tsc中进行了编译,但我可能会弄错。我该如何解决这个问题?

1 个答案:

答案 0 :(得分:1)

您不需要onAddedItem上的泛型参数,如果希望onAddedItem采用与类相同的参数类型,则可以使用class参数。您可以将IPlanItemScheduleView设为通用,以便将PlanItemScheduleView类型参数传递给IControllerListener

export interface IControllerListener<T> {
  onAddedItem(item: T, initial: boolean): void;
}
export interface IPlanItemScheduleView<T extends IPlanItem>  extends IControllerListener <T> {

}
export class PlanItemScheduleView<T extends PlanItem> implements IPlanItemScheduleView<T> {
  public onAddedItem(item: T, initial: boolean): void {
      // implementation that needs properties on PlanItem
  }
}

注意:已编辑以考虑反馈。