有无办法将【泛型局部函数】完美转换为变量?

phommy 2019-04-03 08:31:14
 static void Main(string[] args)
{
var lst = new[] {1, 2, 3};

T AsIs<T>(T input)
{
return input;
}

//能否定义出【一个】变量asIs使其能在以下三句话中代替泛型局部函数AsIs?
//Func<?, ?> asIs = i => i;

var lst2 = lst.Select(AsIs);
var lst3 = lst.Cast<string>().Select(AsIs);
var lst4 = lst.Cast<object>().Select(AsIs);
}


反编译了以上代码的生成结果,发现编译器是将AsIf变成了3个不同的局部变量避开了这个问题

private static void Main(string[] args)
{
int[] numArray = new int[] { 1, 2, 3 };
IEnumerable<int> enumerable = Enumerable.Select<int, int>(numArray, new Func<int, int>(<>c.<>9.<Main>g__AsIs|0_0<int>));
IEnumerable<string> enumerable2 = Enumerable.Select<string, string>(Enumerable.Cast<string>(numArray), new Func<string, string>(<>c.<>9.<Main>g__AsIs|0_0<string>));
IEnumerable<object> enumerable3 = Enumerable.Select<object, object>(Enumerable.Cast<object>(numArray), new Func<object, object>(<>c.<>9.<Main>g__AsIs|0_0<object>));
}
...全文
223 5 打赏 收藏 转发到动态 举报
写回复
用AI写文章
5 条回复
切换为时间正序
请发表友善的回复…
发表回复
秋的红果实 2019-04-03
  • 打赏
  • 举报
回复
写成

var lst2 = lst.Select(x=>x);

你会认为select的参数是一个方法, 那么写成

var lst2 = lst.Select(new Func<int, int>(x=>x));

new Func<int, int>(x=>x)也是一个对象啊,一个变量
秋的红果实 2019-04-03
  • 打赏
  • 举报
回复
明白你的意思,想实现

Func<T, T> AsIs = x => x;

Func已经是泛型了,就是说用泛型再定义一个泛型方法 用“变量”代替“方法”,变量其实就是委托对象了,如下样子

public delegate Func<T,T> genericDel<T>(T input);

因为selector需要Func函数,于是这个委托返回Func类型。但接下来,我是不会弄了 其实可以这样

Func<int,int> AsIs1 = x => x;
Func<string, string> AsIs2 = x => x;
Func<object, object> AsIs3 = x => x;

var lst = new int[] { 1, 2, 3 };
var lst2 = lst.Select(AsIs1);
//..........

不就是变量了吗
exception92 2019-04-03
  • 打赏
  • 举报
回复
select函数本身就支持 Func<TSource, TResult>,自定义一个selector委托,只要签名与Func一致即可。
stherix 2019-04-03
  • 打赏
  • 举报
回复
编译器不是把AsIf变成了3个不同的局部变量 而是生成了一个新类的单例,里面就包含这个内联方法 你这3次调用实际是调用了3次那个新类实例的3次泛型方法 不过你的想法应该是没法实现 .net的变量不可能被赋值成一个泛型函数(方法组),而必须要有明确的参数类型
  • 打赏
  • 举报
回复
什么叫做“完美转换为变量”?泛型是强类型编程,不是什么“变量”。说变量是完全没理解泛型。 有的人更不靠谱,说什么“输入一个字符串,然后就按照字符串代表的自己的意思执行”。这些都不是强类型的编译期进行程序检验的、靠谱的概念,而是在运行时随时随便在用户面前才丢人现眼崩溃的“思路”,但是有的人觉得这种不靠谱的代码才高大上。 泛型是编程模板,你在实际使用(而不是定义)泛型方法时必须用明确的——预先知道的——强类型声明来编程,就上面的 int、string、object 一样必须声明类型,而不是用什么“T" 来声明。编译器根据 T 的不同对应类型而产生明确的强类型的代码(实际上更多是 JIT 编译器来做的,而非 c# 编译器做的)。这才是泛型。 把泛型参数 T 说成是“变量”那就一点都没懂泛型。

110,538

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧