打字稿:返回与参数相同类型的通用函数
考虑一下(不编译):
function roundTo<T = number | null | undefined>(
num: T,
decimals: number,
): T {
if (num === null || num === undefined) return num;
const factor = Math.pow(10, decimals);
return (Math.round(num * factor) / factor);
}
我想将传递给roundto()
函数的相同类型返回。
例如:
const num1: number | null = 1.123456;
roundTo(num1, 1) // return type number | null
const num2: number = 1.123456;
roundTo(num2, 1) // return type number
const num3 = null;
roundTo(num3, 1) // return type null
roughto
的返回类型是在编译时已知的,因此希望能够根据第一个参数中传递的类型从那里转移类型。
我可以通过将返回类型施放为任何来进行编译,但这会破坏类型的安全性。我还可以通过使用扩展
而不是=
并将返回类型作为t 进行编译,但是它具有返回<< 代码>任何当null
或未定义
被传递时。
如何获得打字稿以展示所需的行为?
有关的: https://stackoverflow.com/a/a/51195834/188740 https://stackoverflow.com/a/a/57529925/188740
Consider this (which doesn't compile):
function roundTo<T = number | null | undefined>(
num: T,
decimals: number,
): T {
if (num === null || num === undefined) return num;
const factor = Math.pow(10, decimals);
return (Math.round(num * factor) / factor);
}
I would like to return the same type that's passed in to the roundTo()
function.
For example:
const num1: number | null = 1.123456;
roundTo(num1, 1) // return type number | null
const num2: number = 1.123456;
roundTo(num2, 1) // return type number
const num3 = null;
roundTo(num3, 1) // return type null
The return type of roundTo
is known at compile time, so the desire is to be able to carry the type forward from there based on the type passed in the first parameter.
I can make this compile by casting the return type as any
, but that would break type safety. I can also make this compile by using extends
instead of =
and casing the return type as T
, but it has the undesired behavior of returning any
when null
or undefined
is passed in.
How can I get TypeScript to exhibit the desired behavior?
Related:
https://stackoverflow.com/a/51195834/188740
https://stackoverflow.com/a/57529925/188740
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
它应该是
t扩展...
,而不是t = ...
。后一种形式是“ t的默认值”,它不是被推断出来的,而是总是被称为声明的,基本上杀死了整个想法。实际上,您可以摆脱一种类型的coersion
num为号码
,但如果您真正地想强制推断实际类型在功能内部的t,可能是有条件的键入方式,但恕我直言,这是过度的。
@johnny oshika的另一点 - 可以避免使用不必要的数字类型的狭窄,可以使用:
It should be
T extends ...
, notT = ...
. The latter form is "default value for T", and it is not inferred but rather always taken as declared, basically killing entire idea.Actually, you can get rid of one type coersion
num as number
but probably not the other (at least not an easy way)If you really want to force typescript infer actual type of T inside the function, probably conditional typings are the way, but imho it's overkill.
One more point from @Johnny Oshika - to avoid unwanted narrowing of number types overloads can be used:
此答案归功于@jcalz。
使用过载签名设置有条件的返回类型的
t扩展数字?编号:t
。然后,实现可以放松类型推理。示例:
Credit for this answer goes to @jcalz.
Use an overload signature to set a conditional return type of
T extends number ? number : T
. Then the implementation can relax the type inference.Examples: