前言:
此时同学们对“lamda foreach”可能比较看重,我们都想要学习一些“lamda foreach”的相关资讯。那么小编在网络上搜集了一些关于“lamda foreach””的相关资讯,希望各位老铁们能喜欢,朋友们一起来了解一下吧!委托的概念
委托是一种可以指向方法的数据类型(委托类型),可以声明委托类型的变量
数据类型指的是类似类的,前面提到过一切皆对象,委托就是将方法当作对象使用
声明委托
delegate 返回值类型 委托类型名称(参数);
创建委托
委托类型 变量 = new 委托类型(方法);
注:方法的参数必须与委托类型的参数一致,方法后面不需要括号,方法后面加括号是调用
简化创建委托
创建委托可以不使用new关键词
委托类型 变量 = 方法;
注:方法后面不可以加括号
注:委托是引用类型,可以为null,如果调用会抛出 NullReferenceException(空引用异常)
使用无返回值的委托
直接代码展示
class MainClass{ public static void Main(string[] args) { MyDelegate del = new MyDelegate(UseDelegate); // 创建委托 del(); // 使用委托 } public static void UseDelegate() { Console.WriteLine("使用无参委托"); }}delegate void MyDelegate();
下面同上面是一样的效果
class MainClass{ public static void Main(string[] args) { MyDelegate del = UseDelegate; // 简写创建委托 del(); } public static void UseDelegate() { Console.WriteLine("使用无参委托"); }}delegate void MyDelegate();
输出:
使用无参委托委托相互赋值
class MainClass{ public static void Main(string[] args) { // 委托赋值给委托 需要是同一个委托类型 MyDelegate del = UseDelegate; MyDelegate my = null; my = del; my(); } public static void UseDelegate() { Console.WriteLine("使用无参委托"); }}delegate void MyDelegate();
输出:
使用无参委托有参委托
class MainClass{ public static void Main(string[] args) { MyDelegate myDelegate = UseDelegate; // 创建委托,方法的参数必须与委托的参数一致 myDelegate("Tom-Cat"); // 调用委托 } public static void UseDelegate(string name) { // $"" 里面可以直接写参数,但是需要使用 {参数名} Console.WriteLine($"My Name Is {name}"); }}delegate void MyDelegate(string name);使用有返回值的委托
class MainClass{ public static void Main(string[] args) { MyDelegate myDelegate = UseDelegate; int a = myDelegate("Tom-Cat"); Console.WriteLine("返回值: {0}",a); } public static int UseDelegate(string name) { Console.WriteLine($"My Name Is {name}"); return 1; }}delegate int MyDelegate(string name);
输出:
My Name Is Tom-Cat返回值: 1泛型
泛型是用来替代不确定的数据类型,看下面代码
class MainClass { public static void Main(string[] args) { // 声明类的时候定义数据类型 Persion<string, int, double> p = new Persion<string, int, double>(); p.name = "Tom"; p.age = 10; p.height = 170.50; Console.WriteLine("p.name 的数据类型:{0},内容是:{1}",p.name.GetType(),p.name); Console.WriteLine("p.age 的数据类型:{0},内容是:{1}", p.age.GetType(), p.age); Console.WriteLine("p.height 的数据类型:{0},内容是:{1}", p.height.GetType(), p.height); } } class Persion<T,T1,T2> { public T name; public T1 age; public T2 height; }
输出:
p.name 的数据类型:System.String,内容是:Tomp.age 的数据类型:System.Int32,内容是:10p.height 的数据类型:System.Double,内容是:170.5系统内置泛型委托Action 无返回值
class MainClass{ delegate void A(int i); public static void Main(string[] args) { Action<int> action = Print; // 等价于 下面这一条语句,相比之下不需要自己写 delegate void A(int) A a = Print; a(1); action(1); } public static void Print(int i) { Console.WriteLine("true"); }}
输出:
truetrueFunc 有返回值
class MainClass{ delegate int A(int i); public static void Main(string[] args) { // Func<参数类型1,....,参数类型8,返回值类型> Func<int,int> action = Print; A a = Print; int aValue = a(1); int bValue = action(9); // 调用的时候写需要进入方法的参数 Console.WriteLine("a(1)的返回值:{0},action(9)的返回值:{1}",aValue,bValue); } public static int Print(int i) { Console.WriteLine("true"); return i; }}
输出:
truetruea(1)的返回值:1,action(9)的返回值:9
通过VS编译器中的程序集浏览器可以看到这两个委托
从下面这两幅图可以看到,Func是必须有一个返回值的参数,里面的参数可以最多可以有16个;Action可以没有参数,里面的参数最多也是16个
LINQ
LINQ:语言集成查询 (LINQ) 是一系列直接将查询功能集成到 C# 语言的技术统称。
LINQ源数据:从应用程序的角度来看,原始源数据的特定类型和结构并不重要。 应用程序始终将源数据视为 IEnumerable<T> 或 IQueryable<T> 集合。
代码展示:
public static void Main(string[] args){ // List 继承了 IEnumerable接口,所以可以使用 Where List<int> list = new List<int>(); list.Add(4); list.Add(9); list.Add(100); list.Add(50); // Where()使用了委托,括号里面可以直接使用 lambda表达式,下面会展示怎么使用lambda foreach (var item in list.Where(i => i > 10)) { Console.WriteLine(item); }}
输出:
10050
使用数组实现同样的效果:
public static void Main(string[] args){ int[] list = { 4, 9, 100, 50 }; foreach (var item in list.Where(i => i > 10)) { Console.WriteLine(item); }}
使用类似数据库的语句查询:
public static void Main(string[] args){ int[] list = { 4, 9, 100, 50 }; IEnumerable<int> vs = from item in list where item > 10 select item; foreach (var item in vs) { Console.WriteLine(item); }}lambda
(参数)=>{ 语句; }
匿名方法
当有一个方法只有委托在使用,且只使用一次,就可以使用匿名方法。使用方法看下面代码
class MainClass{ delegate void Del(); public static void Main(string[] args) { // 直接在声明的时候写方法,方法直接用delegate命名,参数必须与委托一致,如果有返回值,需要写return Del myDelegate = delegate () { Console.WriteLine("匿名方法"); }; }}
输出:
匿名方法使用lambda 替代匿名方法无返回值委托
class MainClass{ delegate void Del(); public static void Main(string[] args) { Del myDelegate = () => { Console.WriteLine("匿名方法"); }; }}
与上面是一样的效果,=> 读作 goes to
class MainClass{ public static void Main(string[] args) { // Action 足够应付大部分无返回值的委托 Action<int> action = (int i) => { Console.WriteLine("匿名方法"); }; }}
再简写一点
class MainClass{ public static void Main(string[] args) { Action<int> action = (i) => { Console.WriteLine("匿名方法"); }; }}
如果只有一个参数,多个参数需要写括号
class MainClass{ public static void Main(string[] args) { Action<int> action = i => { Console.WriteLine("匿名方法"); }; }}有返回值委托
class MainClass{ public static void Main(string[] args) { // 如果使用 delegate 的时候有参数,参数必须声明类型,Action、Func都需要遵守这一条 Func<int, int> func = delegate (int i) { return i; }; Console.WriteLine("func({0})的返回值是:{0}",func(9)); }}
输出:
func(9)的返回值是:9
使用lambda简写
class MainClass{ public static void Main(string[] args) { Func<int, int> func = (int i) =>{ return i; }; Console.WriteLine("func({0})的返回值是:{0}",func(9)); }}
再简写
class MainClass{ public static void Main(string[] args) { Func<int, int> func = (i) =>{ return i; }; Console.WriteLine("func({0})的返回值是:{0}",func(9)); }}
如果只有一个参数也可以不写括号
class MainClass{ public static void Main(string[] args) { Func<int, int> func = i =>{ return i; }; Console.WriteLine("func({0})的返回值是:{0}",func(9)); }}
如果只有方法体只有一条语句,可以省略大括号和return
class MainClass{ public static void Main(string[] args) { Func<int, int> func = i =>i; Console.WriteLine("func({0})的返回值是:{0}",func(9)); }}使用委托实现LINQ的where
class MainClass{ public static void Main(string[] args) { int[] a = { 8, 90, 4, 20 }; // 使用了扩展方法,this关键词修饰的可以不写在括号里面 IEnumerable<int> data = a.MyWhere(i => i > 10); foreach (var item in data) { Console.WriteLine(item); } }}// 扩展方法是写在静态类里面的静态方法,扩展方法必须有一个参数,且参数使用this关键词修饰static class A{ public static IEnumerable<T> MyWhere<T>(this IEnumerable<T> data, Func<T, bool> func) { List<T> list = new List<T>(); foreach (var item in data) { if (func(item)) { list.Add(item); } } return list; }}
输出:
9020
标签: #lamda foreach