T arg
)
泛型方法:public static IEnumerable <TSource> Where <TSource>(
this IEnumerable <TSource> source,
Func <TSource, bool> predicate
)
----
应用
List <string> fruits = new List <string> { "apple", "passionfruit", "banana", "mango",
"orange", "blueberry", "grape", "strawberry" };
IEnumerable <string> query = fruits.Where(fruit => fruit.Length < 6);
foreach (string fruit in query)
Console.WriteLine(fruit);
首先 lambda表达式如果换成匿名方法 delegate(string fruit){return fruit.Length < 6;}这样对不对?
其次,目前我只能理解到,因为变量fruits,可以由编译器推出类型TSource 为string是吗?所以,委托Func <TSource, bool> predicate自然就推出是
Func <string, bool> predicate。然后就与对应的匿名方法delegate(string fruit){return fruit.Length < 6;}在返回值与参数类型上一致了,是吧?
最后,我感觉,委托总要通过调用才能发挥作用的。
string str="pea";
predicate(string str);//
可是,用了refelctor,没看到有类似的语句。
对于上面的例子,难道是foreach (string fruit in query) 这句才真正通过委托调用的方法吗?
==========================
大侠能不能举个简单的详细的例子来说明这一用法啊,我主要是对于泛型委托作为一个泛型方法的参数这种用法比较糊涂,不是理解不了委托作为参数,是理解不了具体是怎么实现的。
9 个解决方案
#1
#2
没人啊
#3
是的。
delegate声明的是普通的对象,对象可以被存储。方法和保存有方法的声明的对象不要混淆就行了。
#4
delegate声明的是普通的对象 --> delegate声明的是普通的对象类型
#5
现在不理解的就是 匿名方法的参数x 是怎么赋的值并在扩展方法内部被定义好的委托调用的。
举个最简单的,
delegate int addhandler(int a,int b);
addhandler deladd=delegate(int x,int y){return x+y;}
我们在实际应用的时候 不是应该有一句int i=deladd(3,6)// i=9对吧。
但是 在扩展方法里, 也应该是这样的形式。
int c=3;
int d=6;
int i=deladd(c,d);***********
就是说,方法的代码中一定有类似的代码,最关键的就是deladd(c,d)这句,其中,c d 两个参数应该是外部传进去的。
但是,我不明白的是,lambda表达式相当于匿名方法,在我看来,就是直接在参数中定义了委托要调用的方法,但是,参数的值是从那传过去的呢?
举个最简单的,
delegate int addhandler(int a,int b);
addhandler deladd=delegate(int x,int y){return x+y;}
我们在实际应用的时候 不是应该有一句int i=deladd(3,6)// i=9对吧。
但是 在扩展方法里, 也应该是这样的形式。
int c=3;
int d=6;
int i=deladd(c,d);***********
就是说,方法的代码中一定有类似的代码,最关键的就是deladd(c,d)这句,其中,c d 两个参数应该是外部传进去的。
但是,我不明白的是,lambda表达式相当于匿名方法,在我看来,就是直接在参数中定义了委托要调用的方法,但是,参数的值是从那传过去的呢?
#6
当执行“IEnumerable <string> query =....”那条语句的之后,query中保存着的是IQueable<string>类型的对象,其中它内部保存了Expression类型的lamda解析结果以及IQueryProvider类型的用来执行lamda的具体操作对象,但是只有到foreach执行时才会动态地由QueryPovider解释Expression来开始执行(参数此时传递)。为了“动态”,必须抓住Expression和IQueryProvider两条线分别保存对象,并且之后执行查询这个机制。而匿名方法则是相当静态的,是编译器翻译成很简单的匿名delegate对象以及插入执行代码,因此可以说与.net framework无关几乎只是一种“语言特色”,.net framework几乎无需支持。lamda则是很复杂的,必须从.net framework这一层就实现大量的内容(因此我不认为lamda“只不过是一堆语法糖”)。
#7
相似而已,机制完全不同。简单地应用一下匿名方法,只能适合内存中的可枚举对象集合操作而已。因此早已经有些语言实现了动态查询语法,但是未必真的能够实现linq这样的功能,只能算一点雏形,因为它们只能针对已经能够读取到内存中的可枚举对象集合操作。而lamda实际上对查询表达式翻译为一组内部动作,每一个内部动作具体如何执行则是很灵活的,例如Linq to SQL就可以把一个查询重新翻译为一组优化了的SQL,并动态地在运行时管理内部数据和执行这些SQL。
#8
不能转换,规则限制
#9
lambda表达式是匿名方法的一个特例,仅此而已,给分吧
#1
#2
没人啊
#3
是的。
delegate声明的是普通的对象,对象可以被存储。方法和保存有方法的声明的对象不要混淆就行了。
#4
delegate声明的是普通的对象 --> delegate声明的是普通的对象类型
#5
现在不理解的就是 匿名方法的参数x 是怎么赋的值并在扩展方法内部被定义好的委托调用的。
举个最简单的,
delegate int addhandler(int a,int b);
addhandler deladd=delegate(int x,int y){return x+y;}
我们在实际应用的时候 不是应该有一句int i=deladd(3,6)// i=9对吧。
但是 在扩展方法里, 也应该是这样的形式。
int c=3;
int d=6;
int i=deladd(c,d);***********
就是说,方法的代码中一定有类似的代码,最关键的就是deladd(c,d)这句,其中,c d 两个参数应该是外部传进去的。
但是,我不明白的是,lambda表达式相当于匿名方法,在我看来,就是直接在参数中定义了委托要调用的方法,但是,参数的值是从那传过去的呢?
举个最简单的,
delegate int addhandler(int a,int b);
addhandler deladd=delegate(int x,int y){return x+y;}
我们在实际应用的时候 不是应该有一句int i=deladd(3,6)// i=9对吧。
但是 在扩展方法里, 也应该是这样的形式。
int c=3;
int d=6;
int i=deladd(c,d);***********
就是说,方法的代码中一定有类似的代码,最关键的就是deladd(c,d)这句,其中,c d 两个参数应该是外部传进去的。
但是,我不明白的是,lambda表达式相当于匿名方法,在我看来,就是直接在参数中定义了委托要调用的方法,但是,参数的值是从那传过去的呢?
#6
当执行“IEnumerable <string> query =....”那条语句的之后,query中保存着的是IQueable<string>类型的对象,其中它内部保存了Expression类型的lamda解析结果以及IQueryProvider类型的用来执行lamda的具体操作对象,但是只有到foreach执行时才会动态地由QueryPovider解释Expression来开始执行(参数此时传递)。为了“动态”,必须抓住Expression和IQueryProvider两条线分别保存对象,并且之后执行查询这个机制。而匿名方法则是相当静态的,是编译器翻译成很简单的匿名delegate对象以及插入执行代码,因此可以说与.net framework无关几乎只是一种“语言特色”,.net framework几乎无需支持。lamda则是很复杂的,必须从.net framework这一层就实现大量的内容(因此我不认为lamda“只不过是一堆语法糖”)。
#7
相似而已,机制完全不同。简单地应用一下匿名方法,只能适合内存中的可枚举对象集合操作而已。因此早已经有些语言实现了动态查询语法,但是未必真的能够实现linq这样的功能,只能算一点雏形,因为它们只能针对已经能够读取到内存中的可枚举对象集合操作。而lamda实际上对查询表达式翻译为一组内部动作,每一个内部动作具体如何执行则是很灵活的,例如Linq to SQL就可以把一个查询重新翻译为一组优化了的SQL,并动态地在运行时管理内部数据和执行这些SQL。
#8
不能转换,规则限制
#9
lambda表达式是匿名方法的一个特例,仅此而已,给分吧