惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

U
Unit 42
Microsoft Azure Blog
Microsoft Azure Blog
Engineering at Meta
Engineering at Meta
博客园 - 【当耐特】
人人都是产品经理
人人都是产品经理
Cyber Security Advisories - MS-ISAC
Cyber Security Advisories - MS-ISAC
WordPress大学
WordPress大学
有赞技术团队
有赞技术团队
Blog — PlanetScale
Blog — PlanetScale
酷 壳 – CoolShell
酷 壳 – CoolShell
aimingoo的专栏
aimingoo的专栏
Jina AI
Jina AI
小众软件
小众软件
博客园 - 叶小钗
MongoDB | Blog
MongoDB | Blog
大猫的无限游戏
大猫的无限游戏
博客园 - 聂微东
Y
Y Combinator Blog
云风的 BLOG
云风的 BLOG
I
InfoQ
OSCHINA 社区最新新闻
OSCHINA 社区最新新闻
Martin Fowler
Martin Fowler
P
Proofpoint News Feed
MyScale Blog
MyScale Blog

博客园 - 菜鸟吴迪

Lucene搜索结果排序问题(按时间倒序排的替代解决方法) 利用Lucene.net搜索引擎进行多条件搜索的做法 (转) (转)Razor引擎学习:RenderBody,RenderPage和RenderSection 读取txt文本,批量插入到数据库中! ASP.NET MVC3 返回多个实体或泛型 MySQL数据库集群Master-Slave模式安装摘要 使用HtmlAgilityPack批量抓取网页数据 Jquery each - 菜鸟吴迪 - 博客园 堆?栈?(转) 数据库并发控制!!! Velocity脚本简明教程 Visual Studio的调试技巧 《C#与.NET3.5高级程序设计(第4版)》笔记10 sql分页问题,老话题!! sql查询连续三天之内都有记录的人员!! Asp.net Mvc Controller接收可控的数组或字典类型的实现方法: SELECT INTO 和 INSERT INTO SELECT 两种表复制语句 (转) httpContext里面的东西!!! c#新特性!!!
c#闭包!!
菜鸟吴迪 · 2010-08-20 · via 博客园 - 菜鸟吴迪

简单来讲,闭包允许你将一些行为封装,将它像一个对象一样传来递去,而且它依然能够访问到原来第一次声明时的上下文

奇怪的局部变量:讨论一下C#中的闭包

[0]静态全局字段

C# code

using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace ConsoleApplication3 { class Program { public static int copy;//[0]这个不是闭包 static void Main() { //定义动作组 List<Action> actions = new List<Action>(); for (int counter = 0; counter < 10; counter++) { copy = counter; actions.Add(() => Console.WriteLine(copy)); } //执行动作 foreach (Action action in actions) action(); } } } //注:Action定义如下: //public delegate void Action();

[1]局部变量(闭包一)

C# code

using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace ConsoleApplication3 { class Program { static void Main() { int copy;//[1]闭包一 //定义动作组 List<Action> actions = new List<Action>(); for (int counter = 0; counter < 10; counter++) { copy = counter; actions.Add(() => Console.WriteLine(copy)); } //执行动作 foreach (Action action in actions) action(); } } } //注:Action定义如下: //public delegate void Action();

[2]局部变量(闭包二)

C# code

using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace ConsoleApplication3 { class Program { static void Main() { //定义动作组 List<Action> actions = new List<Action>(); for (int counter = 0; counter < 10; counter++) { int copy;//[1]闭包二 copy = counter; //int copy = counter;//换种写法 actions.Add(() => Console.WriteLine(copy)); } //执行动作 foreach (Action action in actions) action(); } } } //注:Action定义如下: //public delegate void Action();

[3]局部变量(闭包三)

C# code

using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace ConsoleApplication3 { class Program { static void Main() { //定义动作组 List<Action> actions = new List<Action>(); for (int counter = 0; counter < 10; counter++)//[3]闭包三 { actions.Add(() => Console.WriteLine(counter)); } //执行动作 foreach (Action action in actions) action(); } } } //注:Action定义如下: //public delegate void Action();

[0]:输出什么?
[1]:输出什么?
[2]:输出什么?
[3]:输出什么?

这几个例子,可以将匿名函数进行转换,这样可以看的更清楚
在[0]中,“外部变量”copy是类的一个静态成员,因此可以讲匿名函数转换为以下形式:

C# code

class Program { public static int copy;//[0]这个不是闭包 static void TempMethod() { Console.WriteLine(copy); } static void Main() { //定义动作组 List<Action> actions = new List<Action>(); for (int counter = 0; counter < 10; counter++) { copy = counter; actions.Add(new Action(TempMethod)); } //执行动作 foreach (Action action in actions) action(); } }

[1],[2]中“外部变量”copy是Main方法中的局部变量,局部变量的生存期现在必须至少延长为匿名函数委托的生存期。这可以通过将局部变量“提升”到编译器生成的类的字段来实现。之后,局部变量的实例化对应于为编译器生成的类创建实例,而访问局部变量则对应于访问编译器生成的类的实例中的字段。而且,匿名函数将会成为编译器生成类的实例方法:

C# code

class Program { static void Main() { //定义动作组 TempClass tc = new TempClass(); //定义动作组 List<Action> actions = new List<Action>(); for (int counter = 0; counter < 10; counter++) { tc.copy = counter; actions.Add(tc.TempMethod); } //执行动作 foreach (Action action in actions) action(); } class TempClass { public int copy; public void TempMethod() { Console.WriteLine(copy); } } }

C# code

class Program { static void Main() { //定义动作组 //定义动作组 List<Action> actions = new List<Action>(); for (int counter = 0; counter < 10; counter++) { TempClass tc = new TempClass(); tc.copy = counter; actions.Add(tc.TempMethod); } //执行动作 foreach (Action action in actions) action(); } class TempClass { public int copy; public void TempMethod() { Console.WriteLine(copy); } } }

[3]中的“外部变量”counter是for循环的循环因子,因此可以转换为以下形式:

C# code

class Program { static void Main() { //定义动作组 List<Action> actions = new List<Action>(); TempClass tc = new TempClass(); for (tc.copy = 0; tc.copy < 10; tc.copy++) { actions.Add(new Action(tc.TempMethod)); } //执行动作 foreach (Action action in actions) action(); } class TempClass { public int copy; public void TempMethod() { Console.WriteLine(copy); } } }