16.1 foreach 循环中捕获变量的变化
在 foreach 循环内的匿名函数(通常为Lambda表达式)中捕获循环 变量时要格外小心。代码清单16-1就展示了这样一个简单的示例,它看上去似乎会输出 x 、 y 、 z 。
string[] values = new string[] { "x", "y", "z" };
var actions = new List<Action>();
foreach (string value in values)
{
actions.Add(() => Console.WriteLine(value));
}
foreach (Action action in actions)
{
action();
}
在C# 3和C# 4中,以上代码实际上会打印出三个 z 。循环变量( value )可由Lambda表达式捕获,且名义上在循环的每次迭代中,只有一个变量“实例”的值发生了变化。全部三个委托都将引用相同的变量,并且在最终执行时,该变量的值为 z 。这并不是编译器实现上的错误,而是语言被指定所产生的行为。
在C# 5中,语言的行为与当初预期的一样:循环的每次迭代都可有效地引入一个单独变量。 每个委托都引用不同的变量,变量的值就是这次循环迭代中产生的值。
有关该特性的内容就讲到这里,它只是修复了会让很多开发者产生疑惑的语言部分而已。 (Stack Overflow上有超多人询问这方面的问题。)
但此处要提醒一句:如果编写的代码需用不同版本的C#编译器进行编译,则应注意它们产生 的行为是不同的。对于任何版本的C#来说,代码清单16-1都不会产生警告,而在C# 5中,行为却 神不知鬼不觉地发生了改变。要慎之又慎,并且确保有单元测试可以依靠。
16.1 foreach 循环中捕获变量的变化的更多相关文章
- js for 循环中的 变量问题。
今日处理项目中的一个循环,本来就是一个小小的for循环,后来发现该段程序出现了问题,仔细检查代码没有发现其中的错误.无奈只好叫来了老大帮忙.通过在模版中断点调试(该方式只能自己写debugger断点) ...
- C#在foreach循环中修改字典等集合出错的处理
C#在foreach循环中修改字典等集合出错:System.InvalidOperationException: Collection was modified; enumeration operat ...
- 【SQL】小心在循环中声明变量——浅析SQL变量作用域
本文适用:T-SQL(SQL Server) 先看这个语句: --跑3圈 BEGIN --每圈都定义一个表变量,并插入一行 DECLARE @t TABLE(Col INT PRIMARY KEY) ...
- C#不允许在foreach循环中改变数组或集合中元素的值(注:成员的值不受影响)
C#不允许在foreach循环中改变数组或集合中元素的值(注:成员的值不受影响),如以下代码将无法通过编译. foreach (int x in myArray) { x++; //错误代码,因为改变 ...
- 「译」forEach循环中你不知道的3件事
前言 本文925字,阅读大约需要7分钟. 总括: forEach循环中你不知道的3件事. 原文地址:3 things you didn't know about the forEach loop in ...
- 【PHP】 foreach循环中变量引用的一道面试题
$a = array('a','b','c'); foreach($a as &$v){} foreach($a as $v){ } var_dump($a); 现在.不要打开浏览器,猜测一下 ...
- 关于“foreach循环”中遇到的几个问题总结
1.列表页面用"foreach循环"的时候数据没有显示,此时需要检查你对象模型中属性的首字母是否大写,切记不能大写(本人在做一个项目的时候,对象模型是别人建立的,属性首字母大写了, ...
- 用闭包解决 js 循环中函数变量暂存问题
需求:有一个数组,根据数组的值渲染对应的数字div,单击对应的div 在控制台打印对应的数字.如点击1,控制台打印1. 问题: 不管点击哪个值 打出来都是4 代码如下 <!DOCTYPE htm ...
- foreach循环中为什么不要进行remove/add操作
先来看一段代码,摘自阿里巴巴的java开发手册 List<String> a = new ArrayList<String>(); a.add("1"); ...
随机推荐
- 将一个对象相同的属性(不区分大小写)赋值给一个新对象 DataTable的一个简单的扩展
将一个对象相同的属性(不区分大小写)赋值给一个新对象 1 public static T Mapper<S, T>(S source) 2 { 3 T t = Activator.Cr ...
- 转 java中5种创建对象的方法
作为Java开发者,我们每天创建很多对象,但我们通常使用依赖管理系统,比如spring去创建对象.然而这里有很多创建对象的方法,我们会在这篇文章中学到. Java中有5种创建对象的方式,下面给出它们的 ...
- swift 2.0 语法 循环
//: Playground - noun: a place where people can play import UIKit /*: for循环 * 基本用法和OC一致 * 条件表达式必须是bo ...
- unable to execute dex: multiple dex files Cocos2dxAccelerometer
原文转载:http://discuss.cocos2d-x.org/t/conversion-to-dalvik-format-failed-unable-to-execute-dex-multipl ...
- SQL语句多表连接查询语法
一.外连接 1.左连接 left join 或 left outer join SQL语句:select * from student left join score on student.Num= ...
- Intellij热部署插件JRebel使用方法(转载)
Intellij热部署插件JRebel帮助开发者在项目处于运行状态下任意修改Java文件并动态反馈到运行的项目中.插件官方下载地址:https://plugins.jetbrains.com/plug ...
- BNU 13064 Dice (I) 前缀和优化DP
Dice (I) You have N dices; each of them has K faces numbered from 1 to K. Now you have arranged th ...
- centos上装eclipse步骤
1.去官网下个eclipse for linux的 地址:http://www.eclipse.org/downloads/ Eclipse IDE for Java EE Developer ...
- to prof. Choi
Dear Prof. Choi It is my great pleasure to receive your reply ,but terribly sorry for my late reply ...
- 01-S3C2440学习入门概念+环境搭建【转】
本文转载自:http://blog.csdn.net/fengyuwuzu0519/article/details/54754812 一.心得: 这两年学过很多东西,有点杂,总感觉不够踏实,于是准备写 ...