我想将类型any
的元素添加到数组中,然后从此数组中获取数字中的元素:
function OfType<T, U>(list: T[]) : U[]
{
var result: U[] = [];
list.forEach(e => {
// I want to check if e is of type U
//if (typeof(e) === typeof(U)) // ERROR: doesn't work
result.push(<U><any>e);
});
return <any[]>result;
}
var list: any[] = [];
list.push("A");
list.push(2);
var result = OfType<any, number>(list);
alert(result.toString());
但它不允许我根据泛型类型检查元素的类型。
有没有办法实现这个目标?
答案 0 :(得分:1)
Javascript typeof适用于对象的实例,而不适用于类型本身。 (毕竟,TypeScript泛型在编译的JavaScript中消失了。)
您需要获取U的实例,在其上调用typeof,并将其与typeof(e)进行比较。
请记住,JavaScript中的类型信息并不像.NET框架那样丰富。 typeof(myCustomObject)将返回'object',即使该对象是类Foo的实例。
在您的情况下,您正在尝试构建一个.OfType方法,该方法将数组过滤为仅数字。你可以这样写:
var list: any[] = [];
list.push("A");
list.push(2);
var numbers = list.filter(e => typeof(e) === "number");
答案 1 :(得分:1)
正如Judah指出的那样,单独使用泛型类型是不可能的。我找到了一个解决方法,我发送了一个类型为...的参数
function OfType<T, U>(list: T[], arg: Function) : U[]
{
var result: U[] = [];
list.forEach(e => {
// extract the name of the class
// used to match primitive types
var typeName = /function\s*([^(]*)/i.exec(arg+"")[1].toLocaleLowerCase();
var isOfType = typeof(e) === typeName;
// if it is not primitive or didn't match the type
// try to check if it is an instanceof
if (!isOfType)
{
try {
isOfType = (e instanceof arg)
}
catch (ex) { }
}
if (isOfType)
result.push(<U><any>e);
});
return <any[]>result;
}
用法:
var numbers = OfType<any, number>(list, Number);
var foos = OfType<any, Foo>(list, Foo);
alert("Numbers: " + numbers);
alert("Foos: " + foos);
很少冗余,如果有人知道删除此冗余的方法,请发表评论或编辑此代码。
或者,对于原始类型,我只能使用filter
作为犹大提到的。
答案 2 :(得分:1)
您目前可以通过这种方式(TypeScript 3.9)做得更好:
=INDEX(INFO!$A$1:$C$6;MATCH(B2;INFO!$A$1:$A$6;0);MATCH(F1;INFO!$A$1:$C$1;0))
用法示例:
// tslint:disable-next-line: no-any
type Constructor<T> = new (...args: any[]) => T;
export function ofType<TElements, TFilter extends TElements>(array: TElements[], filterType: Constructor<TFilter>): TFilter[] {
return <TFilter[]>array.filter(e => e instanceof filterType);
}