c# - 为什么编译器不推断泛型类型

标签 c# generics visual-studio-2015 language-lawyer type-inference

我有以下方法:

public static void Foo<T>(Predicate<T> validator) { ... }

我想这样调用它:

Foo(s => string.IsNullOrEmpty(s));

为什么编译器不能找出 sstring,因此 Tstring?规范中的什么规则使推理算法在这里失败?

最佳答案

我承认我没有检查整个 C# 5.0 规范,但是 8.5.1 局部变量声明 部分谈到了 var 关键字,它用于声明一个推断类型。

以下是为 var 声明的变量和所有推断变量的规则:

  • 局部变量声明不能包含多个局部变量声明符。
  • local-variable-declarator 必须包含一个local-variable-initializer。
  • local-variable-initializer 必须是一个表达式。
  • 初始化器表达式 必须具有编译时类型。
  • 初始化器表达式不能引用声明的变量本身

因为这是一个 lambda,所以您推断的初始值设定项是:

string.IsNullOrEmpty(s)

好的,所以...

  • 它没有多个局部变量声明符。通过。
  • 它包含一个 local-variable-intitalizer 因为它是一个 lambda。通过。
  • 这是一个表达式。通过。
  • string.IsNullOrEmpty 返回一个字符串。通过。
  • 它依靠将自身传递给函数来确定类型。失败。

因此,要回答您的问题,您的初始化程序最终会失败,因为在将其传递给方法之前必须知道其类型。

不过,Lambda 可以相对轻松地解决这个问题:

Foo(string s => string.IsNullOrEmpty(s));

关于c# - 为什么编译器不推断泛型类型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39681795/

相关文章:

java - 参数化通用 Java 事件处理程序的正确方法

java - Java中通配符泛型的实际使用

asp.net-mvc - VS2015 无法编辑 cshtml 文件

c# - ASP.NET Core 1.0.0 Nuget 依赖问题

c# - Entity Framework 性能问题

c# - 在 Windows 窗体中放置一个 wpf 按钮

java - 树遍历和一阶函数

c# - Xamarin Forms 中没有 WebClient 类

c# - 如何使用 visual studio 命令提示符从 C# 类文件生成 xsd?

c++ - 在 Visual Studio C++ 中弃用单个构造函数的正确语法是什么?