具有继承的Typescript编译器错误泛型类型

时间:2017-06-19 09:42:09

标签: typescript compiler-errors typescript-typings

由于@RequestMapping(value = "/results-pdf", method = RequestMethod.GET) @ResponseBody public ModelAndView generateResultsPdf(@RequestParam("year") String year) { List<Student> studentList = studentService.getResultsByYear(year); JRDataSource jrDataSource = new JRBeanCollectionDataSource(studentList); Map<String, Object> parameterMap = new HashMap<>(); parameterMap.put("title", "Results table")); parameterMap.put("datasource", jrDataSource); return new ModelAndView("resultsPdf", parameterMap); } 变量中的输入错误:

,以下代码无法编译
  

输入'{item:ModelInterface; }'不能分配给类型   'ResponseInterface'。属性“item”的类型不兼容。       类型'ModelInterface'不能分配给'T'类型。

output

interface ModelInterface { } interface ResponseInterface<T> { item: T; } class Store { get<T extends ModelInterface>(): ResponseInterface<T> { let output: ResponseInterface<T> = { item: this.getModel() }; return output; } getModel(): ModelInterface { return null; } } 方法明确定义get将始终扩展T,为什么我不能在没有错误的情况下将ModelInterface对象设置为ModelInterface

我可以通过以下方式克服此错误:

item

但它看起来像一个bug,我遗漏了一些东西,或者打字稿编译器在这种情况下完全失败了?

我已尝试过typescript playground,但也失败了。

有什么想法吗?

1 个答案:

答案 0 :(得分:0)

TModelInterface延伸的事实确保任何T实例都可以“投射”到ModelInterface。但这并不意味着其他。

例如:

class ModelInterface
{
    public name: string;
}

interface ResponseInterface<T> {
    item: T;
}

class ModelInterfaceExtended
{
    public name: string;
    public age: number;
}

class Store
{
    get<T extends ModelInterface>(): ResponseInterface<T> {
        let output: ResponseInterface<T> = {
            item: this.getModel()
        };
        return output;
    }

    getModel(): ModelInterface {
        return null;
    }
}

const s = new Store();
let result = s.get<ModelInterfaceExtended>();

此处result将包含属性ModelInterfaceExtended的属性项,其属性为nameage。而getModel无法创建此类对象,因为返回类型为ModelInterface - 仅限name

您可以通过执行以下更改来修复它:

class ModelInterface
{
    public name: string;
}

interface ResponseInterface<T> {
    item: T;
}

class ModelInterfaceExtended
{
    public name: string;
    public age: number;
}

class Store<T extends ModelInterface>
{
    get(): ResponseInterface<T>
    {
        return {
            item: this.getModel()
        };
    }

    getModel(): T
    {
        return null;
    }
}

const s = new Store();
let result = s.get();