不必在其他文件中重复委托的形状,如何声明对具有给定的已知类型形状的函数的引用?
功能:
/**
* @param {object} prev
* @param {object} next
* @param {string} name - the name of the child param of both objects to compare
*/
exports.getModification = <T> (prev:T,next:T, name:string):Modification<T> =>
{
const getIsChanging = p => prev[p] != null && p in next && next[p];
const getIsAdding = p => !prev[p] && p in next && next[p];
const getIsDeleting = p => prev[p] != null && p in next && !next[p];
const result:Modification<T> = (
getIsChanging(name) ? {changeType:'changing',next: next[name]}
: getIsAdding(name)? {changeType:'adding', next: next[name]}
: getIsDeleting(name) ? {changeType:'deleting',next:undefined}
: {changeType:undefined,next:undefined});
return result;
};
我试图通过
编写方法/委托的定义interface Modification<T>{
changeType: string | undefined;
next: T | undefined;
}
interface GetModificationDelegate<T>{
(prev:T,next:T, name:string) : Modification<T>;
}
// try a type alias
type GetModificationFunction<T> = (prev:T,next:T, name:string) => Modification<T>;
这两个编译都很好。但是,告诉typescript一个符号是对此的引用失败。
var getModification = (app.getModification as GetModificationFunction<T>);
var getModification: <T>GetModificationFunction<T> = app.getModification;
var getModification: <T extends{}>GetModificationFunction<T> = app.getModification;
没有编译。没有求助于类(我假设这很简单)我怎么能简单地告诉typescript什么是它已经知道的形状的泛型委托?
答案 0 :(得分:1)
没有使用参数化类型声明值的语法,只有泛型函数有一个例外。
但如果你绝对需要,还有办法绕过这个限制。如果您对export
使用es6 getModification
语句而不是分配给exports
,则可以沿着
export type GetModificationFunctionType = typeof getModification;
例如,&#34; m.ts&#34;的完整来源。模块是
export interface Modification<T>{
changeType: string | undefined;
next: T | undefined;
}
export const getModification = <T> (prev:T,next:T, name:string):Modification<T> =>
{
const getIsChanging = p => prev[p] != null && p in next && next[p];
const getIsAdding = p => !prev[p] && p in next && next[p];
const getIsDeleting = p => prev[p] != null && p in next && !next[p];
const result:Modification<T> = (
getIsChanging(name) ? {changeType:'changing',next: next[name]}
: getIsAdding(name)? {changeType:'adding', next: next[name]}
: getIsDeleting(name) ? {changeType:'deleting',next:undefined}
: {changeType:undefined,next:undefined});
return result;
};
export type GetModificationFunctionType = typeof getModification;
你可以在另一个模块中使用它,例如&#34; d.ts&#34;:
import {Modification, GetModificationFunctionType} from './m';
var g: GetModificationFunctionType;
g = <T> (prev:T,next:T, name:string):Modification<T> =>
({changeType:undefined,next:undefined});
更新:如果只在某个类的上下文中需要该委托,则可以将其声明为类属性并具有该类的通用参数。但该属性不能是静态的:
class someClass<T> {
delegate1: GetModificationDelegate<T>; // ok
static delegate2: GetModificationDelegate<T>; //error: Static members
// cannot reference class type parameters
}
泛型完全从生成的javascript代码中删除,而documentation states clearly静态成员声明无法引用泛型参数:
正如我们在关于课程的部分中所述,课程有两个方面 type:静态端和实例端。通用类只是 在他们的实例方面而不是他们的静态方面是通用的,所以 使用类时,静态成员不能使用类的类型 参数。