C#中是否有通用数字类型?

Wat*_* v2 10 .net c#

我真的很喜欢一个通用的数字类型作为Func<TInput, THere, TResult>下面给定的第二个泛型类型参数,所以我可以提供一个整数或一个双精度或一个小数,当我喜欢.

var _resultSelectors = new Dictionary<string, Func<DateTime, /*here*/ double, DateTime>>();

// so I can do
_resultSelector.Add("foo", (DateTime dt, int x) => ...);
_resultSelector.Add("bar", (DateTime dt, double d) => ...);
_resultSelector.Add("gar", (DateTime dt, float f) => ...);
_resultSelector.Add("har", (DateTime dt, decimal d) => ...);
Run Code Online (Sandbox Code Playgroud)

缺乏:

  1. 做我自己的类型; 要么
  2. 使用对象和装箱值类型并将其拆箱; 要么
  3. 使用dynamic关键字,

在C#中有没有正确的方法呢?

我猜Java有一个Number类可能符合我的要求,但我想知道C#是否有类似的东西.

我想在C#中没有任何这样的东西,但我想我会要求确定.

InB*_*een 11

不,那里没有.泛型和算术运算(+,-,*,/,等)根本不一起工作.这是一个多次出现的问题,C#设计委员会从未解决过(公平地说,这个功能也需要在CLR上工作,正如Eric Lippert在答案中进一步指出的那样).

好奇的是,如果你检查.NET Framework的源代码,你会发现在某个开发阶段有一个IArithmetic<T>接口,但它被废弃了; 看到这里.

在这个SO答案中,您可以阅读更多相关信息.


D S*_*ley 5

即使有涵盖数字类型,因为你裹了约束在一个基本类型或接口Func它不会对你有任何好.Func的输入类型是逆变的,因此它的参数不能比声明的更多.

换句话说,你不能代替Func<DateTime, ValueType, DateTime>Func<DateTime, int, DateTime>像您可以用IEnumerable<T>(您可以替换IEnumerable<ValueType>IEnumerable<int>)

我认为你最好的赌注是dynamic(仍然是类型安全,但在运行时与编译时)或者double或者decimal如果你想做数学并且不必保持相同的类型.


Som*_*ing 5

C# 10 和 .NET 6:2021 年 11 月起的解决方案

好消息:现在 .NET 6 和 C# 10 中有一个解决方案,参见。https://devblogs.microsoft.com/dotnet/preview-features-in-net-6-generic-math/#generic-math

当你想要任何数字时,你可以使用INumber<T>. 如果您需要任何特定的运算符,请使用相应的接口,例如IAdditionOperatorsfora + bIIncrementOperatorsfora++等。

注意:在我回答时,此功能还只是预览版。微软将在 .NET 6 最终版本中保留这一点,因为他们仍然希望允许突破机会。要使用该功能,必须在项目配置中启用预览功能:

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <EnablePreviewFeatures>true</EnablePreviewFeatures>
    <LangVersion>preview</LangVersion>
    <OutputType>Exe</OutputType>
    <TargetFramework>net6.0</TargetFramework>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="System.Runtime.Experimental" Version="6.0.0-preview.7.21377.19" />
  </ItemGroup>

</Project>
Run Code Online (Sandbox Code Playgroud)