c# - 在 C# 中结合动态绑定和非托管约束
问题描述
前提:
让我们看下面的代码示例:
using System;
public class Program
{
public static unsafe void f(StringComparison c)
{
// One overload used to pin the handle to the memory on the GC Heap and do unsafe stuff.
// Can be generic as well, but I chose to simplify the example for better clarity.
}
public static void f(string c)
{
// Another overload just to describe the problem.
}
public static void Main()
{
// Returns an instance of StringComparison at runtime with the compile-time type of object.
dynamic c = Activator.CreateInstance(typeof(StringComparison));
// Resolves to f(StringComparison) and everything works as expected.
f(c);
}
}
这里正确的重载是通过绑定f
成功调用的。dynamic
当我将unmanaged
约束添加到与泛型的混合中时,如下所示(MCVE):
using System;
public class Program
{
public static unsafe void f<T>(T v) where T : unmanaged
{
// Unsafe generic method needed to handle primitive types and enums (including user defined ones).
// Unsafe because of the same reason in the first sample.
}
public static void f(string s)
{
// Another overload just to describe the problem.
}
public static void Main()
{
// Returns an instance of StringComparison at runtime with the compile-time type of object.
dynamic c = Activator.CreateInstance(typeof(StringComparison));
// Oops! We have an error!
// error CS8377: The type 'dynamic' must be a non-nullable value type,
// along with all fields at any level of nesting,
// in order to use it as parameter 'T' in the generic type or method 'Program.f<T>(T)'
f(c);
}
}
笔记:
- 过载
f(string)
仅用于说明问题。任何强制f<T>(T)
选择重载的不兼容类型也可以工作。 Activator.CreateInstance
还用于说明在运行时返回正确类型(enum
在本例中为 an)实例的函数。
我不熟悉dynamic
在运行时执行重载解析的机制,但MSDN建议:
dynamic
假定支持任何操作。
由于第一个示例有效(dynamic
能够绑定到一个enum
,满足未明确指定的约束unmanaged
),我希望第二个示例也可以工作。
问题:
- 这种行为是预期的还是错误?如果是预期的,请解释原因。
f<T>(T)
是否有任何解决方法可以在不使用反射的情况下调用泛型重载?
解决方案
推荐阅读
- c# - 如何从我的项目访问我的 MongoDB 实例到我的 xunit 测试项目类?
- android - 我怎样才能将我的图像放在一个圆圈中而不出现在 Android Studio 上?
- python - 创建“压缩”字典
- php - 使用命名空间(PHP)从另一个类调用方法
- java - 在其他语言中状态为 200 时,在 Java 中登录后重定向 302
- php - 可以在类中获取数据但返回时只发送布尔值php PDO?
- c# - HtmlAgilityPack NullReferenceException 错误
- python - PySpark:连接数据类型为“Struc”的两列-> 错误:由于数据类型不匹配而无法解决
- java - 使按钮适应 JavaFX 中的窗口大小调整(重新定位)
- blob - 在复制活动期间或在 blob 数据集中指定名称时将日期时间动态附加到文件名