gpt4 book ai didi

c# - 无法使用动态 C# 转换通用基元

转载 作者:行者123 更新时间:2023-12-03 23:08:26 70 4
gpt4 key购买 nike

我正在尝试检查我在返回类型中向下转换的结果是否可以转换为哪种派生类型。我正在检查的派生类型是带有协变参数的泛型。我正在使用 is 运算符将其转换为动态类型。我相信,由于通用参数是原始类型 bool,因此它不起作用。奇怪的是,在监 window 口中,结果符合预期,但代码执行却并非如此。我不确定是否有我遗漏的东西或者这是一个错误。这是预期的行为吗?

我通过检查结果是否是泛型然后获取类型参数并结合使用 MakeGenericType 和“动态结果 = Convert.ChangeType”来解决此问题。

这是一个用于演示的简单示例应用程序。

var testBool = new List<bool>();     // Primitive
var testString = new List<string>(); // Class

if (testBool is IEnumerable<bool>)
Console.WriteLine("Test Bool");
if (testBool is IEnumerable<dynamic>)
Console.WriteLine("Test Bool - Dynamic");
if (testString is IEnumerable<string>)
Console.WriteLine("Test string");
if (testString is IEnumerable<dynamic>)
Console.WriteLine("Test string - Dynamic");

注释:.NET Core 2.1、Visual Studio 2017、C#

Sample Application

最佳答案

dynamic在执行时不作为不同类型存在。动态类型由 C# 编译器结合一些非常巧妙的框架功能来执行。但运行时根本不知道它。

您实际上是在问 testBool 是否实现IEnumerable<object> - 但事实并非如此。 (这就是相关 IL 正在测试的内容。)

存在错误,但它存在于“监视”窗口处理中 - 而不存在于常规执行中。我见过多种情况,其中“监视”窗口的行为与常规代码不太一样。如果这种情况在 dynamic 周围特别严重,我不会感到惊讶。 .

List<string> 的行为而言:

  • List<string>实现IEnumerable<dynamic>由于 IEnumerable<T> 的协方差(即它实现 IEnumerable<object> )
  • List<string> 没有实现IList<dynamic> ,这只是一个不涉及差异的示例。

如果您认为使用 dynamic因为类型参数将有效地检查“此类型是否为某些将动态确定的类型 IEnumerable<T> 实现 T”,但事实并非如此。您可以使用dynamic执行执行时类型推断:

dynamic d = ...; // Whatever value you're interested in
ShowList(d);

private void ShowList<T>(IEnumerable<T> list)
{
Console.WriteLine($"Implements IEnumerable<{typeof(T)}>");
}

private void ShowList(object backstop)
{
Console.WriteLine("I guess it doesn't implement IEnumerable<T> at all");
}

请注意,如果您正在处理完全未知的值,那么这种事情可能会很危险 - 如果您尝试使用实现(例如)IEnumerable<string> 的值来执行此操作。和IEnumerable<bool> ,将以与尝试调用 ShowList 时出现编译时错误相同的方式抛出异常。使用该值,因为类型推断找不到“最佳”T .

关于c# - 无法使用动态 C# 转换通用基元,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51524941/

70 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com