<?xml version="1.0" encoding="utf-8"?><feed xmlns="http://www.w3.org/2005/Atom"><title type="text">博客园_风尘浪子</title><subtitle type="text">只要肯努力，梦想总有一天会实现</subtitle><id>http://feed.cnblogs.com/blog/u/82463/rss</id><updated>2012-05-30T11:09:52Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><generator>feed.cnblogs.com</generator><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/"/><link rel="self" type="application/atom+xml" href="http://feed.cnblogs.com/blog/u/82463/rss"/><entry><id>http://www.cnblogs.com/leslies2/archive/2012/05/17/2504673.html</id><title type="text">.NET基础篇——Entity Framework 数据转换层通用类</title><summary type="text">本文将为您介绍一个对应Entity Framework的 CRUD 通用类，相比起以往的SqlCommand操作，Entity Framework更体现出映射的灵活性。以往的操作中，即使开发出一个通用类，CommandText 通常都需要使用手工输入，特别是重复的Update命令操作中，往往令人不厌其烦。通过Entity Framework可以把CRUD更高度地集中在一个通用类，令开发变得更加简单。</summary><published>2012-05-17T06:16:00Z</published><updated>2012-05-17T06:16:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2012/05/17/2504673.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2012/05/17/2504673.html"/><content type="html">&lt;p&gt;在实现基础的三层开发的时候，大家时常会在数据层对每个实体进行CRUD的操作，其中存在相当多的重复代码。为了减少重复代码的出现，通常都会定义一个共用类，实现相似的操作，下面为大家介绍一下Entity Framework时常用到的通用类。&lt;br /&gt;首先在数据库建立起几个关联表：Person、Company、Position，三个实体之间通过导航属性进行相互引用。&lt;/p&gt;&lt;p&gt;&lt;img style="display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2012/64989/2012051615373812.jpg" alt="" width="381" height="541" /&gt;&lt;/p&gt;&lt;p&gt;下面为大家分别介绍以泛型实现的 Create、Read、Update、Delete 操作：&lt;/p&gt;&lt;p&gt;1. Create&lt;/p&gt;&lt;p&gt;在ObjectContext类之中，早已经为大家预定了一个Create 的操作 AddObject：&lt;/p&gt;&lt;p&gt;void ObjectContext.AddObject（entitySetName string，object entity）&lt;br /&gt;void ObjectSet&amp;lt;T&amp;gt;.AddObject（T entity）&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Add&amp;lt;T&amp;gt;&lt;span style="color: #000000;"&gt;(T entity) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt; T : &lt;span style="color: #0000ff;"&gt;EntityObject&lt;br/&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; changedCount = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TransactionScope(TransactionScopeOption.Required))&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                         context.AddObject(&lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;&lt;span style="color: #000000;"&gt;(T).Name, entity);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                         changedCount =&lt;span style="color: #000000;"&gt; context.SaveChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (changedCount &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            context.AcceptAllChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        scope.Complete();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;span style="color: #000000;"&gt;                { ........ }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; changedCount;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;从下面的测试可以看到，ObjectContext.AddObject（entitySetName string，object entity）已相当成熟，它不但可以加入单个实体，也可通过导航属性，一次性加入多个关联实体。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&lt;span style="color: #000000;"&gt;[] args)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             BaseCommand command = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BaseCommand();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立关联实体&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             Company company = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Company() { CompanyName = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Sun&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; ,Address=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Beijing&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,Telephone=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;010-87654321&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;};&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             Position position = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Position() { PositionName = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Project Manager&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, Salary = &lt;span style="color: #800080;"&gt;15000.00&lt;/span&gt;, Company =&lt;span style="color: #000000;"&gt; company };&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;通过Add&amp;lt;T&amp;gt;同时加入实体对象company与position&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n=command.Add&amp;lt;Position&amp;gt;&lt;span style="color: #000000;"&gt;(position);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;span style="color: #000000;"&gt;            Console.ReadKey();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;若要使用批量插入，只要在AddObject方法前多加一个重复语言即可，在此就不再多作解释了。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddList&amp;lt;T&amp;gt;(List&amp;lt;T&amp;gt; entityList) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; changedCount = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TransactionScope(TransactionScopeOption.Required))&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (T entity &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt;&lt;span style="color: #000000;"&gt; entityList)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                             context.AddObject(&lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;&lt;span style="color: #000000;"&gt;(T).Name, entity);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                         changedCount =&lt;span style="color: #000000;"&gt; context.SaveChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (changedCount &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            context.AcceptAllChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        scope.Complete();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;span style="color: #000000;"&gt;                { ....... }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; changedCount;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;2. Delete&lt;/p&gt;&lt;p&gt;同样地，ObjectContext 类当中也存在方法 ObjectContext.DeleteObject（object entity）用于删除实体。&lt;br /&gt;首先通过输入的参数 id 建立起EntityKey对象，然后在ObjectContext查找此实体，若实体存在则使用ObjectContext.DeleteObject（object entity）方法把此实体删除 。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Delete&amp;lt;T&amp;gt;(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; changedCount = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TransactionScope(TransactionScopeOption.Required))&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立EntityKey对象&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                         EntityKey entityKey = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; EntityKey(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BasicArchitectureEntities.&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + &lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(T).Name, &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Id&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;, id);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;通过EntityKey找到实体&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; objResult =&lt;span style="color: #000000;"&gt; context.GetObjectByKey(entityKey);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;若实体存在则删除实体&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (objResult != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            context.DeleteObject(objResult);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                         changedCount =&lt;span style="color: #000000;"&gt; context.SaveChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (changedCount &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            context.AcceptAllChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                         &lt;br/&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        scope.Complete();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt; &lt;span style="color: #000000;"&gt;                { ...... }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; changedCount;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;ObjectContext.DeleteObject（object entity）与ObjectContext.AddObject（entitySetName string，object entity）相同，可以通过导航属性，一次性删除多个关联实体。但如果数据库中存在下面的数据&lt;/p&gt;&lt;p&gt;Company表：&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012051616161792.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;Position表：&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012051616162944.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;此时使用此 int Delete&amp;lt;Company&amp;gt;（2） 方法删除Company对象，系统将会报错。这是由于导航属性在默认情况下具有延时加载的特性，在系统使用ObjectC&lt;span style="color: #000000;"&gt;ontext.GetObjectByKey(entityKey)方法加载实体时，它的导航属性不会马上加载到上下文当中。而是在调用该导航属性时，对象才会被加载。&lt;br /&gt;&lt;/span&gt;因而系统通过ObjectC&lt;span style="color: #000000;"&gt;ontext.GetObjectByKey(2)获取Company对象时，对应的Position对象并未被加载到上下文当中，所以当删除Company对象时，Position对象不能被同步删除，因而造成逻辑上的错误。为解决这一问题，可以利用&lt;span style="color: #000000;"&gt;RelatedEnd.Load（）方法提前加载&lt;/span&gt;导航属性。&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #000000;"&gt;RelatedEnd是&lt;span id="mt193" class="sentence SentenceHover" data-guid="87b13325138e6fdabf80d11253fb9a4b" data-source="An &amp;lt;span&amp;gt;&amp;lt;span class=&amp;quot;selflink&amp;quot;&amp;gt;EntityCollection&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot;  xmlns=&amp;quot;&amp;quot;&amp;gt;&amp;lt;span&amp;gt;&amp;amp;lt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;TEntity&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot;  xmlns=&amp;quot;&amp;quot;&amp;gt;&amp;lt;span&amp;gt;&amp;amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt; might have a corresponding &amp;lt;span&amp;gt;&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot; &amp;gt;&amp;lt;span&amp;gt;EntityReference&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot;  xmlns=&amp;quot;&amp;quot;&amp;gt;&amp;lt;span&amp;gt;&amp;amp;lt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;TEntity&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot;  xmlns=&amp;quot;&amp;quot;&amp;gt;&amp;lt;span&amp;gt;&amp;amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;."&gt;&lt;span&gt;&lt;span class="selflink"&gt;EntityCollection&lt;span&gt;&amp;lt;&lt;/span&gt;TEntity&lt;span&gt;&amp;gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt; 、&lt;span&gt;EntityReference&lt;span&gt;的父类，它们&lt;span id="mt189" class="sentence SentenceHover" data-guid="db1b4c58cf6d5bb7a85e4400f0038693" data-source="An &amp;lt;span&amp;gt;&amp;lt;span class=&amp;quot;selflink&amp;quot;&amp;gt;EntityCollection&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot;  xmlns=&amp;quot;&amp;quot;&amp;gt;&amp;lt;span&amp;gt;&amp;amp;lt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;TEntity&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot;  xmlns=&amp;quot;&amp;quot;&amp;gt;&amp;lt;span&amp;gt;&amp;amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt; is a collection of objects of a particular entity type that represents the &amp;quot;many&amp;quot; end of a one-to-many or many-to-many relationship. "&gt;是特定实体类型的对象集合，该实体类型表示一对多、多对一、多对多的关系。而RelatedEnd.Load（）方法，可以&lt;span id="mt1" class="sentence" data-guid="3019089d1ceb8edd013fe1d99ce30696" data-source="When overridden in a derived class, loads the related object or objects into the related end with the default merge option."&gt;将一个或多个相关对象提前加载到相关实体当中。&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #000000;"&gt;首先通过ObjectC&lt;span style="color: #000000;"&gt;ontext.GetObjectByKey(entityKey)&lt;/span&gt;方法找到Company对象，然后利用反射属性PropertyInfo类&lt;span style="color: #000000;"&gt;获取&lt;/span&gt;导航属性Position，最后使用RelatedEnd.Load（）方法，把导航属性加载到当前上下文中。此时使用Delete&amp;lt;Company,Position&amp;gt;(2)方法删除Company对象时，系统将能正常运行，并把对应的Position对象一并删除。&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Delete&amp;lt;PKEntity, FKEntity&amp;gt;(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;&lt;span style="color: #000000;"&gt; id)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; PKEntity : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; FKEntity : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; changedCount = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TransactionScope(TransactionScopeOption.Required))&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据软件Id建立EntityKey对象&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                         EntityKey entityKey = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; EntityKey(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BasicArchitectureEntities.&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + &lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(PKEntity).Name, &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Id&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;, id);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据EntityKey查找对应对象&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                         PKEntity objResult = context.GetObjectByKey(entityKey) &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt;&lt;span style="color: #000000;"&gt; PKEntity;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据FKEntity加载导航属性&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                         PropertyInfo propertyInfo = &lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(PKEntity).GetProperty(&lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;&lt;span style="color: #000000;"&gt;(FKEntity).Name);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                         EntityCollection&amp;lt;FKEntity&amp;gt; FKEntityList = propertyInfo.GetValue(objResult, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt; EntityCollection&amp;lt;FKEntity&amp;gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (FKEntityList != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            FKEntityList.Load();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;   &lt;br/&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (objResult != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            context.DeleteObject(objResult);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;                         changedCount =&lt;span style="color: #000000;"&gt; context.SaveChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (changedCount &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            context.AcceptAllChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                         &lt;br/&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        scope.Complete();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt; &lt;span style="color: #000000;"&gt;                { ........ }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; changedCount;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;通过下面的方法也可根据输入的委托predicate，批量删除有关的数据。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Delete&amp;lt;T&amp;gt;(Func&amp;lt;T,&lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt;&amp;gt; predicate) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T: EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; changedCount = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TransactionScope(TransactionScopeOption.Required))&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据输入的委托查找数据&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; list = context.CreateObjectSet&amp;lt;T&amp;gt;&lt;span style="color: #000000;"&gt;().Where(predicate);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;若存在数据，删除有关数据&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (list.Count() &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; obj &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt;&lt;span style="color: #000000;"&gt; list)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="color: #000000;"&gt;                                context.DeleteObject(obj);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                         changedCount =&lt;span style="color: #000000;"&gt; context.SaveChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (changedCount &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            context.AcceptAllChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        scope.Complete();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt; &lt;span style="color: #000000;"&gt;                { ...... }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; changedCount;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;与前面的例子相同，当使用 Delete&amp;lt;Company&amp;gt;(x=&amp;gt;x.Id==2) 方法删除 Company 对象时，由于导航属性 Position 处于延迟加载的状态，以致系统无法实现同步删除，从而令数据出现逻辑性的错误。&lt;br /&gt;此时使用类似的方法，利用 &lt;span style="color: #000000;"&gt;&lt;span style="color: #000000;"&gt;RelatedEnd.Load（） 把导航属性提前加入到上下文中，再删除Company对象时，系统就可以把对应 Position 对象一并删除。&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Delete&amp;lt;PKEntity, FKEntity&amp;gt;(Func&amp;lt;PKEntity,&lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt;&amp;gt;&lt;span style="color: #000000;"&gt; predicate)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; PKEntity : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; FKEntity : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; changedCount = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TransactionScope(TransactionScopeOption.Required))&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据输入的委托查找数据&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; list = context.CreateObjectSet&amp;lt;PKEntity&amp;gt;&lt;span style="color: #000000;"&gt;().Where(predicate);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;若数目大于0，删除有关数据&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (list.Count() &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; obj &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt;&lt;span style="color: #000000;"&gt; list)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                                 &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在删除前加载其导航属性&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                                 PropertyInfo propertyInfo = &lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(PKEntity).GetProperty(&lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;&lt;span style="color: #000000;"&gt;(FKEntity).Name);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                                 EntityCollection&amp;lt;FKEntity&amp;gt; FKEntityList = propertyInfo.GetValue(obj, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;) &lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                                     &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt; EntityCollection&amp;lt;FKEntity&amp;gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                                 &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (FKEntityList.Count &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt; &lt;span style="color: #000000;"&gt;                                    FKEntityList.Load();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;span style="color: #000000;"&gt;                                context.DeleteObject(obj);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                         changedCount =&lt;span style="color: #000000;"&gt; context.SaveChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (changedCount &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            context.AcceptAllChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        scope.Complete();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt; &lt;span style="color: #000000;"&gt;                { ....... }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; changedCount;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;此时使用Delete&amp;lt;Company,Position&amp;gt;(x=&amp;gt;x.Id==2)，这样就可以把Company对象和相关的Position对象同时删除。&lt;/p&gt;&lt;p&gt;&lt;span style="color: #000000;"&gt;&lt;span style="color: #000000;"&gt;&amp;nbsp;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #000000;"&gt;3. Update&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p class="title"&gt;&lt;span class="tcnt"&gt;ObjectContext 中存在方法 &lt;/span&gt;ObjectContext&lt;span&gt;.&lt;/span&gt;ApplyCurrentValues&lt;span&gt;&amp;lt;&lt;/span&gt;&lt;span class="typeparameter"&gt;TEntity&lt;/span&gt;&lt;span&gt;&amp;gt; 和 ObjectContext.&lt;/span&gt;&lt;span id="mt16" class="sentence SentenceHover" data-guid="83479f627df36c9eb194dcbe380a951b" data-source="The &amp;lt;span&amp;gt;&amp;lt;span class=&amp;quot;selflink&amp;quot;&amp;gt;ApplyOriginalValues&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot;  xmlns=&amp;quot;&amp;quot;&amp;gt;&amp;lt;span&amp;gt;&amp;amp;lt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;TEntity&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot;  xmlns=&amp;quot;&amp;quot;&amp;gt;&amp;lt;span&amp;gt;&amp;amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt; method is used to apply changes that were made to objects outside the &amp;lt;span&amp;gt;&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot; &amp;gt;&amp;lt;span&amp;gt;ObjectContext&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;, such as detached objects that are received by a Web service."&gt;&lt;span&gt;&lt;span class="selflink"&gt;ApplyOriginalValues&lt;span&gt;&amp;lt;&lt;/span&gt;TEntity&lt;span&gt;&amp;gt;，用于把&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span id="mt1" class="sentence SentenceHover" data-guid="ee65494706a27116f41876e69bd8bba1" data-source="Copies the scalar values from the supplied object into set of original values for the object in the &amp;lt;span&amp;gt;&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot; &amp;gt;&amp;lt;span&amp;gt;ObjectContext&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt; that has the same key."&gt;将标量值从实体复制到 &lt;span&gt;ObjectContext&lt;/span&gt; 中具有相同主键的对象集中。&lt;/span&gt;&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;em&gt;注意：&lt;span id="mt1" class="sentence SentenceHover" data-guid="ee65494706a27116f41876e69bd8bba1" data-source="Copies the scalar values from the supplied object into set of original values for the object in the &amp;lt;span&amp;gt;&amp;lt;span class=&amp;quot;mtpsTagOuterHtml&amp;quot; &amp;gt;&amp;lt;span&amp;gt;ObjectContext&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt; that has the same key."&gt;在调用此方法前必须把实体预先加载到当前上下文当中，要不然系统将会显示&amp;nbsp; &amp;ldquo;&lt;/span&gt;&lt;span class="tcnt"&gt;objectstatemanager 无法跟踪具有相同键的多个对象&lt;/span&gt;&amp;rdquo; 的错误。&lt;/em&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;span style="color: #000000;"&gt;由于DAL层的对象大部分使用单体模式进行开发，而BaseCommand是一个共用对象，在共同操作时，Create、Delete、Read 等操作一般不会对实体造成逻辑性的影响。但如果有多个实体同时调用 Update 操作，就有可能对实体造成逻辑性影响。为了避免这一事件的发生，此处使用方法锁定的模式，以 lock(object) 锁定某一对象，以确保在同一时间内只会对一个实体进行更新。&lt;br /&gt;首先通过反射方式获取对象的Id，然后通过 ObjectC&lt;span style="color: #000000;"&gt;ontext.GetObjectByKey(entityKey) 方法把实体加载到当前上下文当中，最后利用 ObjectContext&lt;span&gt;.&lt;/span&gt;ApplyCurrentValues&lt;span&gt;&amp;lt;&lt;/span&gt;&lt;span class="typeparameter"&gt;TEntity&lt;/span&gt;&lt;span&gt;&amp;gt; 方法，把新加入的实体的属性复制当前上下文。&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; BaseCommand&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; o = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt;&lt;span style="color: #000000;"&gt;();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         &lt;br/&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Update&amp;lt;T&amp;gt;(T entity) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;lock&lt;/span&gt;&lt;span style="color: #000000;"&gt; (o)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; changedCount = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                 Type type = &lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;&lt;span style="color: #000000;"&gt;(T);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TransactionScope(TransactionScopeOption.Required))&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取实体的Id属性&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                             PropertyInfo property = type.GetProperty(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Id&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; id = property.GetValue(entity, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据Id获取上下文中的对应实体&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                             EntityKey entityKey = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; EntityKey(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BasicArchitectureEntities.&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                                   + type.Name, &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Id&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;, id);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; objResult =&lt;span style="color: #000000;"&gt; context.GetObjectByKey(entityKey);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;                             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;更新实体属性&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (objResult != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;                                 context.ApplyCurrentValues&amp;lt;T&amp;gt;&lt;span style="color: #000000;"&gt;(type.Name, entity);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;                             changedCount =&lt;span style="color: #000000;"&gt; context.SaveChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (changedCount &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt; &lt;span style="color: #000000;"&gt;                                context.AcceptAllChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            scope.Complete();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    { ... }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; changedCount;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt; &lt;span style="color: #000000;"&gt;        }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;在一对多，多对一关系时，也可以使用以下方法进行导航属性的同步更新。首先通过反射获取主实体的主键Id，然后建立EntityKey对象，再通过ObjectContext.GetObjectByKey(entityKey)方法在当前上下文当中获取此实体，最后通过 &lt;span style="color: #000000;"&gt;&lt;span style="color: #000000;"&gt;ObjectContext&lt;span&gt;.&lt;/span&gt;ApplyCurrentValues&lt;span&gt;&amp;lt;&lt;/span&gt;&lt;span class="typeparameter"&gt;TEntity&lt;/span&gt;&lt;span&gt;&amp;gt; 方法，把新加入的实体的属性复制当前上下文。&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;下一步就是对导航属性进行更新，首先通过反射获取外键属性，然后对一对多，多对一的关系进行分别处理。在一对多关系时，把导航属性转换成EntityCollection&amp;lt;T2&amp;gt;对象集合，然后通过 &lt;span style="color: #000000;"&gt;&lt;span style="color: #000000;"&gt;ObjectContext&lt;span&gt;.&lt;/span&gt;ApplyCurrentValues&lt;span&gt;&amp;lt;&lt;/span&gt;&lt;span class="typeparameter"&gt;TEntity&lt;/span&gt;&lt;span&gt;&amp;gt; 方法对集合中的每个对象进行逐个更新。&lt;br /&gt;在多对一关系时，直接把导航属性转换成T2类型的对象进行更新。&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Update&amp;lt;T1, T2&amp;gt;&lt;span style="color: #000000;"&gt;(T1 entity)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T1 : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T2 : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;lock&lt;/span&gt;&lt;span style="color: #000000;"&gt; (o)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; changedCount = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                 Type typeT1 = &lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;&lt;span style="color: #000000;"&gt;(T1);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 Type typeT2 = &lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;&lt;span style="color: #000000;"&gt;(T2);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TransactionScope(TransactionScopeOption.Required))&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                             PropertyInfo property = typeT1.GetProperty(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Id&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; id = property.GetValue(entity, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据软件Id建立EntityKey对象&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                             EntityKey entityKey = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; EntityKey(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BasicArchitectureEntities.&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                                  + typeT1.Name, &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Id&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;, id);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据EntityKey查找对应对象&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                             T1 objT1 = context.GetObjectByKey(entityKey) &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt;&lt;span style="color: #000000;"&gt; T1;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;                             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在上下文中更新当前对象&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (objT1 != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;                                 context.ApplyCurrentValues&amp;lt;T1&amp;gt;&lt;span style="color: #000000;"&gt;(typeT1.Name, entity);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;                             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取外键属性&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                             PropertyInfo propertyInfo =&lt;span style="color: #000000;"&gt; typeT1.GetProperty(typeT2.Name);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;                             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在一对多关键时更新导航属性&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; T2List = propertyInfo.GetValue(entity, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;) &lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;                                    &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt; EntityCollection&amp;lt;T2&amp;gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (T2List != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                                 &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; obj &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt;&lt;span style="color: #000000;"&gt; T2List.ToList())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt; &lt;span style="color: #000000;"&gt;                                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                                     &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; oldEntity =&lt;span style="color: #000000;"&gt; context.GetObjectByKey(obj.EntityKey);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;                                     &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (oldEntity != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;                                         context.ApplyCurrentValues&amp;lt;T2&amp;gt;&lt;span style="color: #000000;"&gt;(typeT2.Name, obj);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt; &lt;span style="color: #000000;"&gt;                                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;                             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在多对一，一对一关系时更新导航属性&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; objT2 = propertyInfo.GetValue(entity, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;) &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt;&lt;span style="color: #000000;"&gt; T2;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (objT2!= &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;                                 &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; oldEntity =&lt;span style="color: #000000;"&gt; context.GetObjectByKey(objT2.EntityKey);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;                                 &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (oldEntity != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;                                     context.ApplyCurrentValues&amp;lt;T2&amp;gt;&lt;span style="color: #000000;"&gt;(typeT2.Name, objT2);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;                             changedCount =&lt;span style="color: #000000;"&gt; context.SaveChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;                             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (changedCount &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt; &lt;span style="color: #000000;"&gt;                                context.AcceptAllChanges();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt; &lt;span style="color: #000000;"&gt;                            scope.Complete();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt; &lt;span style="color: #000000;"&gt;                    { ...... }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; changedCount;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;65&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;66&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;通过此方法，无论你要通过Company同步更新Position，还是反过来通过Position同步更新Company，系统也能正常运行。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;4. Read&lt;/p&gt;&lt;p&gt;Read 是CRUD中最常见的，下面就为大家介绍最通用的几种方法&lt;/p&gt;&lt;p&gt;4.1 通过Id获取单个实体&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; T GetObject&amp;lt;T&amp;gt;(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                     EntityKey entityKey = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; EntityKey(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BasicArchitectureEntities.&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                           + &lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(T).Name, &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Id&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;, id);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; objResult =&lt;span style="color: #000000;"&gt; context.GetObjectByKey(entityKey);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; objResult &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt;&lt;span style="color: #000000;"&gt; T;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;4.2 通过输入的Func&amp;lt;T,bool&amp;gt;委托获取对象&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; T GetObject&amp;lt;T&amp;gt;(Func&amp;lt;T,&lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt;&amp;gt; predicate) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; objectSet = context.CreateObjectSet&amp;lt;T&amp;gt;&lt;span style="color: #000000;"&gt;().Where(predicate);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (objectSet.Count() &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; objectSet.First();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;4.3通过输入的Func&amp;lt;T,bool&amp;gt;委托获取对象，并同时加载单个导航属性&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; T GetObject&amp;lt;T&amp;gt;(Func&amp;lt;T, &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt;&amp;gt; predicate,&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&lt;span style="color: #000000;"&gt; includePath) &lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; objectQuery = context.CreateObjectSet&amp;lt;T&amp;gt;&lt;span style="color: #000000;"&gt;()&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        .Include(includePath)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;span style="color: #000000;"&gt;                        .Where(predicate);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (objectQuery.Count() &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; objectQuery.First();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;4.4通过输入的Func&amp;lt;T,bool&amp;gt;委托获取对象，并同时加载多个导航属性&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; T GetObject&amp;lt;T&amp;gt;(Func&amp;lt;T, &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt;&amp;gt; predicate, &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&lt;span style="color: #000000;"&gt;[] includePath)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; list = context.CreateObjectSet&amp;lt;T&amp;gt;().Where(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;1==1&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; path &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt;&lt;span style="color: #000000;"&gt; includePath)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                         list=&lt;span style="color: #000000;"&gt;list.Include(path);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; returnValue =&lt;span style="color: #000000;"&gt; list.Where(predicate).ToList();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (returnValue.Count() &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; returnValue.First();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;4.5 通过输入的Func&amp;lt;T,bool&amp;gt;委托获取对象集合&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; IList&amp;lt;T&amp;gt; GetList&amp;lt;T&amp;gt;(Func&amp;lt;T,&lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt;&amp;gt; func) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T:EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                     ObjectSet&amp;lt;T&amp;gt; objectSet = context.CreateObjectSet&amp;lt;T&amp;gt;&lt;span style="color: #000000;"&gt;();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     IList&amp;lt;T&amp;gt; list =&lt;span style="color: #000000;"&gt; objectSet.Where(func).ToList();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; list;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;4.6通过输入的Func&amp;lt;T,bool&amp;gt;委托获取对象集合，并同时加入单个导航属性&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; IList&amp;lt;T&amp;gt; GetList&amp;lt;T&amp;gt;(Func&amp;lt;T, &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt;&amp;gt; func,&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&lt;span style="color: #000000;"&gt; includePath)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     ObjectSet&amp;lt;T&amp;gt; objectSet = context.CreateObjectSet&amp;lt;T&amp;gt;&lt;span style="color: #000000;"&gt;();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                     IList&amp;lt;T&amp;gt; list =&lt;span style="color: #000000;"&gt; objectSet.Include(includePath).Where(func).ToList();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; list;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;4.7通过输入的Func&amp;lt;T,bool&amp;gt;委托获取对象集合，并同时加入多个导航属性&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; IList&amp;lt;T&amp;gt; GetList&amp;lt;T&amp;gt;(Func&amp;lt;T, &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt;&amp;gt; func, &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&lt;span style="color: #000000;"&gt;[] includePath)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt;&lt;span style="color: #000000;"&gt; T : EntityObject&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; list = context.CreateObjectSet&amp;lt;T&amp;gt;().Where(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;1==1&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; path &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt;&lt;span style="color: #000000;"&gt; includePath)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                         list =&lt;span style="color: #000000;"&gt; list.Include(path);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; list.Where(func).ToList();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;4.8 通过原始的SqlCommandText获取对象集&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; IList&amp;lt;T&amp;gt; GetList&amp;lt;T&amp;gt;(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&lt;span style="color: #000000;"&gt; commandText)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br/&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BasicArchitectureEntities context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BasicArchitectureEntities())&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="color: #000000;"&gt;                {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                     IList&amp;lt;T&amp;gt; list = context.ExecuteStoreQuery&amp;lt;T&amp;gt;&lt;span style="color: #000000;"&gt;(commandText).ToList();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; list;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="color: #000000;"&gt;                }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;&lt;span style="color: #000000;"&gt; (Exception ex)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="color: #000000;"&gt;            {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="color: #000000;"&gt;            }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;只能完成这一个DAL层的通用类以后，您就可在CompanyDAL、PersonDAL、PositionDAL ...... 等多个类中调用这个通用类，轻松地完成各项CRUD的操作。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; CompanyDAL：ICompanyDAL&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #000000;"&gt;    {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; BaseCommand command = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; BaseCommand();&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;&lt;span style="color: #000000;"&gt; AddCompany(Company company)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; command.Add&amp;lt;Company&amp;gt;&lt;span style="color: #000000;"&gt;(company);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;span style="color: #000000;"&gt;        }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; DeleteCompany(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;&lt;span style="color: #000000;"&gt; id)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; command.Delete&amp;lt;Company&amp;gt;&lt;span style="color: #000000;"&gt;(id);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="color: #000000;"&gt;        }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br/&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;&lt;span style="color: #000000;"&gt; UpdateComapny(Company company)&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #000000;"&gt;        {&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; command.Update&amp;lt;Company&amp;gt;&lt;span style="color: #000000;"&gt;(company);&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;span style="color: #000000;"&gt;        }&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;span style="color: #000000;"&gt;        .............&lt;br/&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;相比起以往的SqlCommand操作，Entity Framework更体现出映射的灵活性。以往的操作中，即使开发出一个通用类，CommandText 通常都需要使用手工输入，特别是重复的Update命令操作中，往往令人不厌其烦。通过Entity Framework可以把CRUD更高度地集中在一个通用类，令开发变得更加简单。&lt;br /&gt;希望本篇文章对您的系统开发有所帮助。&lt;/p&gt;&lt;p&gt;对软件架构开发有兴趣的朋友欢迎加入博客园讨论组&lt;span style="color: #0000ff;"&gt;&lt;a href="http://home.cnblogs.com/group/102576/" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt; &amp;ldquo;.NET高级编程&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;对NET开发有兴趣的朋友欢迎加入QQ群：162338858 &lt;a href="http://qun.qq.com/#jointhegroup/gid/162338858" target="_blank"&gt;&lt;img style="height: 20px;" title="点击这里加入此群" src="http://images.cnblogs.com/cnblogs_com/leslies2/gp.do.png" alt="点击这里加入此群" border="0" /&gt;&lt;/a&gt;&lt;/p&gt;&lt;div style="float: right; text-align: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;a id="Editor_Edit_hlEntryLink" title="view: .NET基础篇&amp;mdash;&amp;mdash;Entity Framework 数据转换层通用类" href="http://www.cnblogs.com/leslies2/archive/2012/05/16/2504673.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2012/05/16/2504673.html&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2504673.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/05/17/2504673.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html</id><title type="text">C#综合揭秘——深入分析委托与事件</title><summary type="text">本章主要介绍了委托（Delegate）的使用，解释委托的协变与逆变，以及如何使用 Delegate 使 Observer（观察者）模式的使用变得更加简单。而事件（Event）属于一种特殊的委托，最后，本文还介绍了匿名方法，泛型委托Predicate，Action，Func 的来由，以及 Lambda 表达式的使用方式。委托对象是一个派生自 System.MultcastDelegate 的类，它能通过 Invoke 方式进行同步调用，也可以通过 BeginInvoke，EndInvoke 方式实现异步调用。而事件（Event）属于一种特殊的委托，它与委托类型同步使用，可以简化的开发过程。本文会讲述事件的使用方式，并以ASP.NET的用户控件为例子，介绍一下自定义事件的使用。</summary><published>2012-03-22T03:04:00Z</published><updated>2012-03-22T03:04:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html"/><content type="html">&lt;p&gt;引言&lt;/p&gt;&lt;p&gt;&lt;a name="a0"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;本篇文章将为你介绍一下 Delegate 的使用方式，逐渐揭开 C# 当中事件（Event）的由来，它能使处理委托类型的过程变得更加简单。&lt;br /&gt;还将为您解释委托的协变与逆变，以及如何使用 Delegate 使 Observer（观察者）模式的使用变得更加简单。&lt;br /&gt;在事件的介绍上，会讲述事件的使用方式，并以ASP.NET的用户控件为例子，介绍一下自定义事件的使用。&lt;br /&gt;最后一节，将介绍Predicate&amp;lt;T&amp;gt;、Action&amp;lt;T&amp;gt;、Func&amp;lt;T，TResult&amp;gt;多种泛型委托的使用和Lambda的发展过程与其使用方式。&lt;br /&gt;因为时间仓促，文中有错误的地方敬请点评。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;目录&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a1"&gt;&lt;span style="color: #0000ff;"&gt;一、委托类型的来由&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a2"&gt;&lt;span style="color: #0000ff;"&gt;二、建立委托类&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a3"&gt;&lt;span style="color: #0000ff;"&gt;三、委托使用方式&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a4"&gt;&lt;span style="color: #0000ff;"&gt;四、深入解析事件&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a5"&gt;&lt;span style="color: #0000ff;"&gt;五、Lambda 表达式&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a name="a1"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;一、委托类型的来由&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;记得在使用C语言的年代，整个项目中都充满着针指的身影，那时候流行使用函数指针来创建回调函数，使用回调可以把函数回调给程序中的另一个函数。但函数指针只是简单地把地址指向另一个函数，并不能传递其他额外信息。&lt;br /&gt;在.NET中，在大部分时间里都没有指针的身影，因为指针被封闭在内部函数当中。可是回调函数却依然存在，它是以委托的方式来完成的。委托可以被视为一个更高级的指针，它不仅仅能把地址指向另一个函数，而且还能传递参数，返回值等多个信息。系统还为委托对象自动生成了同步、异步的调用方式，开发人员使用 BeginInvoke、EndInvoke 方法就可以抛开 Thread 而直接使用多线程调用 。&lt;/p&gt;&lt;p&gt;&lt;a name="a2"&gt;&lt;/a&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&amp;nbsp;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;二、建立委托类&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;使用delegate就可以直接建立任何名称的委托类型，当进行系统编译时，系统就会自动生成此类型。您可以使用delegate void MyDelegate() 方式建立一个委托类，并使用ILDASM.exe观察其成员。由ILDASM.exe 中可以看到，它继承了System.MulticastDelegate类，并自动生成BeginInvoke、EndInvoke、Invoke 等三个常用方法。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031017103813.jpg" alt="" width="561" height="169" /&gt;&lt;/p&gt;&lt;p&gt;Invoke 方法是用于同步调用委托对象的对应方法，而BeginInvoke、EndInvoke是用于以异步方式调用对应方法的。&lt;br /&gt;对于异步调用的使用方式，可以参考：&lt;span style="color: #0000ff;"&gt;&lt;a id="cb_post_title_url" class="postTitle2" href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html#t4" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;C#综合揭秘&amp;mdash;&amp;mdash;细说多线程&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; MyDelegate:MulticastDelegate&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;同步调用委托方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;virtual&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Invoke();&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;异步调用委托方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;virtual&lt;/span&gt; IAsyncResult BeginInvoke(AsyncCallback callback,&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; state);&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;virtual&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; EndInvoke(IAsyncResult result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;8&lt;/span&gt;      }&lt;/div&gt;&lt;p&gt;MulticastDelegate是System.Delegate的子类，它&lt;span&gt;是一个特殊类，&lt;/span&gt;编译器和其他工具可以从此类派生，但是自定义类不能显式地从此类进行派生。它支持多路广播委托，并拥有一个带有链接的委托列表，在调用多路广播委托时，系统将按照调用列表中的委托出现顺序来同步调用这些委托。&lt;/p&gt;&lt;p&gt;MulticastDelegate具有两个常用属性：Method、Target。其中Method 用于获取委托所表示的方法Target 用于获取当前调用的类实例。&lt;/p&gt;&lt;p&gt;MulticastDelegate有以下几个常用方法：&lt;/p&gt;&lt;table class="memberListTable" style="font-size: 12px; width: 600px;" border="0"&gt;&lt;colgroup&gt; &lt;col width="30%" /&gt; &lt;col width="70%" /&gt; &lt;/colgroup&gt;&lt;tbody&gt;&lt;tr&gt;&lt;th&gt;&lt;span style="font-size: 12px;"&gt;方法名称&lt;/span&gt;&lt;/th&gt;&lt;th&gt;&lt;span style="font-size: 12px;"&gt;说明&lt;/span&gt;&lt;/th&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&amp;nbsp;Clone&lt;/td&gt;&lt;td&gt;&lt;span&gt;&amp;nbsp; 创建委托的浅表副本。 &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&amp;nbsp;GetInvocationList&lt;/td&gt;&lt;td&gt;&amp;nbsp; 按照调用顺序返回此多路广播委托的调用列表。&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&amp;nbsp;GetMethodImpl&lt;/td&gt;&lt;td&gt;&amp;nbsp;&lt;span&gt; 返回由当前的 MulticastDelegate 表示的静态方法。 &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&amp;nbsp;GetObjectData&lt;/td&gt;&lt;td&gt;&amp;nbsp; 用序列化该实例所需的所有数据填充 &lt;span&gt;SerializationInfo&lt;/span&gt; 对象。&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&amp;nbsp;MemberwiseClone&lt;/td&gt;&lt;td&gt;&amp;nbsp; 创建当前 &lt;span&gt;Object&lt;/span&gt; 的浅表副本。&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&amp;nbsp;RemoveImpl&lt;/td&gt;&lt;td&gt;&amp;nbsp; 调用列表中移除与指定委托相等的元素&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;MulticastDelegate与Delegate给委托对象建立了强大的支持，下面向各位详细介绍一下委托的使用方式。&lt;/p&gt;&lt;p&gt;&lt;a name="a3"&gt;&lt;/a&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;三、委托使用方式&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.1 简单的委托&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;当建立委托对象时，委托的参数类型必须与委托方法相对应。只要向建立委托对象的构造函数中输入方法名称example.Method，委托就会直接绑定此方法。使用myDelegate.Invoke（string message），就能显式调用委托方法。但在实际的操作中，我们无须用到 Invoke 方法，而只要直接使用myDelegate(string message)，就能调用委托方法。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Example&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 MessageBox.Show(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             Example example=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Example();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             MyDelegate myDelegate=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(example.Method);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             myDelegate(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello World&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.2 带返回值的委托&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;当建立委托对象时，委托的返回值必须与委托方法相对应。使用下面的例子，方法将返回 &amp;ldquo;Hello Leslie&amp;rdquo; 。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Example&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Method(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             Example example=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Example();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;绑定委托方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             MyDelegate myDelegate=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(example.Method);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;调用委托，获取返回值&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = myDelegate(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.3 多路广播委托&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在第二节前曾经提过，委托类继承于MulticastDelegate，这使委托对象支持多路广播，即委托对象可以绑定多个方法。当输入参数后，每个方法会按顺序进行迭代处理，并返回最后一个方法的计算结果。&lt;br /&gt;下面的例子中，Price 类中有两个计算方法，Ordinary 按普通的9.5折计算，Favourable 按优惠价 8.5 折计算。委托同时绑定了这两个方法，在输入参数100以后，Ordinary、Favourable这两个方法将按顺序迭代执行下去，最后返回 Favourable 方法的计算结果 85。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; message);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Price&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; Ordinary(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; price)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; price1 = &lt;span style="color: #800080;"&gt;0.95&lt;/span&gt; * price;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Ordinary Price : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+price1);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; price1;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; Favourable(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; price)&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; price1 = &lt;span style="color: #800080;"&gt;0.85&lt;/span&gt; * price;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Favourable Price : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + price1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; price1;&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                 Price price = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Price();&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                 &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;绑定Ordinary方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                 MyDelegate myDelegate = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(price.Ordinary);&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                 &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;绑定Favourable方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;                 myDelegate += &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(price.Favourable);&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;                 &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;调用委托&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Current Price : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + myDelegate(&lt;span style="color: #800080;"&gt;100&lt;/span&gt;));&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;                 Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031111335897.jpg" alt="" width="582" height="89" /&gt;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;&lt;strong&gt;3.4 浅谈Observer模式&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;回顾一下简单的 Observer 模式，它使用一对多的方式，可以让多个观察者同时关注同一个事物，并作出不同的响应。&lt;br /&gt;例如下面的例子，Manager的底薪为基本工资的1.5倍，Assistant的底薪为基本工资的1.2倍。WageManager类的RegisterWorker方法与RemoveWorker方法可以用于注册和注销观察者，最后执行Execute方法可以对多个已注册的观察者同时输入参数。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;div style="border: 1px solid #808080; background-color: white; width：80%;padding-top: 20px; padding-bottom: 20px;"&gt;&lt;img style="display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2012/64989/2012031218131747.jpg" alt="" width="772" height="175" /&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; WageManager&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         IList&amp;lt;Worker&amp;gt; workerList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Worker&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; RegisterWorker(Worker worker)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             workerList.Add(worker);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; RemoveWorker(Worker worker)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             workerList.Remove(worker);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Excute(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; basicWages)&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (workerList.Count != &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; worker &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; workerList)&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                     worker.GetWages(basicWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             WageManager wageManager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; WageManager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//注册观察者&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             wageManager.RegisterWorker(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Manager());&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             wageManager.RegisterWorker(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Assistant());&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//同时输入底薪3000元，分别进行计算&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             wageManager.Excute(&lt;span style="color: #800080;"&gt;3000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;abstract&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Worker&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;abstract&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; GetWages(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; basicWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Manager:Worker&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;Manager实际工资为底薪1.5倍&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;override&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; GetWages(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; basicWages)&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; totalWages = &lt;span style="color: #800080;"&gt;1.5&lt;/span&gt; * basicWages;&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Manager's wages is &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + totalWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; totalWages;&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Assistant : Worker&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;Assistant实际工资为底薪的1.2倍&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;override&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; GetWages(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; basicWages)&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; totalWages = &lt;span style="color: #800080;"&gt;1.2&lt;/span&gt; * basicWages;&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Assistant's wages is &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + totalWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; totalWages;&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031218231193.jpg" alt="" width="576" height="88" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;开发 Observer 模式时借助委托，可以进一步简化开发的过程。由于委托对象支持多路广播，所以可以把Worker类省略。在WageManager类中建立了一个委托对象wageHandler，通过Attach与Detach方法可以分别加入或取消委托。如果观察者想对事物进行监测，只需要加入一个委托对象即可。记得在第二节曾经提过，委托的GetInvodationList方法能获取多路广播委托列表，在Execute方法中，就是通过去多路广播委托列表去判断所绑定的委托数量是否为0。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; Handler(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; basicWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Manager&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; GetWages(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; basicWages)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; totalWages=&lt;span style="color: #800080;"&gt;1.5&lt;/span&gt; * basicWages;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                  Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Manager's wages is : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + totalWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; totalWages;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Assistant&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; GetWages(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; basicWages)&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; totalWages = &lt;span style="color: #800080;"&gt;1.2&lt;/span&gt; * basicWages;&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                  Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Assistant's wages is : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + totalWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; totalWages;&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; WageManager&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; Handler wageHandler;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;加入观察者&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Attach(Handler wageHandler1)&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                  wageHandler += wageHandler1;&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;删除观察者&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Detach(Handler wageHandler1)&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                  wageHandler -= wageHandler1;&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;通过GetInvodationList方法获取多路广播委托列表，如果观察者数量大于0即执行方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Execute(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; basicWages)&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (wageHandler!=&lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt;(wageHandler.GetInvocationList().Count() != &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;                         wageHandler(basicWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;                  WageManager wageManager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; WageManager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;                  &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;加入Manager观察者&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;                  Manager manager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Manager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;                  Handler managerHandler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Handler(manager.GetWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;                  wageManager.Attach(managerHandler);&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;                  &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;加入Assistant观察者&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;                  Assistant assistant = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Assistant();&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;                  Handler assistantHandler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Handler(assistant.GetWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt;                  wageManager.Attach(assistantHandler);&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;                  &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;同时加入底薪3000元，分别进行计算&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;                  wageManager.Execute(&lt;span style="color: #800080;"&gt;3000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt;                  Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt;          }&lt;/div&gt;&lt;p&gt;最后运行结果与上面的例子相同。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.5 委托的协变与逆变&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在 Framework 2.0 出现之前，委托协变这个概念还没有出现。此时因为委托是安全类型，它们不遵守继承的基础规则。即会这下面的情况：Manager 虽然是 Worker 的子类，但 GetWorkerHander 委托不能直接绑定 GetManager 方法，因为在委托当中它们的返回值 Manager 与 Worker 被视为完全无关的两个类型。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Worker&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;      {.......}&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Manager:Worker&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;      {.......}&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; Worker GetWorkerHandler(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; Manager GetManagerHandler(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; Worker GetWorker(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id)&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;              Worker worker = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Worker();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;              ..............&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; worker;&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; Manager GetManager(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id)&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;              Manager manager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Manager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;              ..............&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; manager;&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;              GetWorkerHandler workerHandler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; GetWorkerHandler(GetWorker);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; worker=workerHandler(&lt;span style="color: #800080;"&gt;1&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;              GetManagerHandler managerHandler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; GetManagerHandler(GetManager);&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; manager = managerHandler(&lt;span style="color: #800080;"&gt;2&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;              Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;      }&lt;/div&gt;&lt;p&gt;自从Framework 2.0 面试以后，委托协变的概念就应运而生，此时委托可以按照传统的继承规则进行转换。即 GetWorkerHandler 委托可以直接绑定 GetManager 方法。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;     public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Worker&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;      {.......}&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Manager:Worker&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;      {.......}&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; Worker GetWorkerHandler(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//在 Framework2.0 以上，委托 GetWorkerHandler 可绑定 GetWorker 与 GetManager 两个方法&lt;/span&gt;&lt;br style="color: #0000ff;" /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; Worker GetWorker(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id)&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;              Worker worker = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Worker();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; worker;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; Manager GetManager(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id)&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;              Manager manager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Manager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; manager;&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             GetWorkerHandler workerHandler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; GetWorkerHandler(GetWorker);&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             Worker worker=workerHandler(&lt;span style="color: #800080;"&gt;1&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             GetWorkerHandler managerHandler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; GetWorkerHandler(GetManager);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             Manager manager = managerHandler(&lt;span style="color: #800080;"&gt;2&lt;/span&gt;) &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt; Manager;&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;      }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;委托逆变，是指委托方法的参数同样可以接收 &amp;ldquo;继承&amp;rdquo; 这个传统规则。像下面的例子，以 object 为参数的委托，可以接受任何 object 子类的对象作为参数。最后可以在处理方法中使用 is 对输入数据的类型进行判断，分别处理对不同的类型的对象。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Handler(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; obj);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; GetMessage(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; message)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (message &lt;span style="color: #0000ff;"&gt;is&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;His name is : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + message.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if &lt;/span&gt;(message &lt;span style="color: #0000ff;"&gt;is&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;His age is : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + message.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             Handler handler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Handler(GetMessage);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             handler(&lt;span style="color: #800080;"&gt;29&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;    }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031319523360.jpg" alt="" width="572" height="101" /&gt;&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;em&gt;注意&lt;/em&gt;：&lt;em&gt;委托与其绑定方法的参数必须一至，即当 Handler 所输入的参数为 object 类型，其绑定方法 GetMessage 的参数也必须为 object 。否则，即使绑定方法的参数为 object 的子类，系统也无法辨认。&lt;br /&gt;&lt;/em&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;br /&gt;&lt;strong&gt;3.6 泛型委托&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;委托逆变虽然实用，但如果都以 object 作为参数，则需要每次都对参数进行类型的判断，这不禁令人感到厌烦。&lt;br /&gt;为此，泛型委托应运而生，泛型委托有着委托逆变的优点，同时利用泛型的特性，可以使一个委托绑定多个不同类型参数的方法，而且在方法中不需要使用 is 进行类型判断，从而简化了代码。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Handler&amp;lt;T&amp;gt;(T obj);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; GetWorkerWages(Worker worker)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Worker's total wages is &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + worker.Wages);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; GetManagerWages(Manager manager)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Manager's total wages is &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+manager.Wages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             Handler&amp;lt;Worker&amp;gt; workerHander = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Handler&amp;lt;Worker&amp;gt;(GetWorkerWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             Worker worker = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Worker();&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             worker.Wages = &lt;span style="color: #800080;"&gt;3000&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             workerHander(worker);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             Handler&amp;lt;Manager&amp;gt; managerHandler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Handler&amp;lt;Manager&amp;gt;(GetManagerWages);&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             Manager manager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Manager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             manager.Wages = &lt;span style="color: #800080;"&gt;4500&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             managerHandler(manager);&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031418544941.jpg" alt="" width="591" height="89" /&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a name="a4"&gt;&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;四、深入解析事件&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.1 事件的由来&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在介绍事件之前大家可以先看看下面的例子， PriceManager 负责对商品价格进行处理，当委托对象 GetPriceHandler 的返回值大于100元，按8.8折计算，低于100元按原价计算。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; PriceHandler();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; PriceManager&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; PriceHandler GetPriceHandler;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;委托处理，当价格高于100元按8.8折计算，其他按原价计算&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; GetPrice()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (GetPriceHandler.GetInvocationList().Count() &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (GetPriceHandler() &amp;gt; &lt;span style="color: #800080;"&gt;100&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; GetPriceHandler()*&lt;span style="color: #800080;"&gt;0.88&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; GetPriceHandler();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; -&lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             PriceManager priceManager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; PriceManager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;调用priceManager的GetPrice方法获取价格&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt; &lt;span style="color: #008000;"&gt;            //&lt;/span&gt;&lt;span style="color: #008000;"&gt;直接调用委托的Invoke获取价格，两者进行比较&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             priceManager.GetPriceHandler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; PriceHandler(ComputerPrice);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;GetPrice\n  Computer's price is {0}!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;                 priceManager.GetPrice()));&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Invoke\n  Computer's price is {0}!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;                 priceManager.GetPriceHandler.Invoke()));&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             Console.WriteLine();&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;             priceManager.GetPriceHandler = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; PriceHandler(BookPrice);&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;GetPrice\n  Book's price is {0}!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                 priceManager.GetPrice()));&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Invoke\n  Book's price is {0}!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; ,&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;                 priceManager.GetPriceHandler.Invoke()));&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;书本价格为98元&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; BookPrice()&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800080;"&gt;98.0&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算机价格为8800元&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; ComputerPrice()&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800080;"&gt;8800.0&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031421515670.jpg" alt="" width="567" height="166" /&gt;&lt;/p&gt;&lt;p&gt;观察运行的结果，如果把委托对象 GetPriceHandler 设置为 public ，外界可以直接调用 GetPriceHandler.Invoke 获取运行结果而移除了 GetPrice 方法的处理，这正是开发人员最不想看到的。&lt;br /&gt;为了保证系统的封装性，开发往往需要把委托对象 GetPriceHandler 设置为 private, 再分别加入 AddHandler，RemoveHandler 方法对 GetPriceHandler 委托对象进行封装。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; PriceHandler();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; PriceManager&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; PriceHandler GetPriceHandler;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;委托处理，当价格高于100元按8.8折计算，其他按原价计算&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; GetPrice()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (GetPriceHandler!=&lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (GetPriceHandler() &amp;gt; &lt;span style="color: #800080;"&gt;100&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; GetPriceHandler()*&lt;span style="color: #800080;"&gt;0.88&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; GetPriceHandler();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; -&lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AddHandler(PriceHandler handler)&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             GetPriceHandler += handler;&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; RemoveHandler(PriceHandler handler)&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             GetPriceHandler -= handler;&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;     ................&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;     ................&lt;/div&gt;&lt;p&gt;为了保存封装性，很多操作都需要加入AddHandler、RemoveHandler 这些相似的方法代码，这未免令人感到厌烦。&lt;br /&gt;为了进一步简化操作，事件这个概念应运而生。&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.2 事件的定义&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;事件（event）可被视作为一种特别的委托，它为委托对象隐式地建立起add_XXX、remove_XXX 两个方法，用作注册与注销事件的处理方法。而且事件对应的变量成员将会被视为 private 变量，外界无法超越事件所在对象直接访问它们，这使事件具备良好的封装性，而且免除了add_XXX、remove_XXX等繁琐的代码。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; EventTest&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; MyDelegate();&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;event&lt;/span&gt; MyDelegate MyEvent;&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;观察事件的编译过程可知，在编译的时候，系统为 MyEvent 事件自动建立add_MyEvent、remove_MyEvent 方法。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031423160285.jpg" alt="" width="557" height="179" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.3 事件的使用方式&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;事件能通过+=和-=两个方式注册或者注销对其处理的方法，使用+=与-=操作符的时候，系统会自动调用对应的 add_XXX、remove_XXX 进行处理。&lt;br /&gt;值得留意，在PersonManager类的Execute方法中，如果 MyEvent 绑定的处理方法不为空，即可使用MyEvent（string）引发事件。但如果在外界的 main 方法中直接使用 personManager.MyEvent (string) 来引发事件，系统将引发错误报告。这正是因为事件具备了良好的封装性，使外界不能超越事件所在的对象访问其变量成员。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;em&gt;注意&lt;/em&gt;：&lt;em&gt;在事件所处的对象之外，事件只能出现在+=，-=的左方。&lt;/em&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;此时，开发人员无须手动添加 add_XXX、remove_XXX 的方法，就可实现与4.1例子中的相同功能，实现了良好的封装。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; PersonManager&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;event&lt;/span&gt; MyDelegate MyEvent;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;执行事件&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Execute(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (MyEvent != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                 MyEvent(name);&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             PersonManager personManager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; PersonManager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;绑定事件处理方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             personManager.MyEvent += &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(GetName);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             personManager.Execute(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; GetName(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;My name is &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + name);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.4 事件处理方法的绑定&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在绑定事件处理方法的时候，事件出现在+=、-= 操作符的左边，对应的委托对象出现在+=、-= 操作符的右边。对应以上例子，事件提供了更简单的绑定方式，只需要在+=、-= 操作符的右方写上方法名称，系统就能自动辩认。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; PersonManager&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;event&lt;/span&gt; MyDelegate MyEvent;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         .........&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             PersonManager personManager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; PersonManager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;绑定事件处理方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             personManager.MyEvent += GetName;&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             .............&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; GetName(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         {.........}&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;    }&lt;/div&gt;&lt;p&gt;如果觉得编写 GetName 方法过于麻烦，你还可以使用匿名方法绑定事件的处理。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; PersonManager&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;event&lt;/span&gt; MyDelegate MyEvent;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;执行事件&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Execute(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (MyEvent != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                 MyEvent(name);&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             PersonManager personManager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; PersonManager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用匿名方法绑定事件的处理&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             personManager.MyEvent += &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt;(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name){&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;My name is &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+name);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             };&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             personManager.Execute(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.5 C#控件中的事件&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在C#控件中存在多个的事件，像Click、TextChanged、SelectIndexChanged 等等，很多都是通过 EventHandler 委托绑定事件的处理方法的，EventHandler 可说是C#控件中最常见的委托 。&lt;/p&gt;&lt;p&gt;public delegate void EventHandler (Object sender, EventArgs e)&lt;/p&gt;&lt;p&gt;EventHandler 委托并无返回值，sender 代表引发事件的控件对象，e 代表&lt;span id="mt2" class="sentence SentenceHover" data-guid="08ae9ff8ba93b0b269b5f865da35e7c5" data-source="The type of the event data generated by the event."&gt;由该事件生成的数据&lt;/span&gt; 。在ASP.NET中可以直接通过btn.Click+=new EventHandler(btn_onclick) 的方式为控件绑定处理方法。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;html &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;xmlns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="http://www.w3.org/1999/xhtml"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;head &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;script &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;type&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="text/C#"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        protected &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; Page_Load(object sender, EventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            btn.Click &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;+=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; EventHandler(btn_onclick);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        public &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; btn_onclick(object obj, EventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            Button btn &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; (Button)obj;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            Response.Write(btn.Text);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;    &amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;script&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;head&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;form &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;id&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="form1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Button &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="btn"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; Text&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Button"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;form&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;html&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;/div&gt;&lt;p&gt;更多时候，只需要在页面使用 OnClick=&amp;ldquo;btn_onclick" 方法，在编译的时候系统就会自动对事件处理方法进行绑定。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;html &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;xmlns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="http://www.w3.org/1999/xhtml"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;head &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;script &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;type&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="text/C#"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        public &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; btn_onclick(object obj, EventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            Button btn &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; (Button)obj;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            Response.Write(btn.Text);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;    &amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;script&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;head&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;form &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;id&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="form1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Button &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="btn"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; Text&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Button"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; OnClick&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="btn_onclick"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;form&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;html&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;EventHandler 只是 EventHandler&amp;lt;TEventArgs&amp;gt; 泛型委托的一个简单例子。事实上，大家可以利用 EventHandler&amp;lt;TEventArgs&amp;gt; 构造出所需要的委托。&lt;/p&gt;&lt;p&gt;public delegate void EventHandler&amp;lt;TEventArgs&amp;gt; (Object sender, TEventArgs e)&lt;/p&gt;&lt;p&gt;在EventHandler&amp;lt;TEventArgs&amp;gt;中，sender代表事件源，e 代表派生自EventArgs类的事件参数。开发人员可以建立派生自EventArgs的类，从中加入需要使用到的事件参数，然后建立 EventHandler&amp;lt;TEventArgs&amp;gt; 委托。&lt;/p&gt;&lt;p&gt;下面的例子中，先建立一个派生自EventArgs的类MyEventArgs作为事件参数，然后在EventManager中建立事件myEvent , 通过 Execute 方法可以激发事件。最后在测试中绑定 myEvent 的处理方法 ShowMessage，在ShowMessage显示myEventArgs 的事件参数 Message。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; MyEventArgs : EventArgs&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; args;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; MyEventArgs(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             args = message;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Message&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt; { &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; args; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt; { args = value; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; EventManager&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;event&lt;/span&gt; EventHandler&amp;lt;MyEventArgs&amp;gt; myEvent;&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Execute(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message)&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (myEvent != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                 myEvent(&lt;span style="color: #0000ff;"&gt;this&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyEventArgs(message));&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             EventManager eventManager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; EventManager();&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;             eventManager.myEvent += &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; EventHandler&amp;lt;MyEventArgs&amp;gt;(ShowMessage);&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             eventManager.Execute(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;How are you!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowMessage(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; obj,MyEventArgs e)&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;             Console.WriteLine(e.Message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031522535977.jpg" alt="" width="565" height="112" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.6 为用户控件建立事件&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在ASP.NET开发中，页面往往会出现很多类似的控件与代码，开发人员可以通过用户控件来避免重复的代码。但往往同一个用户控件，在不同的页面中需要有不同的响应。此时为用户控件建立事件，便可轻松地解决此问题。&lt;br /&gt;下面例子中，在用户控件 MyControl 中建立存在一个GridView控件，GridView 控件通过 GetPersonList 方法获取数据源。在用户控件中还定义了 RowCommand 事件，在 GridView 的 GridView_RowCommand 方法中激发此事件。这样，在页面使用此控件时，开发人员就可以定义不同的方法处理 RowCommand 事件。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; public class Person&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     public int ID&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;     public string Name&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;     { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;     public int Age&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;     { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="color: #008000;"&gt;&amp;lt;!--&lt;/span&gt;&lt;span style="color: #008000;"&gt;    用户控件     &lt;/span&gt;&lt;span style="color: #008000;"&gt;--&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="background-color: #ffff00; color: #000000;"&gt;&amp;lt;%&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;@ Control Language&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;C#&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; AutoEventWireup&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;true&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; CodeFile&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;MyControl.ascx.cs&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; Inherits&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;MyControl&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt; &lt;span style="background-color: #ffff00; color: #000000;"&gt;%&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;script &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;type&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="text/C#"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    protected &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; Page_Load(object sender, EventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        GridView1.DataSource &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; GetPersonList();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        GridView1.DataBind();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #008000;"&gt;    //&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;绑定数据源&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    protected IList&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;Person&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; GetPersonList()&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        IList&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;Person&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; list &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; List&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;Person&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        Person person1 &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; Person();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        person1.ID &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;1&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        person1.Name &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;Leslie&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        person1.Age &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;29&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        list.Add(person1);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        ...........&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;        return&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; list;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    public event GridViewCommandEventHandler RowCommand;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    protected &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; GridView1_RowCommand(object sender, GridViewCommandEventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;        if&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; (RowCommand &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;!=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            RowCommand(sender, e);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;    }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;script&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;    &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:GridView &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="GridView1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; AutoGenerateColumns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="False"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt; &lt;span style="color: #ff0000;"&gt;        onrowcommand&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="GridView1_RowCommand"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;Columns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:BoundField &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;DataField&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="ID"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; HeaderText&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="ID"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:BoundField &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;DataField&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Name"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; HeaderText&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Name"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:BoundField &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;DataField&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Age"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; HeaderText&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Age"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:ButtonField &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;CommandName&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Get"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; Text&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Select"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;Columns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;    &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:GridView&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt; &lt;span style="color: #008000;"&gt;&amp;lt;!--&lt;/span&gt;&lt;span style="color: #008000;"&gt;     页面代码       &lt;/span&gt;&lt;span style="color: #008000;"&gt;--&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt; &lt;span style="background-color: #ffff00; color: #000000;"&gt;&amp;lt;%&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;@ Page Language&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;C#&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; AutoEventWireup&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;true&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; CodeFile&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;Default2.aspx.cs&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; Inherits&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;Default2&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt; &lt;span style="background-color: #ffff00; color: #000000;"&gt;%&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt; &lt;span style="background-color: #ffff00; color: #000000;"&gt;&amp;lt;%&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;@ Register Src&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;~/MyControl.ascx&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; TagPrefix&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;ascx&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; TagName&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;myControl&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt; &lt;span style="background-color: #ffff00; color: #000000;"&gt;%&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;!&lt;/span&gt;&lt;span style="color: #ff00ff;"&gt;DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;html &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;xmlns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="http://www.w3.org/1999/xhtml"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;head &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;script &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;type&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="text/C#"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;       protected &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; myControl_RowCommand(object sender, GridViewCommandEventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;       {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;          if&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; (e.CommandName &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;==&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;Get&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;65&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;          {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;66&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            GridView gridView&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;(GridView)sender;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;67&lt;/span&gt;             &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;int&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; index &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;int&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;.Parse(e.CommandArgument.ToString());&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;68&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            label.Text&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;gridView.Rows[index].Cells[&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;1&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;].Text;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;69&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;          }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;70&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;       }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;71&lt;/span&gt;    &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;script&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;72&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;head&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;73&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;74&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;form &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;id&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="form1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;75&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;76&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;ascx:myControl &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="myControl"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; OnRowCommand&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="myControl_RowCommand"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;ascx:myControl&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;77&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;78&lt;/span&gt;         Select Name ： &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="label"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;79&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;80&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;form&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;81&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;82&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;html&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031611310387.jpg" alt="" width="459" height="210" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;使用控件已有的事件固然简单，但它限制了传送的参数类型，使开发人员无法传送额外的自定义参数。在结构比较复杂的用户控件中，使用已有的控件事件，显然不够方便，此时，您可以考虑为用户控件建立自定义事件。&lt;br /&gt;首先用户控件中包含订单信息与订单明细列表，首先定义一个事件参数 MyEventArgs，里面包含了订单信息与一个 OrderItem 数组。然后建立用户控件的委托MyDelegate 与对应的事件 MyEvent，在 Button 的 Click 事件中激发 MyEvent 自定义事件。这样在页面处理方法 myControl_Click 中就可以通过事件参数 MyEventArgs 获取用户控件中的属性，计算订单的总体价格。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;  1&lt;/span&gt; &lt;span style="color: #008000;"&gt;&amp;lt;!--&lt;/span&gt;&lt;span style="color: #008000;"&gt;   基础类    &lt;/span&gt;&lt;span style="color: #008000;"&gt;--&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;  2&lt;/span&gt;  public class OrderItem&lt;br /&gt;&lt;span style="color: #008080;"&gt;  3&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt;  4&lt;/span&gt;      public OrderItem(string id,string goods,double price,int count)&lt;br /&gt;&lt;span style="color: #008080;"&gt;  5&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;  6&lt;/span&gt;          this.OrderItemID = id;     &lt;span style="color: #008000;"&gt;//明细单ID&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;  7&lt;/span&gt;          this.Goods = goods;        &lt;span style="color: #008000;"&gt;//商品名称&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;  8&lt;/span&gt;          this.Price = price;        &lt;span style="color: #008000;"&gt;//商品单价&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;  9&lt;/span&gt;          this.Count = count;        &lt;span style="color: #008000;"&gt;//商品数量&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 10&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 11&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 12&lt;/span&gt;      public string OrderItemID&lt;br /&gt;&lt;span style="color: #008080;"&gt; 13&lt;/span&gt;      { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 14&lt;/span&gt;      public string Goods&lt;br /&gt;&lt;span style="color: #008080;"&gt; 15&lt;/span&gt;      { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 16&lt;/span&gt;      public double Price&lt;br /&gt;&lt;span style="color: #008080;"&gt; 17&lt;/span&gt;      { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 18&lt;/span&gt;      public int Count&lt;br /&gt;&lt;span style="color: #008080;"&gt; 19&lt;/span&gt;      { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 20&lt;/span&gt;  }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 21&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 22&lt;/span&gt;  &lt;span style="color: #008000;"&gt;/// 事件参数&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 23&lt;/span&gt;  public class MyEventArgs：EventArgs&lt;br /&gt;&lt;span style="color: #008080;"&gt; 24&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 25&lt;/span&gt;      public MyEventArgs(string name,string address,string tel,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 26&lt;/span&gt;                         string orderCode,IList&lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;OrderItem&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt; orderItemList)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 27&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 28&lt;/span&gt;          Name = name;    &lt;span style="color: #008000;"&gt;//买家姓名&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 29&lt;/span&gt;          Address = address;    &lt;span style="color: #008000;"&gt;//买家地址&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 30&lt;/span&gt;          Tel = tel;   &lt;span style="color: #008000;"&gt; //买家电话&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 31&lt;/span&gt;          OrderCode = orderCode;    &lt;span style="color: #008000;"&gt; //订单号码&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 32&lt;/span&gt;          OrderItemList = orderItemList;    &lt;span style="color: #008000;"&gt; //订单明细&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 33&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 34&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 35&lt;/span&gt;      public string Name&lt;br /&gt;&lt;span style="color: #008080;"&gt; 36&lt;/span&gt;      { get;set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 37&lt;/span&gt;      public string Address&lt;br /&gt;&lt;span style="color: #008080;"&gt; 38&lt;/span&gt;      { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 39&lt;/span&gt;      public string Tel&lt;br /&gt;&lt;span style="color: #008080;"&gt; 40&lt;/span&gt;      { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 41&lt;/span&gt;      public string OrderCode&lt;br /&gt;&lt;span style="color: #008080;"&gt; 42&lt;/span&gt;      { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 43&lt;/span&gt;      public IList&lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;OrderItem&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt; OrderItemList&lt;br /&gt;&lt;span style="color: #008080;"&gt; 44&lt;/span&gt;      { get; set; }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 45&lt;/span&gt;  }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 46&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 47&lt;/span&gt;  &lt;span style="color: #008000;"&gt;&amp;lt;!--&lt;/span&gt;&lt;span style="color: #008000;"&gt;     用户控件      &lt;/span&gt;&lt;span style="color: #008000;"&gt;--&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 48&lt;/span&gt;  &lt;span style="background-color: #ffff00; color: #000000;"&gt;&amp;lt;%&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;@ Control Language&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;C#&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; AutoEventWireup&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;true&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; CodeFile&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;MyControl.ascx.cs&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; Inherits&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;MyControl&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt; &lt;span style="background-color: #ffff00; color: #000000;"&gt;%&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 49&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;script &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;type&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="text/C#"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 50&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     protected &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; Page_Load(object sender, EventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 51&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 52&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;         GridView1.DataSource &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; GetList();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 53&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;         GridView1.DataBind();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 54&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 55&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt; &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 56&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #008000;"&gt;     //&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;模拟数据源&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 57&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     protected IList&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;OrderItem&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; GetList()&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 58&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 59&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;         IList&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;OrderItem&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; list &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; List&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;OrderItem&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 60&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;         OrderItem orderItem &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; OrderItem(&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;1&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;, &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;Asus N75S&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;, &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;8800&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;, &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;2&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 61&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;         list.Add(orderItem);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 62&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;         ..........&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 63&lt;/span&gt;          &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;return&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; list;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 64&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 65&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt; &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 66&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #008000;"&gt;     //&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;自定义委托  &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 67&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     public delegate &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; MyDelegate(object sender,MyEventArgs myEventArgs);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 68&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #008000;"&gt;     //&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;自定义事件 &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 69&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     public event MyDelegate MyEvent;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 70&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 71&lt;/span&gt;      &lt;span style="background-color: #f5f5f5; color: #008000;"&gt;//&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;按下Button时激发自定义事件&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 72&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     protected &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; btn_click(object sender, EventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 73&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 74&lt;/span&gt;          &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;if&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; (MyEvent &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;!=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 75&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;         {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 76&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;             MyEventArgs myEventArgs &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; MyEventArgs(labelName.Text, labelAddress.Text, labelTel.Text&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 77&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;                 , labelOrderCode.Text, GetList());&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 78&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;             MyEvent(&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;this&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;,myEventArgs);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 79&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;         }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 80&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;     }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 81&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;script&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 82&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 83&lt;/span&gt;     Name : &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="labelName"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;Leslie&lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 84&lt;/span&gt;     Address : &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="labelAddress"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;ZhongShan University 2A 501&lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 85&lt;/span&gt;     Tel : &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="labelTel"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;13660123456&lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 86&lt;/span&gt;     Order Code : &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="labelOrderCode"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;A12012031223B0030&lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 87&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:GridView &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="GridView1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; AutoGenerateColumns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="False"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; CellPadding&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="5"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 88&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;Columns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 89&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:BoundField &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;DataField&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="OrderItemID"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; HeaderText&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="ID"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 90&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:BoundField &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;DataField&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Goods"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; HeaderText&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Goods"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 91&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:BoundField &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;DataField&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Price"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; HeaderText&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Price"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 92&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:BoundField &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;DataField&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Count"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; HeaderText&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Count"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 93&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;Columns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 94&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:GridView&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 95&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 96&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Button &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="btn"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; Text&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Account"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; OnClick&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="btn_click"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 97&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 98&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 99&lt;/span&gt;  &lt;span style="color: #008000;"&gt;&amp;lt;!--&lt;/span&gt;&lt;span style="color: #008000;"&gt;    页面处理      &lt;/span&gt;&lt;span style="color: #008000;"&gt;--&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;100&lt;/span&gt;  &lt;span style="background-color: #ffff00; color: #000000;"&gt;&amp;lt;%&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;@ Page Language&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;C#&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; AutoEventWireup&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;true&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; CodeFile&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;Default2.aspx.cs&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; Inherits&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;Default2&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt; &lt;span style="background-color: #ffff00; color: #000000;"&gt;%&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;101&lt;/span&gt;  &lt;span style="background-color: #ffff00; color: #000000;"&gt;&amp;lt;%&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;@ Register Src&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;~/MyControl.ascx&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; TagPrefix&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;ascx&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; TagName&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;myControl&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #800000;"&gt;"&lt;/span&gt; &lt;span style="background-color: #ffff00; color: #000000;"&gt;%&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;102&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;!&lt;/span&gt;&lt;span style="color: #ff00ff;"&gt;DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;103&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;104&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;html &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;xmlns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="http://www.w3.org/1999/xhtml"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;105&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;head &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;106&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;107&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;script &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;type&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="text/C#"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;108&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #008000;"&gt;        //&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;在页面定义用户控件MyEvent事件的处理方法&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;109&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        protected &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; myControl_Click(object sender,MyEventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;110&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;111&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #008000;"&gt;            //&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;计算订单总体价格&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;112&lt;/span&gt;             &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;double&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; totalPrice&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;0&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;113&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            IList&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;OrderItem&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; list&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;e.OrderItemList;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;114&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            foreach(OrderItem item &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;in&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; list)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;115&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;                totalPrice&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;+=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;item.Price&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;*&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;item.Count;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;116&lt;/span&gt;             &lt;span style="background-color: #f5f5f5; color: #008000;"&gt;//&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;展示订单号&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #008000;"&gt;及总体费用&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;117&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            labelOrderCode.Text &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; e.OrderCode;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;118&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            labelTotalPrice.Text &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; totalPrice.ToString();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;119&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;120&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;script&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;121&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;head&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;122&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;123&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;form &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;id&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="form1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;124&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;125&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;ascx:myControl &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="myControl"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; OnMyEvent&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="myControl_Click"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;ascx:myControl&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;126&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;127&lt;/span&gt;          OrderCode ： &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="labelOrderCode"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;128&lt;/span&gt;          TotalPrice :  &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="labelTotalPrice"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Label&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;129&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;130&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;form&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;131&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;132&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;html&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012031613234461.jpg" alt="" width="528" height="327" /&gt;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;若对自定义事件不太熟悉的朋友很多时候会使用 UserControl.FindControl 的方式获取用户控件中的属性，但当你深入了解自定义事件的开发过程以后，就能有效简化开发的过程。&lt;/p&gt;&lt;p&gt;&lt;a name="a5"&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;五、Lambda 表达式&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.1 Lambda 的意义&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在Framework 2.0 以前，声明委托的唯一方法是通过方法命名，从Framework 2.0 起，系统开始支持匿名方法。&lt;br /&gt;通过匿名方法&lt;span id="mt12" class="sentence" data-guid="54e6a5891e43dccd90395669e62c9ab1" data-source="By using anonymous methods, you reduce the coding overhead in instantiating delegates because you do not have to create a separate method."&gt;，可以直接把一段代码绑定给事件，因此减少了实例化委托所需的编码系统开销。&lt;br /&gt;&lt;/span&gt;而在 Framework 3.0 开始，&lt;span id="mt2" class="sentence" data-guid="b9090b2ae309b4860db3509db583dfe7" data-source="C# 2.0 introduced anonymous methods and in C# 3.0 and later, lambda expressions supersede anonymous methods as the preferred way to write inline code."&gt;Lambda 表达式开始逐渐取代了匿名方法，作为编写内联代码的首选方式。总体来说，Lambda 表达式的作用是为了使用更简单的方式来编写匿名方法，彻底简化委托的使用方式。&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.2 回顾匿名方法的使用&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;匿名方法的使用已经在4.4节简单介绍过，在此回顾一下。 &lt;br /&gt;使用下面的方式，可以通过匿名方法为Button的Click事件绑定处理方法。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;             Button btn = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Button();&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;             btn.Click+=&lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt;(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; obj,EventArgs e){&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;                 MessageBox.Show(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello World !&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;             };&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;总是使用 delegate（）{......} 的方式建立匿名方法，令人不禁感觉郁闷。于是从Framework 3.0 起， Lambda 表达式开始出现。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.3 简单介绍泛型委托&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在介绍 Lambda 表达式前，先介绍一下常用的几个泛型委托。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.3.1&amp;nbsp;泛型委托 Predicate&amp;lt;T&amp;gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;早在Framework 2.0 的时候，微软就为 List&amp;lt;T&amp;gt; 类添加了 Find、FindAll 、ForEach 等方法用作数据的查找。&lt;/p&gt;&lt;p&gt;public T Find ( Predicate&amp;lt;T&amp;gt; match）&lt;br /&gt;public List&amp;lt;T&amp;gt; FindAll（Predicate&amp;lt;T&amp;gt;&amp;nbsp; match）&lt;/p&gt;&lt;p&gt;在这些方法中存在一个Predicate &amp;lt;T&amp;gt; 表达式，它是一个返回bool的泛型委托，能接受一个任意类型的对象作为参数。&lt;/p&gt;&lt;p&gt;public delegate bool Predicate&amp;lt;T&amp;gt;（T obj）&lt;/p&gt;&lt;p&gt;在下面例子中，Predicate 委托绑定了参数为Person类的方法Match作为查询条件，然后使用 FindAll 方法查找到合适条件的 List&amp;lt;Person&amp;gt; 集合。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             List&amp;lt;Person&amp;gt; list = GetList();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;绑定查询条件&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Predicate&amp;lt;Person&amp;gt; predicate = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Predicate&amp;lt;Person&amp;gt;(Match);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             List&amp;lt;Person&amp;gt; result = list.FindAll(predicate);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             Console.WriteLine（&amp;ldquo;Person count is : &amp;rdquo; + result.Count);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;模拟源数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; List&amp;lt;Person&amp;gt; GetList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Person&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person(&lt;span style="color: #800080;"&gt;1&lt;/span&gt;,&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;span style="color: #800080;"&gt;29&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             personList.Add(person1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             ........&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;查询条件&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt; Match(Person person)&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; person.Age &amp;lt;= &lt;span style="color: #800080;"&gt;30&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Person&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Person(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id, &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name, &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; age)&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             ID = id;&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;             Name = name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             Age = age;&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; ID&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;         { &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;; &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Name&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;         { &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;; &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Age&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;         { &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;; &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.3.2 泛型委托 Action&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Action&amp;lt;T&amp;gt; 的使用方式与 Predicate&amp;lt;T&amp;gt; 相似，不同之处在于 Predicate&amp;lt;T&amp;gt; 返回值为 bool ,&amp;nbsp; Action&amp;lt;T&amp;gt; 的返回值为 void。&lt;br /&gt;Action 支持0~16个参数，可以按需求任意使用。&lt;/p&gt;&lt;p&gt;public delegate void Action（）&lt;br /&gt;public delegate void Action&amp;lt;T1&amp;gt;（T1 obj1）&lt;br /&gt;public delegate void Action&amp;lt;T1，T2&amp;gt; （T1 obj1, T2 obj2）&lt;br /&gt;public delegate void Action&amp;lt;T1，T2，T3&amp;gt; （T1 obj1, T2 obj2，T3 obj3）&lt;br /&gt;............&lt;br /&gt;public delegate void Action&amp;lt;T1，T2，T3，......，T16&amp;gt; （T1 obj1, T2 obj2，T3 obj3，......，T16 obj16）&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             Action&amp;lt;&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&amp;gt; action=ShowMessage;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             action(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello World&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             MessageBox.Show(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.3.3 泛型委托 Func&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;委托 Func 与 Action 相似，同样支持 0~16 个参数，不同之处在于Func 必须具有返回值&lt;/p&gt;&lt;p&gt;public delegate TResult Func&amp;lt;TResult&amp;gt;（）&lt;br /&gt;public delegate TResult Func&amp;lt;T1,TResult&amp;gt;（T1 obj1）&lt;br /&gt; public delegate TResult Func&amp;lt;T1,T2,TResult&amp;gt;（T1 obj1,T2 obj2）&lt;br /&gt;public delegate TResult Func&amp;lt;T1,T2,T3,TResult&amp;gt;（T1 obj1,T2 obj2,T3 obj3）&lt;br /&gt;............&lt;br /&gt;public delegate TResult Func&amp;lt;T1,T2,T3,......,T16,TResult&amp;gt;（T1 obj1,T2 obj2,T3 obj3,......,T16 obj16）&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             Func&amp;lt;&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt;&amp;gt; func = Account;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; result=func(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Result is : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+result);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; Account(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; a,&lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt; condition)&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (condition)&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; a * &lt;span style="color: #800080;"&gt;1.5&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; a * &lt;span style="color: #800080;"&gt;2&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.4 揭开 Lambda 神秘的面纱&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Lambda 的表达式的编写格式如下：&lt;/p&gt;&lt;div style="border: 1px solid #808080; padding: 5px; width: 150px; text-algin: center;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; x=&amp;gt; x * 1.5&lt;/div&gt;&lt;p&gt;当中 &amp;ldquo; =&amp;gt; &amp;rdquo; 是 Lambda 表达式的操作符，在左边用作定义一个参数列表，右边可以操作这些参数。&lt;/p&gt;&lt;p&gt;例子一, 先把 int x 设置 1000，通过 Action 把表达式定义为 x=x+500 ，最后通过 Invoke 激发委托。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; x = &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;             Action action = () =&amp;gt; x = x + &lt;span style="color: #800080;"&gt;500&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;             action.Invoke();&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Result is : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + x);&lt;br /&gt;&lt;span style="color: #008080;"&gt;8&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;9&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;例子二，通过 Action&amp;lt;int&amp;gt; 把表达式定义 x=x+500， 到最后输入参数1000，得到的结果与例子一相同。&lt;br /&gt;注意，此处Lambda表达式定义的操作使用 { } 括弧包括在一起，里面可以包含一系列的操作。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             Action&amp;lt;&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;&amp;gt; action = (x) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                 x = x + &lt;span style="color: #800080;"&gt;500&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Result is : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + x);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             };&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             action.Invoke(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;例子三，定义一个Predicate&amp;lt;int&amp;gt;，当输入值大约等于1000则返回 true , 否则返回 false。与5.3.1的例子相比，Predicate&amp;lt;T&amp;gt;的绑定不需要显式建立一个方法，而是直接在Lambda表达式里完成，简洁方便了不少。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             Predicate&amp;lt;&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;&amp;gt; predicate = (x) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (x &amp;gt;= &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;false&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             };&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             bool result=predicate.Invoke(&lt;span style="color: #800080;"&gt;500&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;例子四，在计算商品的价格时，当商品重量超过30kg则打9折，其他按原价处理。此时可以使用Func&amp;lt;double,int,double&amp;gt;，参数1为商品原价，参数2为商品重量，最后返回值为 double 类型。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             Func&amp;lt;&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt;&amp;gt; func = (price, weight) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (weight &amp;gt;= &lt;span style="color: #800080;"&gt;30&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; price * &lt;span style="color: #800080;"&gt;0.9&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; price;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             };&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; totalPrice = func(&lt;span style="color: #800080;"&gt;200.0&lt;/span&gt;, &lt;span style="color: #800080;"&gt;40&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;例子五，使用Lambda为Button定义Click事件的处理方法。与5.2的例子相比，使用Lambda比使用匿名方法更加简单。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;             Button btn = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Button();&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;             btn.Click += (obj, e) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;                 MessageBox.Show(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello World!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;             };&lt;br /&gt;&lt;span style="color: #008080;"&gt;8&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;9&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;例子六，此处使用5.3.1的例子，在List&amp;lt;Person&amp;gt;的FindAll方法中直接使用Lambda表达式。&lt;br /&gt;相比之下，使用Lambda表达式，不需要定义Predicate&amp;lt;T&amp;gt;对象，也不需要显式设定绑定方法，简化了不工序。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             List&amp;lt;Person&amp;gt; personList = GetList();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;查找年龄少于30年的人&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             List&amp;lt;Person&amp;gt; result=personList.FindAll((person) =&amp;gt; person.Age =&amp;lt; 30);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Person count is : &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + result.Count);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;模拟源数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; List&amp;lt;Person&amp;gt; GetList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Person&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person(&lt;span style="color: #800080;"&gt;1&lt;/span&gt;,&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;span style="color: #800080;"&gt;29&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;              personList.Add(person1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;              .......&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Person&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Person(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id, &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name, &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; age)&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;              ID = id;&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;              Name = name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;              Age = age;&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; ID&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;          { &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;; &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Name&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;          { &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;; &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Age&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;          { &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;; &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;      }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;当在使用LINQ技术的时候，到处都会弥漫着 Lambda 的身影，此时更能体现 Lambda 的长处。&lt;br /&gt;但 LINQ 涉及到分部类，分部方法，IEnumerable&amp;lt;T&amp;gt;，迭代器等多方面的知识，这些已经超出本章的介绍范围。&lt;br /&gt;通过这一节的介绍，希望能够帮助大家更深入地了解 Lambda 的使用。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;本章小结&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;本章主要介绍了委托（Delegate）的使用，委托对象是一个派生自 System.MultcastDelegate 的类，它能通过 Invoke 方式进行同步调用，也可以通过 BeginInvoke，EndInvoke 方式实现异步调用。而事件（Event）属于一种特殊的委托，它与委托类型同步使用，可以简化的开发过程。&lt;br /&gt;最后，本文还介绍了匿名方法的使用方式，以及 Lambda 表达式的由来。&lt;br /&gt;对.NET开发有兴趣的朋友请加入博客园讨论小组&lt;span style="color: #0000ff;"&gt;&lt;a href="http://home.cnblogs.com/group/102576/" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&amp;ldquo;.NET高级编程&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;一起探讨！&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&amp;nbsp;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;C#综合揭秘&lt;/span&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt; &lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说进程、应用程序域与上下文&lt;/span&gt;&lt;/a&gt; &lt;/span&gt;&lt;span style="color: #0000ff;"&gt; &lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;细说多线程（上）&lt;/span&gt;&lt;/a&gt; &lt;/span&gt; &lt;span style="color: #0000ff;"&gt; &lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt; &lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说多线程（下）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说事务&lt;br /&gt;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;深入分析委托与事件&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="float: right; text-align: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;a id="Editor_Edit_hlEntryLink" title="view: C#综合揭秘&amp;mdash;&amp;mdash;深入解析委托与事件" href="http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2389318.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html</id><title type="text">C#综合揭秘——细说进程、应用程序域与上下文之间的关系</title><summary type="text">本文主要是介绍进程（Process）、应用程序域（AppDomain）、.NET上下文（Context）的概念与操作。一个进程内可以包括多个应用程序域，也有包括多个线程，线程也可以穿梭于多个应用程序域当中。但在同一个时刻，线程只会处于一个应用程序域内。线程也能穿梭于多个上下文当中，进行对象的调用。虽然在一般的开发当中这三者并不常用，但熟悉三者的关系，深入了解其作用，对提高系统的性能有莫大的帮助。在本篇最后的一节当中将会介绍到三者与线程之间的关系，希望对多线程开发人员能提供一定的帮助。</summary><published>2012-03-06T01:36:00Z</published><updated>2012-03-06T01:36:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html"/><content type="html">&lt;p&gt;引言&lt;/p&gt;&lt;p&gt;&lt;a name="t0"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;本文主要是介绍进程（Process）、应用程序域（AppDomain）、.NET上下文（Context）的概念与操作。&lt;br /&gt;虽然在一般的开发当中这三者并不常用，但熟悉三者的关系，深入了解其作用，对提高系统的性能有莫大的帮助。&lt;br /&gt;在本篇最后的一节当中将会介绍到三者与线程之间的关系，希望对多线程开发人员能提供一定的帮助。&lt;br /&gt;因为时间仓促，文中有错误的地方敬请点评。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;目录&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#a"&gt;&lt;span style="color: #0000ff;"&gt;一、进程的概念与作用&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#b0"&gt;&lt;span style="color: #0000ff;"&gt;二、应用程序域&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#c"&gt;&lt;span style="color: #0000ff;"&gt;三、深入了解.NET上下文&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#d"&gt;&lt;span style="color: #0000ff;"&gt;四、进程应用程序域与线程的关系&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;a name="a"&gt;&lt;/a&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;一、进程的概念与作用&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;进程（Process）是Windows系统中的一个基本概念，它包含着一个运行程序所需要的资源。进程之间是相对独立的，一个进程无法直接访问另一个进程的数据（除非利用分布式计算方式），一个进程运行的失败也不会影响其他进程的运行，Windows系统就是利用进程把工作划分为多个独立的区域的。进程可以理解为一个程序的基本边界。&lt;/p&gt;&lt;p&gt;&lt;a name="a1"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1.1 Process 的属性与方法&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在 System.Diagnostics 命名空间当中存在Process类，专门用于管理进程的开始、结束，访问进程中的模块，获取进程中的线程，设定进程的优先级别等。&lt;br /&gt;表1.0 显示了Process类的常用属性：&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;table class="memberListTable" style="width: 600px; font-size: 12px;" border="0"&gt;&lt;colgroup&gt;&lt;col width="25%" /&gt; &lt;col width="75%" /&gt; &lt;/colgroup&gt;&lt;tbody&gt;&lt;tr valign="top"&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;属性&lt;/strong&gt;&lt;/td&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;说明&lt;/strong&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;BasePriority&lt;/td&gt;&lt;td&gt;获取关联进程的基本优先级。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ExitCode&lt;/td&gt;&lt;td&gt;获取关联进程终止时指定的值。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ExitTime&lt;/td&gt;&lt;td&gt;获取关联进程退出的时间。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Handle&lt;/td&gt;&lt;td&gt;返回关联进程的本机句柄。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;HandleCount&lt;/td&gt;&lt;td&gt;获取由进程打开的句柄数。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;HasExited&lt;/td&gt;&lt;td&gt;获取指示关联进程是否已终止的值。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Id&lt;/td&gt;&lt;td&gt;获取关联进程的唯一标识符。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;MachineName&lt;/td&gt;&lt;td&gt;获取关联进程正在其上运行的计算机的名称。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;MainModule&lt;/td&gt;&lt;td&gt;获取关联进程的主模块。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Modules&lt;/td&gt;&lt;td&gt;获取已由关联进程加载的模块。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;PriorityClass&lt;/td&gt;&lt;td&gt;获取或设置关联进程的总体优先级类别。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ProcessName&lt;/td&gt;&lt;td&gt;获取该进程的名称。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;StartInfo&lt;/td&gt;&lt;td&gt;获取或设置要传递给Process的Start方法的属性。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;StartTime&lt;/td&gt;&lt;td&gt;获取关联进程启动的时间。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;SynchronizingObject&lt;/td&gt;&lt;td&gt;获取或设置用于封送由于进程退出事件而发出的事件处理程序调用的对象。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Threads&lt;/td&gt;&lt;td&gt;获取在关联进程中运行的一组线程&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&lt;em&gt;&lt;strong&gt;&amp;nbsp;&lt;span style="font-size: 12px;"&gt;表1.0&lt;/span&gt;&lt;/strong&gt;&lt;/em&gt;&lt;/p&gt;&lt;p&gt;除了上述属性，Process类也定义了下列经常使用的方法：&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;table class="memberListTable" style="width: 600px; font-size: 12px;" border="0"&gt;&lt;colgroup&gt;&lt;col width="25%" /&gt; &lt;col width="75%" /&gt; &lt;/colgroup&gt;&lt;tbody&gt;&lt;tr valign="top"&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;方法&lt;/strong&gt;&lt;/td&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;说明&lt;/strong&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;GetProcessById&lt;/td&gt;&lt;td&gt;创建新的 Process 组件，并将其与您指定的现有进程资源关联。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;GetProcessByName&lt;/td&gt;&lt;td&gt;创建多个新的 Process 组件，并将其与您指定的现有进程资源关联。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;GetCurrentProcess&lt;/td&gt;&lt;td&gt;获取新的 &lt;span&gt;Process&lt;/span&gt; 组件并将其与当前活动的进程关联。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;GetProcesses&lt;/td&gt;&lt;td&gt;获取本地计算机上正在运行的每一个进程列表。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Start&lt;/td&gt;&lt;td&gt;启动一个进程。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Kill&lt;/td&gt;&lt;td&gt;立即停止关联的进程。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Close&lt;/td&gt;&lt;td&gt;释放与此组件关联的所有资源。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;WaitForExit&lt;/td&gt;&lt;td&gt;指示 Process 组件无限期地等待关联进程退出。&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&amp;nbsp;&lt;span style="font-size: 12px;"&gt;&lt;em&gt;&lt;strong&gt;表1.1&lt;/strong&gt;&lt;/em&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;Process类的详细信息可以参考 &lt;span style="color: #0000ff;"&gt;&lt;a href="http://msdn.microsoft.com/zh-cn/library/system.diagnostics.process.aspx" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://msdn.microsoft.com/zh-cn/library/system.diagnostics.process.aspx&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;br /&gt;下面将举例介绍一下Process的使用方式&lt;/p&gt;&lt;p&gt;&lt;a name="a2"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 14px;"&gt;&lt;strong&gt;1.2 建立与销毁进程&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;利用 Start 与Kill 方法可以简单建立或者销毁进程，下面例子就是利用 Start 方法启动记事本的进程，并打开File.txt文件。2秒钟以后，再使用 Kill 方法销毁进程，并关闭记事本。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;             Process process = Process.Start(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;notepad.exe&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;File.txt&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;2000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;             process.Kill();&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&lt;a name="a3"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1.3 列举计算机运行中的进程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在表1.0 中可以看到，使用 GetProcesses 方法可以获取本地计算机上正在运行的每一个进程列表。&lt;br /&gt;而进程的 Id 属性是每个进程的唯一标志，通过下面的方法，可以显示当前计算机运行的所有进程信息。&lt;br /&gt;因为篇幅关系，下面例子只获取前10个进程。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; processList = Process.GetProcesses()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;                 .OrderBy(x=&amp;gt;x.Id)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                 .Take(&lt;span style="color: #800080;"&gt;10&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; process &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; processList)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;ProcessId is:{0} \t ProcessName is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                     process.Id, process.ProcessName));&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;运行结果&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030423552094.jpg" alt="" width="540" height="173" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;如果已知进程的Id，就可以通过 GetProcessById 方法获取对应的进程。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; process = Process.GetProcessById(&lt;span style="color: #800080;"&gt;1772&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Process name is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + process.ProcessName);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (ArgumentException ex)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Process is nothing!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;同样地，你也可能通过GetProcessByName方法获取多个对应名称的进程。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;em&gt;注意：如果不能找到当前ID的进程，系统就会抛出ArgumentException异常。所以使用方法 GetProcessById 获取进程时应该包含在 try{...} catch{..} 之内。&lt;/em&gt;&lt;em&gt;&lt;/em&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;a name="a4"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1.4 获取进程中的多个模块&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在表1.0 中包含了Process类的Modules属性，通过此属性可能获取进程中的多个模块。&lt;br /&gt;这些模块可以是以 *.dll 结尾的程序集，也可以是 *.exe 结尾的可执行程序。&lt;br /&gt;下面的例子就是通过 Process 的 GetCurrentProcess 方法获取当前运行的进程信息，然后显示当前进程的多个模块信息。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; moduleList = Process.GetCurrentProcess().Modules;&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (System.Diagnostics.ProcessModule module &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; moduleList)&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  URL:{1}\n  Version:{2}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;                     module.ModuleName,module.FileName,module.FileVersionInfo.FileVersion));&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;8&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;运行结果：&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030423574222.jpg" alt="" width="537" height="324" /&gt;&lt;/p&gt;&lt;p&gt;&lt;a name="b0"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;二、应用程序域&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;使用.NET建立的可执行程序 *.exe，并没有直接承载到进程当中，而是承载到应用程序域（AppDomain）当中。应用程序域是.NET引入的一个新概念，它比进程所占用的资源要少，可以被看作是一个轻量级的进程。&lt;br /&gt;在一个进程中可以包含多个应用程序域，一个应用程序域可以装载一个可执行程序（*.exe）或者多个程序集（*.dll）。这样可以使应用程序域之间实现深度隔离，即使进程中的某个应用程序域出现错误，也不会影响其他应用程序域的正常运作。&lt;/p&gt;&lt;p&gt;当一个程序集同时被多个应用程序域调用时，会出现两种情况：&lt;br /&gt;第一种情况：CLR分别为不同的应用程序域加载此程序集。&lt;br /&gt;第二种情况：CLR把此程序集加载到所有的应用程序域之外，并实现程序集共享，此情况比较特殊，被称作为Domain Neutral。&lt;/p&gt;&lt;p&gt;&lt;a name="b1"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.1 AppDomain的属性与方法&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在System命名空间当中就存在AppDomain类，用管理应用程序域。下面是AppDomain类的常用属性：&lt;/p&gt;&lt;table class="memberListTable" style="width: 600px; font-size: 12px;" border="0"&gt;&lt;colgroup&gt;&lt;col width="25%" /&gt; &lt;col width="75%" /&gt; &lt;/colgroup&gt;&lt;tbody&gt;&lt;tr valign="top"&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;属性&lt;/strong&gt;&lt;/td&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;说明&lt;/strong&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ActivationContext&lt;/td&gt;&lt;td&gt;获取当前应用程序域的激活上下文。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ApplicationIdentity&lt;/td&gt;&lt;td&gt;获得应用程序域中的应用程序标识。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;BaseDirectory&lt;/td&gt;&lt;td&gt;获取基目录。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;CurrentDomain&lt;/td&gt;&lt;td&gt;获取当前 Thread 的当前应用程序域。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Id&lt;/td&gt;&lt;td&gt;获得一个整数，该整数唯一标识进程中的应用程序域。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;RelativeSearchPath&lt;/td&gt;&lt;td&gt;获取相对于基目录的路径，在此程序集冲突解决程序应探测专用程序集。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;SetupInformation&lt;/td&gt;&lt;td&gt;获取此实例的应用程序域配置信息。&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="font-size: 12px;"&gt;&lt;em&gt;表2.0&lt;/em&gt;&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;AppDomain类中有多个方法，可以用于创建一个新的应用程序域，或者执行应用程序域中的应用程序。&lt;/p&gt;&lt;table class="memberListTable" style="width: 600px; font-size: 12px;" border="0"&gt;&lt;colgroup&gt;&lt;col width="25%" /&gt; &lt;col width="75%" /&gt; &lt;/colgroup&gt;&lt;tbody&gt;&lt;tr valign="top"&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;方法&lt;/strong&gt;&lt;/td&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;说明&lt;/strong&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;CreateDomain&lt;/td&gt;&lt;td&gt;创建新的应用程序域。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;CreateInstance&lt;/td&gt;&lt;td&gt;创建在指定程序集中定义的指定类型的新实例。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;CreateInstanceFrom&lt;/td&gt;&lt;td&gt;创建在指定程序集文件中定义的指定类型的新实例。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;DoCallBack&lt;/td&gt;&lt;td&gt;在另一个应用程序域中执行代码，该应用程序域由指定的委托标识。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ExecuteAssembly&lt;/td&gt;&lt;td&gt;执行指定文件中包含的程序集。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ExecuteAssemblyByName&lt;/td&gt;&lt;td&gt;执行程序集。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;GetAssemblies&lt;/td&gt;&lt;td&gt;获取已加载到此应用程序域的执行上下文中的程序集。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;GetCurrentThreadId&lt;/td&gt;&lt;td&gt;获取当前线程标识符。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;GetData&lt;/td&gt;&lt;td&gt;为指定名称获取存储在当前应用程序域中的值。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;IsDefaultAppDomain&lt;/td&gt;&lt;td&gt;返回一个值，指示应用程序域是否是进程的默认应用程序域。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;SetData&lt;/td&gt;&lt;td&gt;为应用程序域属性分配值。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Load&lt;/td&gt;&lt;td&gt;将 Assembly 加载到此应用程序域中。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;Unload&lt;/td&gt;&lt;td&gt;卸载指定的应用程序域。&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&lt;em&gt;&lt;strong&gt;&lt;span style="font-size: 12px;"&gt;表2.1&lt;/span&gt;&lt;/strong&gt;&lt;/em&gt;&lt;/p&gt;&lt;p&gt;AppDomain类中有多个事件，用于管理应用程序域生命周期中的不同部分。&lt;/p&gt;&lt;table class="memberListTable" style="width: 600px; font-size: 12px;" border="0"&gt;&lt;colgroup&gt;&lt;col width="25%" /&gt; &lt;col width="75%" /&gt; &lt;/colgroup&gt;&lt;tbody&gt;&lt;tr valign="top"&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;事件&lt;/strong&gt;&lt;/td&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;说明&lt;/strong&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;AssemblyLoad&lt;/td&gt;&lt;td&gt;在加载程序集时发生。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;AssemblyResolve&lt;/td&gt;&lt;td&gt;在对程序集的解析失败时发生。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;DomainUnload&lt;/td&gt;&lt;td&gt;在即将卸载 AppDomain 时发生。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ProcessExit&lt;/td&gt;&lt;td&gt;当默认应用程序域的父进程存在时发生。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ReflectionOnlyAssemblyResolve&lt;/td&gt;&lt;td&gt;当程序集的解析在只反射上下文中失败时发生。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;ResourceResolve&lt;/td&gt;&lt;td&gt;当资源解析因资源不是程序集中的有效链接资源或嵌入资源而失败时发生。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;TypeResolve&lt;/td&gt;&lt;td&gt;在对类型的解析失败时发生。&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;UnhandledException&lt;/td&gt;&lt;td&gt;当某个异常未被捕获时出现。&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&lt;span style="font-size: 12px;"&gt;&lt;em&gt;&lt;strong&gt;表2.2&lt;/strong&gt;&lt;/em&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;下面将举例详细介绍一下AppDomain的使用方式&lt;/p&gt;&lt;p&gt;&lt;a name="b2"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.2 在AppDomain中加载程序集&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;由表2.1中可以看到，通过CreateDomain方法可以建立一个新的应用程序域。&lt;br /&gt;下面的例子将使用CreateDomain建立一个应用程序域，并使用Load方法加载程序集Model.dll。最后使用GetAssemblies方法，列举此应用程序域中的所有程序集。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; appDomain = AppDomain.CreateDomain(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;NewAppDomain&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;             appDomain.Load(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Model&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; assembly &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; appDomain.GetAssemblies())&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n----------------------------&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;                     assembly.FullName));&lt;br /&gt;&lt;span style="color: #008080;"&gt;8&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;9&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030423593415.jpg" alt="" width="545" height="148" /&gt;&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;em&gt;注意：当加载程序集后，就无法把它从AppDomain中卸载，只能把整个AppDomain卸载。&lt;/em&gt;&lt;em&gt;&lt;/em&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;当需要在AppDomain加载可执行程序时，可以使用ExecuteAssembly方法。&lt;/p&gt;&lt;p&gt;AppDomain.ExecuteAssembly("Example.exe");&lt;/p&gt;&lt;p&gt;&lt;a name="b3"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.3 卸载AppDomain&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;通过Unload可以卸载AppDomain，在AppDomain卸载时将会触发DomainUnload事件。&lt;br /&gt;下面的例子中，将会使用CreateDomain建立一个名为NewAppDomain的应用程序域。然后建立AssemblyLoad的事件处理方法，在程序集加载时显示程序集的信息。最后建立DomainUnload事件处理方法，在AppDomain卸载时显示卸载信息。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;新建名为NewAppDomain的应用程序域&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             AppDomain newAppDomain = AppDomain.CreateDomain(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;NewAppDomain&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立AssemblyLoad事件处理方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             newAppDomain.AssemblyLoad +=&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 (obj, e) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                 {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                     Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0} is loading!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, e.LoadedAssembly.GetName()));&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                 };&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立DomainUnload事件处理方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             newAppDomain.DomainUnload +=&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                 (obj, e) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                     Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;NewAppDomain Unload!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                 };&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;加载程序集&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             newAppDomain.Load(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Model&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;模拟操作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; n &amp;lt; &lt;span style="color: #800080;"&gt;5&lt;/span&gt;; n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  Do Work.......!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;卸载AppDomain&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             AppDomain.Unload(newAppDomain);&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030500010516.jpg" alt="" width="538" height="146" /&gt;&lt;/p&gt;&lt;p&gt;&lt;a name="b4"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.4 在AppDomain中建立程序集中指定类的对象&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;使用CreateInstance方法，能建立程序集中指定类的对像。但使用此方法将返回一个ObjectHandle对象，若要将此值转化为原类型，可调用Unwrap方法。&lt;br /&gt;下面例子会建立Model.dll程序集中的Model.Person对象。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Test&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person=(Person)AppDomain.CurrentDomain&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                           .CreateInstance(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Model&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Model.Person&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;).Unwrap();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;              person.ID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;              person.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;              person.Age = &lt;span style="color: #800080;"&gt;29&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;              Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}'s age is {1}!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,person.Name,person.Age));&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;              Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Model&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Person&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; ID&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;           {&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;               &lt;span&gt;get&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;               &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;           }&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Name&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;           {&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;                &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;           }&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Age&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;           {&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;                &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;                &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;           }&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a name="c"&gt;&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;三、深入了解.NET上下文&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.1 .NET上下文的概念&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;应用程序域是进程中承载程序集的逻辑分区，在应用程序域当中，存在更细粒度的用于承载.NET对象的实体，那就.NET上下文Context。&lt;br /&gt;所有的.NET对象都存在于上下文当中，每个AppDomain当中至少存在一个默认上下文（context 0）。&lt;br /&gt;一般不需要指定特定上下文的对象被称为上下文灵活对象（context-agile），建立此对象不需要特定的操作，只需要由CLR自行管理，一般这些对象都会被建立在默认上下文当中。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030513303267.jpg" alt="" width="307" height="161" /&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;em&gt;&lt;span style="font-size: 12px;"&gt;图3.0&lt;/span&gt;&lt;/em&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.2 透明代理&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在上下文的接口当中存在着一个消息接收器负责检测拦截和处理信息，当对象是MarshalByRefObject的子类的时候，CLR将会建立透明代理，实现对象与消息之间的转换。&lt;br /&gt;应用程序域是CLR中资源的边界，一般情况下，应用程序域中的对象不能被外界的对象所访问。而MarshalByRefObject 的功能就是允许在支持远程处理的应用程序中跨应用程序域边界访问对象，在使用.NET Remoting远程对象开发时经常使用到的一个父类。&lt;br /&gt;此文章针对的是进程与应用程序域的作用，关于MarshalByRefObject的使用已经超越了本文的范围，关于.NET Remoting 远程对象开发可参考：&amp;ldquo;&lt;a title="回顾.NET Remoting分布式开发" href="http://www.cnblogs.com/leslies2/archive/2011/05/11/2040996.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;回顾.NET Remoting分布式开发&amp;rdquo;&lt;/span&gt;&lt;/a&gt;。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.3 上下文绑定&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;当系统需要对象使用消息接收器机制的时候，即可使用ContextBoundObject类。ContextBoundObject继承了MarshalByRefObject类，保证了它的子类都会通过透明代理被访问。&lt;br /&gt;在第一节介绍过：一般类所建立的对象为上下文灵活对象（context-agile），它们都由CLR自动管理，可存在于任意的上下文当中。而 ContextBoundObject 的子类所建立的对象只能在建立它的对应上下文中正常运行，此状态被称为上下文绑定。其他对象想要访问ContextBoundObject 的子类对象时，都只能通过代透明理来操作。&lt;/p&gt;&lt;p&gt;下面的例子，是上下文绑定对象与上下文灵活对象的一个对比。Example 是一个普通类，它的对象会运行在默认上下文当中。而ContextBound类继承了ContextBoundObject，它的对象是一个上下文绑定对象。ContextBound还有一个Synchronization特性，此特性会保证ContextBound对象被加载到一个线程安全的上下文当中运行。另外，Context类存在ContextProperties属性，通过此属性可以获取该上下文的已有信息。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Example&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Test()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 ContextMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Example Test\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;访问上下文绑定对象测试&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Sync(ContextBound contextBound)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                 contextBound.Test(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Example call on contextBound\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         [Synchronization]&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; ContextBound:ContextBoundObject&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Test(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message)&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                 ContextMessage(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             Example example = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Example();&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             example.Test();&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             ContextBound contextBound = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ContextBound();&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             contextBound.Test(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;ContentBound Test\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;             example.Sync(contextBound);&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示上下文信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ContextMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;             Context context = Thread.CurrentContext;&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}ContextId is {1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, data, context.ContextID));&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; prop &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; context.ContextProperties)&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;                 Console.WriteLine(prop.Name);&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;             Console.WriteLine();&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030515541664.jpg" alt="" width="529" height="219" /&gt;&lt;/p&gt;&lt;p&gt;由运行结果可以发现，example对象一般只会工作于默认上下文context 0 当中，而contextBound则会工作于线程安全的上下文 context 1当中。当example需要调用contextBound对象时，就会通过透明代理把消息直接传递到context 1中。&lt;br /&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a name="d"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;四、进程、应用程序域、线程的相互关系&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.1 跨AppDomain运行代码&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在应用程序域之间的数据是相对独立的，当需要在其他AppDomain当中执行当前AppDomain中的程序集代码时，可以使用CrossAppDomainDelegate委托。把CrossAppDomainDelegate委托绑定方法以后，通过AppDomain的DoCallBack方法即可执行委托。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;CurrentAppDomain start!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立新的应用程序域对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             AppDomain newAppDomain = AppDomain.CreateDomain(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;newAppDomain&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;绑定CrossAppDomainDelegate的委托方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             CrossAppDomainDelegate crossAppDomainDelegate=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; CrossAppDomainDelegate(MyCallBack);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;绑定DomainUnload的事件处理方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             newAppDomain.DomainUnload += (obj, e) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;NewAppDomain unload!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             };&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;调用委托&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             newAppDomain.DoCallBack(crossAppDomainDelegate);&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             AppDomain.Unload(newAppDomain) ;&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; MyCallBack()&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name = AppDomain.CurrentDomain.FriendlyName;&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt;(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n=&lt;span style="color: #800080;"&gt;0&lt;/span&gt;;n&amp;lt;&lt;span style="color: #800080;"&gt;4&lt;/span&gt;;n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format( &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  Do work in {0}........&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; , name));&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030517162240.jpg" alt="" width="541" height="134" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.2 跨AppDomain的线程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;线程存在于进程当中，它在不同的时刻可以运行于多个不同的AppDomain当中。它是进程中的基本执行单元，在进程入口执行的第一个线程被视为这个进程的主线程。在.NET应用程序中，都是以Main()方法作为入口的，当调用此方法时 系统就会自动创建一个主线程。线程主要是由CPU寄存器、调用栈和线程本地存储器（Thread Local Storage，TLS）组成的。CPU寄存器主要记录当前所执行线程的状态，调用栈主要用于维护线程所调用到的内存与数据，TLS主要用于存放线程的状态信息。&lt;br /&gt;关于线程的介绍，可参考 &lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&amp;ldquo;C#综合揭秘&amp;mdash;&amp;mdash;细说多线程（上）&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;、&amp;ldquo;&lt;span style="color: #0000ff;"&gt;&lt;a id="cb_post_title_url" href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;C#综合揭秘&amp;mdash;&amp;mdash;细说多线程（下）&amp;rdquo; &lt;br /&gt;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;下面的例子将介绍一下如何跨AppDomain使用线程，首先建立一个ConsoleApplication项目，在执行时输入当前线程及应用程序域的信息，最后生成Example.exe的可执行程序。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CurrentThreadID is:{0}\tAppDomainID is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;                 Thread.CurrentThread.ManagedThreadId, AppDomain.CurrentDomain.Id);&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;             Console.Read();&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;然后再新建一个ConsoleApplication项目，在此项目中新一个AppDomain对象，在新的AppDomain中通过ExecuteAssembly方法执行Example.exe程序。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;当前应用程序域信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;CurrentAppDomain start!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             ShowMessage();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立新的应用程序域对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             AppDomain newAppDomain = AppDomain.CreateDomain(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;newAppDomain&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在新的应用程序域中执行Example.exe&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             newAppDomain.ExecuteAssembly(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Example.exe&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             AppDomain.Unload(newAppDomain);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowMessage()&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CurrentThreadID is:{0}\tAppDomainID is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                 Thread.CurrentThread.ManagedThreadId, AppDomain.CurrentDomain.Id);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030518084844.jpg" alt="" width="561" height="99" /&gt;&lt;/p&gt;&lt;p&gt;可见，ID等于9的线程在不同时间内分别运行于AppDomain 1与AppDomain 2当中。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.3 跨上下文的线程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;线程既然能够跨越AppDomain的边界，当然也能跨越不同的上下文。&lt;br /&gt;下面这个例子中，线程将同时运行在默认上下文与提供安全线程的上下文中。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         [Synchronization]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; ContextBound : ContextBoundObject&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Test()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                 ShowMessage();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;当前应用程序域信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;CurrentAppDomain start!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             ShowMessage();&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在上下文绑定对象中运行线程&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             ContextBound contextBound = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ContextBound();&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             contextBound.Test();&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowMessage()&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CurrentThreadID is:{0}\tContextID is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;                  Thread.CurrentThread.ManagedThreadId, Thread.CurrentContext.ContextID);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030518354637.jpg" alt="" width="544" height="96" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;本篇总结&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;进程（Process）、线程（Thread）、应用程序域（AppDomain）、上下文（Context）的关系如图5.0，一个进程内可以包括多个应用程序域，也有包括多个线程，线程也可以穿梭于多个应用程序域当中。但在同一个时刻，线程只会处于一个应用程序域内。线程也能穿梭于多个上下文当中，进行对象的调用。&lt;/p&gt;&lt;p&gt;虽然进程、应用程序域与上下文在平常的开发中并非经常用到，但深入地了解三者的关系，熟悉其操作方式对合理利用系统的资源，提高系统的效率是非常有意义的。&lt;br /&gt;尤其是三者与线程之间的关系尤为重要，特别是在一个多线程系统中，如果不能理清其关系而盲目使用多线程，容易造成资源抢占与死锁之类的错误。&lt;/p&gt;&lt;p&gt;&lt;img style="border: 1px ridge #808080; display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2012/64989/2012010713392540.jpg" alt="" width="502" height="264" /&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 12px;"&gt;&lt;em&gt;&lt;strong&gt;&amp;nbsp;图5.0&lt;/strong&gt;&lt;/em&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;希望本篇文章对相关的开发人员有所帮助。&lt;br /&gt;对.NET开发有兴趣的朋友请加入博客园讨论小组&lt;span style="color: #0000ff;"&gt;&lt;a href="http://home.cnblogs.com/group/102576/" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&amp;ldquo;.NET高级编程&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;一起探讨！&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;C#综合揭秘&lt;/span&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说进程、应用程序域与上下文&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;细说多线程（上）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说多线程（下）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说事务&lt;br /&gt;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;深入分析委托与事件&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="float: right; text-align: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;br /&gt;&lt;a id="Editor_Edit_hlEntryLink" title="C#综合揭秘&amp;mdash;&amp;mdash;细说进程、应用程序域与上下文" href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html&amp;nbsp;&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2379235.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/leslies2/archive/2012/03/01/2375462.html</id><title type="text">先睹为快：Visual Studio 11测试版已于2.29在微软官方网站正式发布</title><summary type="text">在2011的下半年，Visual Studio 11就已经呼之欲出，在2012年的2月29日，微软官方网站正式发布了VS11的测试版。VS11中使用了Framework4.5，与Framework4.0相比，没有发生太大的改变，只是对功能进行了优化。下载地址:http://www.microsoft.com/visualstudio/11/zh-cn/downloads单单一个安装包就需要1.7G左右，安装旗舰装大约需要7.6G的空间，安装时间可能比较长，可需要耐心等待喔。</summary><published>2012-03-01T09:04:00Z</published><updated>2012-03-01T09:04:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2012/03/01/2375462.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2012/03/01/2375462.html"/><content type="html">&lt;p&gt;在2011的下半年，Visual Studio 11就已经呼之欲出，在2012年的2月29日，微软官方网站正式发布了VS11的测试版。&lt;br /&gt;VS11中使用了Framework4.5，与Framework4.0相比，没有发生太大的改变，只是对功能进行了优化。&lt;/p&gt;&lt;p&gt;下载地址:&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.microsoft.com/visualstudio/11/zh-cn/downloads" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://www.microsoft.com/visualstudio/11/zh-cn/downloads&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;单单一个安装包就需要1.7G左右，安装旗舰版大约需要3.6G的空间，安装时间可能比较长，需要耐心地等待喔。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030118361288.png" alt="" width="390" height="513" /&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;一、支持触屏管理与Metro&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;VS11明显是面向Windows 8开发的，与Windows 8相同，它支持触屏管理与Metro 风格的应用开发，并支持本地或者远程调试。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030121242122.jpg" alt="" width="777" height="463" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;二、ASP.NET&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;在ASP.NET方面，在数据绑定上增加了新ItemType属性来定义绑定类型， 以SelectMethod来绑定获取数据源的方法。&lt;br /&gt;在显示类型属性的时候，只需要使用&amp;lt;%#:Item.Id%&amp;gt;即可代替原来的&amp;lt;%#Eval("Id")%&amp;gt;，使用起来会更加简单。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Repeater &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="repeater1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; SelectMethod&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="GetPersonList"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt;  ItemType&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Person"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;ItemTemplate&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;               ID &lt;span style="background-color: #ffff00; color: #000000;"&gt;&amp;lt;%&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;#:Item.ID&lt;/span&gt;&lt;span style="background-color: #ffff00; color: #000000;"&gt;%&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;               Age &lt;span style="background-color: #ffff00; color: #000000;"&gt;&amp;lt;%&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;#:Item.Age&lt;/span&gt;&lt;span style="background-color: #ffff00; color: #000000;"&gt;%&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;               Name &lt;span style="background-color: #ffff00; color: #000000;"&gt;&amp;lt;%&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;#:Item.Name&lt;/span&gt;&lt;span style="background-color: #ffff00; color: #000000;"&gt;%&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;ItemTemplate&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Repeater&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;/div&gt;&lt;p&gt;绑定数据源&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Person&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         person1.ID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         person1.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         person1.Age = &lt;span style="color: #800080;"&gt;29&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         personList.Add(person1);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;span style="font-family: Tahoma; font-size: small;"&gt;&lt;span style="font-family: Tahoma; font-size: small;"&gt;在编写ASP.NET页面代码的时候，开发人员编辑控件件会出现Smart Tasks提示，使开发更加简单：&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030121152746.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;在页面也能看到属性设置工具，非常地方便&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030121184644.jpg" alt="" width="616" height="630" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;三、支持HTML 5和CSS 3&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;从 VS10起，系统就开始支持 HTML 5 与 CSS 3 , 而在VS11,更是增强了这方面的功能。&lt;br /&gt;在视觉方面，它支持了开张（Expand）、闭合功能（Collapse），使用起来更加方便。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030121363790.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;CSS有父子关系的设定，只要启用这功能，CSS就可以有伸缩的效果，阅读CSS与阅读代码一样井井有条。&lt;br /&gt;如图，在菜单选择Tools -&amp;gt; Options -&amp;gt; Text Editor -&amp;gt; CSS -&amp;gt; Formatting，选择 Indentation 中的 Hierarchical Indentation&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030121055556.jpg" alt="" width="658" height="428" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030121323242.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;以往无论是页面开发人员还是程序员，都不太喜欢用VS来开发CSS，因为使用不太方便。&lt;br /&gt;有见及此，VS11为CSS代码添加了感知能力，无论在普通属性或者是色彩设置方面，使用都非常地方便。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030121294384.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012030121270726.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;对audio这些HTML 5中的控件，VS 11无不支持&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; &amp;lt;audio controls="controls"&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;     &amp;lt;source src="mylove.mp3"/&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt; &amp;lt;/audio&amp;gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;四、Javascript&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;在VS2010中，已经增加了对Javascript的支持，使用也比较方便，但唯一欠缺的就是对JSON的支持。&lt;br /&gt;特别是在使用数组型的JSON数据时候，往往需要使用第三方插件才会比较方便，本人更多的是使用Newtonsoft.Json工具包。&lt;br /&gt;在VS11中，明显是正视了这个问题，它&lt;span id="comment_body_2320804" class="blog_comment_body"&gt;支持了ECMAScript 5，而且&lt;/span&gt;为JSON提供了更方便的转换方式。&lt;/p&gt;&lt;p&gt;使用 parse 方法，可以将JSON数组转换为对象集，使用alert可以显示数组中Leslie的Age。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; window.onload = &lt;span style="color: #0000ff;"&gt;function&lt;/span&gt; () {&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; obj = JSON.parse('[{"ID":"1","Age":"23","Name":"Rose"},{"ID":"2","Age":"29","Name":"Leslie"}]');&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;      alert(obj[1].Age);&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;反过来，使用 stringify 方法可以把对象转换为JSON&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; obj.ID = "1";&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt; obj.Name = "Leslie";&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt; obj.Age="29";&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt; alert(JSON.stringify(obj));&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;五、异步操作&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;在异步操作方面，VS11也作出了一点调整，比如在异步获取上，它在原基础上增加一个await操作。&lt;br /&gt;功能与PLINQ相似，系统能自动判断操作是否能提高系统的性能，如果通过判定，将在在后台线程中运行，不会影响主线程的运作。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;   &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; response = &lt;strong&gt;&lt;span style="background-color: #ff0000; color: #ffffff;"&gt;await&lt;/span&gt;&lt;/strong&gt; &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; HttpClient().GetAsync(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;http://msdn.microsoft.com&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;); &lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;   &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; result = response.EnsureSuccessStatusCode().Content.ReadAsString();&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;   &lt;span style="color: #0000ff;"&gt;this&lt;/span&gt;.textBox1.Text = result;&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;   .......&lt;br /&gt;&lt;span style="color: #008080;"&gt;8&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;若要使用异步页面，注意把页面的异步属性设置为true&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; &amp;lt;%@ Page Title="" Language="C#" MasterPageFile="~/Site.Master" AutoEventWireup="true"&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;     CodeBehind="ProductDetails.aspx.cs" Inherits="WebFormsLab.ProductDetails"&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;     &lt;span style="color: #ff0000;"&gt;Async="true"&lt;/span&gt; %&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt; &amp;lt;asp:Label ID="threadsMessageLabel" runat="server" /&amp;gt;&lt;/div&gt;&lt;p&gt;同样地与原本的异步页面比较一下，只需要在异步调用时加上 await&amp;nbsp; 的执行方式&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; UpdateProductImage(Product product)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;   &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; imageUrl = product.ImagePath;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;   &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (!&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.IsNullOrEmpty(imageUrl) &amp;amp;&amp;amp; !VirtualPathUtility.IsAbsolute(imageUrl))&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;   {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;     product.ImagePath = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;/Images/{0}{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, product.ProductId, Path.GetExtension(imageUrl));&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;     RegisterAsyncTask(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; PageAsyncTask(async(o,a,ct) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; startThread = Thread.CurrentThread.ManagedThreadId;&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; wc = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; WebClient())&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         &lt;strong&gt;&lt;span style="background-color: #ff0000; color: #ffffff;"&gt;await&lt;/span&gt;&lt;/strong&gt; wc.DownloadFileTaskAsync(imageUrl, Server.MapPath(product.ImagePath));&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; endThread = Thread.CurrentThread.ManagedThreadId;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;       threadsMessageLabel.Text = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Started on thread: {0}&amp;lt;br /&amp;gt; Finished on thread: {1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, startThread, endThread);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;     }));&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;   }&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;六、代码测试&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;VS11新增了一个重复代码分析功能，使代码的修改更加简单快节。&lt;br /&gt;它还有一个调试工具，叫做 &amp;ldquo;Page Inspector&amp;rdquo;，专门为ASP.NET开发而设，能加强调试的功能。&lt;br /&gt;还有带有一个 Metro 风格模拟器，允许开发者模拟测试 Metro 应用的触摸和旋转事件。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;结束语&lt;/strong&gt;&lt;/span&gt;&lt;br /&gt;据说在WF与F#上，VS11也进行了不少的优化，这需要更多时间进行更深入的了解。&lt;br /&gt;相信VS11能更有效地帮助代码的编写，减少开发时间。&lt;br /&gt;Visual Studio 11视频介绍：&lt;span style="color: #0000ff;"&gt;&lt;a href="http://v.youku.com/v_show/id_XMzU2NzU3NzU2.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://v.youku.com/v_show/id_XMzU2NzU3NzU2.html&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;br /&gt;对.NET开发有兴趣的朋友请加入博客园讨论小组&lt;span style="color: #0000ff;"&gt;&lt;a href="http://home.cnblogs.com/group/102576/" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&amp;ldquo;.NET高级编程&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; 一起探讨！&lt;/p&gt;&lt;div style="float: right; text-align: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/01/2375462.html"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2012/03/01/2375462.html&amp;nbsp;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;a title="http://www.cnblogs.com/leslies2" href="http://www.cnblogs.com/leslies2"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;div id="BlogPostCategory"&gt;&amp;nbsp;&lt;/div&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2375462.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/01/2375462.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html</id><title type="text">C#综合揭秘——细说多线程（下）</title><summary type="text">本文主要从线程的基础用法，CLR线程池当中工作者线程与I/O线程的开发，并行操作PLINQ等多个方面介绍多线程的开发。其中委托的BeginInvoke方法以及回调函数最为常用。而 I/O线程可能容易遭到大家的忽略，其实在开发多线程系统，更应该多留意I/O线程的操作。特别是在ASP.NET开发当中，可能更多人只会留意在客户端使用Ajax或者在服务器端使用UpdatePanel。其实合理使用I/O线程在通讯项目或文件下载时，能尽量降低IIS中的压力。并行编程是Framework4.0中极力推广的异步操作方式，更值得更深入地学习。</summary><published>2012-02-08T07:38:00Z</published><updated>2012-02-08T07:38:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html"/><content type="html">&lt;p&gt;&lt;a name="t0"&gt;&lt;/a&gt;引言&lt;/p&gt;&lt;p&gt;本文主要从线程的基础用法，CLR线程池当中工作者线程与I/O线程的开发，并行操作PLINQ等多个方面介绍多线程的开发。&lt;br /&gt;其中委托的BeginInvoke方法以及回调函数最为常用。&lt;br /&gt;而 I/O线程可能容易遭到大家的忽略，其实在开发多线程系统，更应该多留意I/O线程的操作。特别是在ASP.NET开发当中，可能更多人只会留意在客户端使用Ajax或者在服务器端使用UpdatePanel。其实合理使用I/O线程在通讯项目或文件下载时，能尽量降低IIS的压力。&lt;br /&gt;并行编程是Framework4.0中极力推广的异步操作方式，更值得更深入地学习。&lt;br /&gt;希望本篇文章能对各位的学习研究有所帮助，当中有所错漏的地方敬请点评。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;目录&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html#t1"&gt;&lt;span style="color: #0000ff;"&gt;一、线程的定义&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html#t2"&gt;&lt;span style="color: #0000ff;"&gt;二、线程的基础知识&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html#t3"&gt;&lt;span style="color: #0000ff;"&gt;三、以ThreadStart方式实现多线程&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html#t4"&gt;&lt;span style="color: #0000ff;"&gt;四、CLR线程池的工作者线程&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t5"&gt;&lt;span style="color: #0000ff;"&gt;五、CLR线程池的I/O线程&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t6"&gt;&lt;span style="color: #0000ff;"&gt;六、异步 SqlCommand&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t7"&gt;&lt;span style="color: #0000ff;"&gt;七、并行编程与PLINQ&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t8"&gt;&lt;span style="color: #0000ff;"&gt;八、计时器与锁&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a name="t5"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="font-size: 16px;"&gt;五、CLR线程池的I/O线程&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在前一节所介绍的线程都属于CLR线程池的工作者线程，这一节开始为大家介绍一下CLR线程池的I/O线程&lt;/p&gt;&lt;p&gt;I/O 线程是.NET专为访问外部资源所设置的一种线程，因为访问外部资源常常要受到外界因素的影响，为了防止让主线程受影响而长期处于阻塞状态，.NET为多个I/O操作都建立起了异步方法，例如：FileStream、TCP/IP、WebRequest、WebService等等，而且每个异步方法的使用方式都非常类似，都是以BeginXXX为开始，以EndXXX结束，下面为大家一一解说。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.1&amp;nbsp; 异步读写 FileStream&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;需要在 FileStream 异步调用 I/O线程，必须使用以下构造函数建立 FileStream 对象，并把useAsync设置为 true。&lt;/p&gt;&lt;p&gt;FileStream stream = new FileStream ( string path, FileMode mode, FileAccess access, FileShare share, int bufferSize,bool useAsync ) ;&lt;/p&gt;&lt;p&gt;其中&lt;span class="parameter"&gt; path &lt;/span&gt;&lt;strong&gt;&lt;/strong&gt;是文件的相对路径或绝对路径; &lt;span class="parameter"&gt;mode &lt;/span&gt;确定如何打开或创建文件;&lt;span class="parameter"&gt; access&lt;/span&gt; 确定&lt;strong&gt;&lt;/strong&gt;访问文件的方式; share 确定文件如何进程共享; bufferSize 是代表缓冲区大小,一般默认最小值为8，在启动异步读取或写入时，文件大小一般大于缓冲大小; userAsync代表是否启动异步I/O线程。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;strong&gt;&lt;em&gt;注意：当使用 BeginRead 和 BeginWrite 方法在执行大量读或写时效果更好，但对于少量的读/写，这些方法速度可能比同步读取还要慢，因为进行线程间的切换需要大量时间。&lt;/em&gt;&lt;/strong&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.1.1 异步写入&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;FileStream中包含BeginWrite、EndWrite 方法可以启动I/O线程进行异步写入。&lt;/p&gt;&lt;p&gt;public override IAsyncResult BeginWrite ( byte[] array, int offset, int numBytes, AsyncCallback userCallback, Object stateObject )&lt;br /&gt;public override void EndWrite (IAsyncResult asyncResult )&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;BeginWrite 返回值为IAsyncResult, 使用方式与委托的BeginInvoke方法相似，最好就是使用回调函数，避免线程阻塞。在最后两个参数中，参数AsyncCallback用于绑定回调函数; 参数Object用于传递外部数据。要注意一点：AsyncCallback所绑定的回调函数必须是带单个 IAsyncResult 参数的无返回值方法。&lt;br /&gt;在例子中，把FileStream作为外部数据传递到回调函数当中，然后在回调函数中利用IAsyncResult.AsyncState获取FileStream对象，最后通过FileStream.EndWrite（IAsyncResult）结束写入。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把线程池的最大值设置为1000&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;新立文件File.sour&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             FileStream stream = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; FileStream(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;File.sour&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, FileMode.OpenOrCreate, &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                                        FileAccess.ReadWrite,FileShare.ReadWrite,&lt;span style="color: #800080;"&gt;1024&lt;/span&gt;,&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] bytes = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[&lt;span style="color: #800080;"&gt;16384&lt;/span&gt;];&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;An operating-system ThreadId has no fixed relationship........&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             bytes = Encoding.Unicode.GetBytes(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;启动异步写入&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             stream.BeginWrite(bytes, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;)bytes.Length,&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(Callback),stream);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             stream.Flush();&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Callback(IAsyncResult result)&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;200&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;AsyncCallback&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;结束异步写入&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             FileStream stream = (FileStream)result.AsyncState;&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             stream.EndWrite(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;             stream.Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  CurrentThreadId is {1}\n  &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WorkerThreads is:{2}  CompletionPortThreads is :{3}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;                   data, Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;由输出结果可以看到，在使用FileStream.BeginWrite方法后，系统将自动启动CLR线程池中I/O线程。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011318310539.jpg" alt="" width="528" height="136" /&gt;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.1.2 异步读取&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;FileStream 中包含 BeginRead 与 EndRead 可以异步调用I/O线程进行读取。&lt;/p&gt;&lt;p&gt;public override IAsyncResult BeginRead ( byte[] array,int offset,int numBytes, AsyncCallback userCallback,Object stateObject)&lt;br /&gt;public override int EndRead(IAsyncResult asyncResult)&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;其使用方式与BeginWrite和EndWrite相似，AsyncCallback用于绑定回调函数; Object用于传递外部数据。在回调函数只需要使用IAsyncResut.AsyncState就可获取外部数据。EndWrite 方法会返回从流读取到的字节数量。&lt;/p&gt;&lt;p&gt;首先定义 FileData 类，里面包含FileStream对象，byte[] 数组和长度。然后把FileData对象作为外部数据传到回调函数，在回调函数中，把IAsyncResult.AsyncState强制转换为FileData，然后通过FileStream.EndRead（IAsyncResult）结束读取。最后比较一下长度，若读取到的长度与输入的数据长度不一至，则抛出异常。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; FileData&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; FileStream Stream;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Length;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] ByteData;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;          {       &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把线程池的最大值设置为1000&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;              ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;              ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;              ReadFile();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;              Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ReadFile()&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] byteData=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[&lt;span style="color: #800080;"&gt;80961024&lt;/span&gt;];&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;              FileStream stream = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; FileStream(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;File1.sour&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, FileMode.OpenOrCreate, &lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                                      FileAccess.ReadWrite, FileShare.ReadWrite, &lt;span style="color: #800080;"&gt;1024&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;              &lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把FileStream对象,byte[]对象，长度等有关数据绑定到FileData对象中，以附带属性方式送到回调函数&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;              FileData fileData = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; FileData();&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;              fileData.Stream = stream;&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;              fileData.Length = (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;)stream.Length;&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;              fileData.ByteData = byteData;&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;              &lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;启动异步读取&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;              stream.BeginRead(byteData, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, fileData.Length, &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(Completed), fileData);&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;   &lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Completed(IAsyncResult result)&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;              ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Completed&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把AsyncResult.AsyncState转换为FileData对象，以FileStream.EndRead完成异步读取&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;              FileData fileData = (FileData)result.AsyncState;&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; length=fileData.Stream.EndRead(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;              fileData.Stream.Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;如果读取到的长度与输入长度不一致，则抛出异常&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (length != fileData.Length)&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;throw&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Exception(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Stream is not complete!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data=Encoding.ASCII.GetString(fileData.ByteData, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, fileData.Length);&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;              Console.WriteLine(data.Substring(2,22));&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;              ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  CurrentThreadId is {1}\n  &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt;                           &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WorkerThreads is:{2}  CompletionPortThreads is :{3}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;                           data, Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;              Console.WriteLine(message);      &lt;br /&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt;              &lt;br /&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt;    }&lt;/div&gt;&lt;p&gt;由输出结果可以看到，在使用FileStream.BeginRead方法后，系统将自动启动CLR线程池中I/O线程。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011222590320.jpg" alt="" width="538" height="163" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;strong&gt;&lt;em&gt;注意：如果你看到的测试结果正好相反：工作者线程为999，I/O线程为1000，这是因为FileStream的文件容量小于缓冲值1024所致的。此时文件将会一次性读取或写入，而系统将启动工作者线程而非I/O线程来处理回调函数。&lt;/em&gt;&lt;/strong&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.2 异步操作TCP/IP套接字&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在介绍 TCP/IP 套接字前先简单介绍一下 NetworkStream 类，它是用于网络访问的基础数据流。 NetworkStream 提供了好几个方法控制套接字数据的发送与接收, 其中BeginRead、EndRead、BeginWrite、EndWrite 能够实现异步操作，而且异步线程是来自于CLR线程池的I/O线程。&lt;/p&gt;&lt;p&gt;public override int ReadByte ()&lt;br /&gt;public override int Read (byte[] buffer,int offset, int size)&lt;/p&gt;&lt;p&gt;public override void WriteByte (byte value)&lt;br /&gt;public override void Write (byte[] buffer,int offset, int size)&lt;/p&gt;&lt;p&gt;public override IAsyncResult BeginRead (byte [] buffer, int offset, int size,&amp;nbsp; AsyncCallback callback, Object state )&lt;br /&gt;public override int EndRead(IAsyncResult result)&lt;/p&gt;&lt;p&gt;public override IAsyncResult BeginWrite (byte [] buffer, int offset, int size,&amp;nbsp; AsyncCallback callback, Object state )&lt;br /&gt;public override void EndWrite(IAsyncResult result)&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;若要创建 NetworkStream，必须提供已连接的 Socket。而在.NET中使用TCP/IP套接字不需要直接与Socket打交道，因为.NET把Socket的大部分操作都放在System.Net.TcpListener和System.Net.Sockets.TcpClient里面，这两个类大大地简化了Socket的操作。一般套接字对象Socket包含一个Accept（）方法，此方法能产生阻塞来等待客户端的请求，而在TcpListener类里也包含了一个相似的方法 public TcpClient AcceptTcpClient（）用于等待客户端的请求。此方法将会返回一个TcpClient 对象，通过 TcpClient 的 public NetworkStream GetStream（）方法就能获取NetworkStream对象，控制套接字数据的发送与接收。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;下面以一个例子说明异步调用TCP/IP套接字收发数据的过程。&lt;/p&gt;&lt;p&gt;首先在服务器端建立默认地址127.0.0.1用于收发信息，使用此地址与端口500新建TcpListener对象，调用TcpListener.Start 侦听传入的连接请求，再使用一个死循环来监听信息。&lt;/p&gt;&lt;p&gt;在ChatClient类包括有接收信息与发送信息两个功能：当接收到客户端请求时，它会利用 NetworkStream.BeginRead 读取客户端信息，并在回调函数ReceiveAsyncCallback中输出信息内容，若接收到的信息的大小小于1时，它将会抛出一个异常。当信息成功接收后，再使用 NetworkStream.BeginWrite 方法回馈信息到客户端&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;设置CLR线程池最大线程数&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;    &lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;默认地址为127.0.0.1&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             IPAddress ipAddress = IPAddress.Parse(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;127.0.0.1&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             TcpListener tcpListener = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TcpListener(ipAddress, &lt;span style="color: #800080;"&gt;500&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             tcpListener.Start();&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;以一个死循环来实现监听&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;while&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             {   &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;调用一个ChatClient对象来实现监听&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                 ChatClient chatClient = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ChatClient(tcpListener.AcceptTcpClient());    &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; ChatClient&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; TcpClient tcpClient;&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] byteMessage;&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; clientEndPoint;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; ChatClient(TcpClient tcpClient1)&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             tcpClient = tcpClient1;&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             byteMessage = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[tcpClient.ReceiveBufferSize];&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;            &lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示客户端信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;             clientEndPoint = tcpClient.Client.RemoteEndPoint.ToString();&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Client's endpoint is &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + clientEndPoint);&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用NetworkStream.BeginRead异步读取信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;             NetworkStream networkStream = tcpClient.GetStream();&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;             networkStream.BeginRead(byteMessage, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, tcpClient.ReceiveBufferSize,&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                                          &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(ReceiveAsyncCallback), &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ReceiveAsyncCallback(IAsyncResult iAsyncResult)&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示CLR线程池状态&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;100&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;\nMessage is receiving&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用NetworkStream.EndRead结束异步读取&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;             NetworkStream networkStreamRead = tcpClient.GetStream();&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; length=networkStreamRead.EndRead(iAsyncResult);&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;如果接收到的数据长度少于1则抛出异常&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (length &amp;lt; &lt;span style="color: #800080;"&gt;1&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;                 tcpClient.GetStream().Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;throw&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Exception(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Disconnection!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示接收信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = Encoding.UTF8.GetString(byteMessage, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, length);&lt;br /&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Message:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用NetworkStream.BeginWrite异步发送信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] sendMessage = Encoding.UTF8.GetBytes(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Message is received!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;65&lt;/span&gt;             NetworkStream networkStreamWrite=tcpClient.GetStream();&lt;br /&gt;&lt;span style="color: #008080;"&gt;66&lt;/span&gt;             networkStreamWrite.BeginWrite(sendMessage, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, sendMessage.Length, &lt;br /&gt;&lt;span style="color: #008080;"&gt;67&lt;/span&gt;                                             &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(SendAsyncCallback), &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;68&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;69&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;70&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把信息转换成二进制数据，然后发送到客户端&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;71&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; SendAsyncCallback(IAsyncResult iAsyncResult)&lt;br /&gt;&lt;span style="color: #008080;"&gt;72&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;73&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示CLR线程池状态&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;74&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;100&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;75&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;\nMessage is sending&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;76&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;77&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用NetworkStream.EndWrite结束异步发送&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;78&lt;/span&gt;             tcpClient.GetStream().EndWrite(iAsyncResult);&lt;br /&gt;&lt;span style="color: #008080;"&gt;79&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;80&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;重新监听&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;81&lt;/span&gt;             tcpClient.GetStream().BeginRead(byteMessage, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, tcpClient.ReceiveBufferSize,&lt;br /&gt;&lt;span style="color: #008080;"&gt;82&lt;/span&gt;                                                &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(ReceiveAsyncCallback), &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;83&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;84&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;85&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;86&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;87&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;88&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;89&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;90&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  CurrentThreadId is {1}\n  &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;91&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WorkerThreads is:{2}  CompletionPortThreads is :{3}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;92&lt;/span&gt;                   data, Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;93&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;94&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;95&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;96&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;而在客户端只是使用简单的开发方式，利用TcpClient连接到服务器端，然后调用NetworkStream.Write方法发送信息，最后调用NetworkStream.Read方法读取回馈信息&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;连接服务端&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             TcpClient tcpClient = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TcpClient(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;127.0.0.1&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #800080;"&gt;500&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;发送信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             NetworkStream networkStream = tcpClient.GetStream();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] sendMessage = Encoding.UTF8.GetBytes(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Client request connection!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             networkStream.Write(sendMessage, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, sendMessage.Length);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             networkStream.Flush();&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;接收信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] receiveMessage=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[&lt;span style="color: #800080;"&gt;1024&lt;/span&gt;];&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; count=networkStream.Read(receiveMessage, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;,&lt;span style="color: #800080;"&gt;1024&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             Console.WriteLine(Encoding.UTF8.GetString(receiveMessage));&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;注意观察运行结果，服务器端的异步操作线程都是来自于CLR线程池的I/O线程&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011422394590.jpg" alt="" width="640" height="314" /&gt;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.3 异步WebRequest&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;span id="xn45_5db71a9c82c67265cd4726a9eac5c930" class="sentence"&gt;&lt;span&gt;&lt;span class="selflink"&gt;System.Net.WebRequest&lt;/span&gt;&lt;/span&gt; 是 .NET 为实现&lt;span id="xn45_5db71a9c82c67265cd4726a9eac5c930" class="sentence"&gt;访问 Internet &lt;/span&gt;的 &amp;ldquo;请求/响应模型&amp;rdquo; 而开发的一个 &lt;span&gt;&lt;span class="input"&gt;abstract&lt;/span&gt;&lt;/span&gt; 基类，&lt;/span&gt; &lt;span id="xn46_b1466be5e739e8e14ac31a4d25c68e4b" class="sentence"&gt;它主要有三个子类：FtpWebRequest、HttpWebRequest、FileWebRequest。当使用WebRequest.Create（string uri）创建对象时，应用程序就可以根据请求协议判断实现类来进行操作。FileWebRequest、FtpWebRequest、HttpWebRequest 各有其作用：FileWebRequest 使用 &amp;ldquo;file://路径&amp;rdquo; 的URI方式实现对本地资源和内部文件的请求/响应、&lt;span id="xn46_b1466be5e739e8e14ac31a4d25c68e4b" class="sentence"&gt;FtpWebRequest 使用FTP文件传输协议实现文件请求/响应、&lt;/span&gt;HttpWebRequest 用于处理HTTP的页面请求/响应。由于使用方法相类似，下面就以常用的HttpWebRequest为例子介绍一下异步WebRequest的使用方法。&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span class="sentence"&gt;在使用ASP.NET开发网站的时候，往往会忽略了HttpWebRequest的使用，因为开发都假设客户端是使用浏览器等工具去阅读页面的。但如果你对REST开发方式有所了解，那对 HttpWebRequest 就应该非常熟悉。它可以在路径参数、头文件、页面主体、Cookie 等多处地方加入请求条件，然后对回复数据进行适当处理。HttpWebRequest 包含有以下几个常用方法用于处理请求/响应：&lt;/span&gt;&lt;/p&gt;&lt;p&gt;public override Stream GetRequestStream ()&lt;br /&gt;public override WebResponse GetResponse ()&lt;/p&gt;&lt;p&gt;public override IAsyncResult BeginGetRequestStream ( AsyncCallback callback, Object state )&lt;br /&gt;public override Stream EndGetRequestStream ( IAsyncResult asyncResult )&lt;br /&gt;public override IAsyncResult BeginGetResponse ( AsyncCallback callback, Object state )&lt;br /&gt;public override WebResponse EndGetResponse ( IAsyncResult asyncResult )&lt;/p&gt;&lt;p&gt;&lt;span class="sentence"&gt;其中BeginGetRequestStream、EndGetRequestStream 用于异步向HttpWebRequest对象写入请求信息;&amp;nbsp; BeginGetResponse、EndGetResponse 用于异步发送页面请求并获取返回信息。使用异步方式操作Internet的&amp;ldquo;请求/响应&amp;rdquo;，避免主线程长期处于等待状态，而操作期间异步线程是来自CLR线程池的I/O线程。&lt;/span&gt;&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;strong&gt;&lt;em&gt;注意：&lt;strong&gt;&lt;em&gt;请求与响应&lt;/em&gt;&lt;/strong&gt;不能使用同步与异步混合开发模式，即当请求写入使用GetRequestStream同步模式，即使响应使用BeginGetResponse异步方法，操作也与GetRequestStream方法在于同一线程内。&lt;/em&gt;&lt;/strong&gt;&lt;/div&gt;&lt;p&gt;&lt;span class="sentence"&gt;下面以简单的例子介绍一下异步请求的用法。&lt;/span&gt;&lt;/p&gt;&lt;p&gt;首先为Person类加上可序列化特性，在服务器端建立Hanlder.ashx，通过Request.InputStream 获取到请求数据并把数据转化为String对象，此实例中数据是以 &amp;ldquo;Id：1&amp;rdquo; 的形式实现传送的。然后根据Id查找对应的Person对象，并把Person对象写入Response.OutStream 中返还到客户端。&lt;/p&gt;&lt;p&gt;在客户端先把 HttpWebRequird.Method 设置为 "post"，使用异步方式通过BeginGetRequireStream获取请求数据流，然后写入请求数据 &amp;ldquo;Id:1&amp;rdquo;。再使用异步方法BeginGetResponse 获取回复数据，最后把数据反序列化为Person对象显示出来。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;span class="sentence"&gt;&lt;strong&gt;&lt;em&gt;注意：HttpWebRequire.Method默认为get，&lt;span class="sentence"&gt;在写入请求前&lt;/span&gt;必须把HttpWebRequire.Method设置为post,否则在使用BeginGetRequireStream 获取请求数据流的时候，系统就会发出 &amp;ldquo;无法发送具有此谓词类型的内容正文" 的异常。&lt;/em&gt;&lt;/strong&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;span class="sentence"&gt;Model&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Model&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     [Serializable]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Person&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; ID&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Name&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Age&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&lt;span class="sentence"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span class="sentence"&gt;服务器端&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Handler : IHttpHandler {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ProcessRequest(HttpContext context)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把信息转换为String，找出输入条件Id&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] bytes=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[&lt;span style="color: #800080;"&gt;1024&lt;/span&gt;];&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; length=context.Request.InputStream.Read(bytes,&lt;span style="color: #800080;"&gt;0&lt;/span&gt;,&lt;span style="color: #800080;"&gt;1024&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; condition = Encoding.Default.GetString(bytes);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id = &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;.Parse(condition.Split(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] { &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; }, &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                            StringSplitOptions.RemoveEmptyEntries)[&lt;span style="color: #800080;"&gt;1&lt;/span&gt;]);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据Id查找对应Person对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person = GetPersonList().Where(x =&amp;gt; x.ID == id).First();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;所Person格式化为二进制数据写入OutputStream&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         BinaryFormatter formatter = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; BinaryFormatter();&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         formatter.Serialize(context.Response.OutputStream, person);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;模拟源数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Person&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person();&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;         person1.ID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         person1.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         person1.Age = &lt;span style="color: #800080;"&gt;30&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;         personList.Add(person1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         ...........&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt; IsReusable&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt; { &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;;}&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&lt;span class="sentence"&gt;客户端&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             Request();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Request()&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;); &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用WebRequest.Create方法建立HttpWebRequest对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             HttpWebRequest webRequest = (HttpWebRequest)WebRequest.Create(&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                                             &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;http://localhost:5700/Handler.ashx&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             webRequest.Method = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;post&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;            &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;对写入数据的RequestStream对象进行异步请求&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             IAsyncResult result=webRequest.BeginGetRequestStream(&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(EndGetRequestStream),webRequest);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; EndGetRequestStream(IAsyncResult result)&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;RequestStream Complete&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取RequestStream&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             HttpWebRequest webRequest = (HttpWebRequest)result.AsyncState;&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             Stream stream=webRequest.EndGetRequestStream(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;写入请求条件&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] condition = Encoding.Default.GetBytes(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Id:1&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             stream.Write(condition, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, condition.Length);&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;异步接收回传信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             IAsyncResult responseResult = webRequest.BeginGetResponse(&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(EndGetResponse), webRequest);&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; EndGetResponse(IAsyncResult result)&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显出线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;GetResponse Complete&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;结束异步请求，获取结果&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;             HttpWebRequest webRequest = (HttpWebRequest)result.AsyncState;&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;             WebResponse webResponse = webRequest.EndGetResponse(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把输出结果转化为Person对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;             Stream stream = webResponse.GetResponseStream();&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;             BinaryFormatter formatter = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; BinaryFormatter();&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person=(Person)formatter.Deserialize(stream);&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Person    Id:{0} Name:{1} Age:{2}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;                 person.ID, person.Name, person.Age));&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  CurrentThreadId is {1}\n  &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WorkerThreads is:{2}  CompletionPortThreads is :{3}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt;                   data, Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;65&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;66&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;67&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&lt;span class="sentence"&gt;从运行结果可以看到，BeginGetRequireStream、BeginGetResponse方法是使用CLR线程池的I/O线程。&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011812134254.jpg" alt="" width="546" height="229" /&gt;&lt;/p&gt;&lt;p&gt;&lt;span id="xn46_b1466be5e739e8e14ac31a4d25c68e4b" class="sentence"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span class="sentence"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span id="xn46_b1466be5e739e8e14ac31a4d25c68e4b" class="sentence"&gt;5.4 异步调用WebService&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;span id="xn46_b1466be5e739e8e14ac31a4d25c68e4b" class="sentence"&gt;相比TCP/IP套接字，在使用WebService的时候，服务器端需要更复杂的操作处理，使用时间往往会更长。为了避免客户端长期处于等待状态，&lt;span id="xn46_b1466be5e739e8e14ac31a4d25c68e4b" class="sentence"&gt;在配置服务引用时选择 &amp;ldquo;生成异步操作&amp;rdquo;&lt;/span&gt;，系统可以自动建立异步调用的方式。&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span class="sentence"&gt;以.NET 2.0以前，系统都是使用ASMX来设计WebService，而近年来WCF可说是火热登场，下面就以WCF为例子简单介绍一下异步调用WebService的例子。&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span class="sentence"&gt;由于系统可以自动生成异步方法，使用起来非常简单，首先在服务器端建立服务ExampleService，里面包含方法Method。客户端引用此服务时，选择 &amp;ldquo;生成异步操作&amp;rdquo;。然后使用 BeginMethod 启动异步方法， 在回调函数中调用EndMethod结束异步调用。&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span class="sentence"&gt;服务端&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;      [ServiceContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IExampleService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;          [OperationContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Method(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; ExampleService : IExampleService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Method(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;              ServiceHost host = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ServiceHost(&lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(ExampleService));&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;              host.Open();&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;              Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;              host.Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;           }&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;  &amp;lt;configuration&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;      &amp;lt;system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;          &amp;lt;services&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;              &amp;lt;service name=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Example.ExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;                  &amp;lt;endpoint address=&lt;span style="color: #800000;"&gt;""&lt;/span&gt; binding=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;wsHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; contract=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Example.IExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;                      &amp;lt;identity&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;                          &amp;lt;dns value=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;localhost&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;                      &amp;lt;/identity&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;                  &amp;lt;/endpoint&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                  &amp;lt;endpoint address=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;mex&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; binding=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;mexHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; contract=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;IMetadataExchange&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                  &amp;lt;host&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                      &amp;lt;baseAddresses&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                          &amp;lt;add baseAddress=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;http://localhost:7200/Example/ExampleService/&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;                      &amp;lt;/baseAddresses&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;                  &amp;lt;/host&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;              &amp;lt;/service&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;          &amp;lt;/services&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;      &amp;lt;/system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;  &amp;lt;/configuration&amp;gt;&lt;/div&gt;&lt;p&gt;&lt;span class="sentence"&gt;客户端&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;设置最大线程数&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;              ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;              ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;              &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立服务对象，异步调用服务方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;              ExampleServiceReference.ExampleServiceClient exampleService = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                                      ExampleServiceReference.ExampleServiceClient();&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;              exampleService.BeginMethod(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(AsyncCallbackMethod), &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                                          exampleService);  &lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;              Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AsyncCallbackMethod(IAsyncResult result)&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;              Thread.Sleep(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;              ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Complete&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;              ExampleServiceReference.ExampleServiceClient example =&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                  (ExampleServiceReference.ExampleServiceClient)result.AsyncState;&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data=example.EndMethod(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;              Console.WriteLine(data);&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;              ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  CurrentThreadId is {1}\n  &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;                    &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WorkerThreads is:{2}  CompletionPortThreads is :{3}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;                    data, Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;              Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;  &amp;lt;configuration&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;      &amp;lt;system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;          &amp;lt;bindings&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;              &amp;lt;wsHttpBinding&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;                  &amp;lt;binding name=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WSHttpBinding_IExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; closeTimeout=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;00:01:00&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;                      openTimeout=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;00:01:00&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; receiveTimeout=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;00:10:00&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; sendTimeout=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;00:01:00&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;                      bypassProxyOnLocal=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;false&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; transactionFlow=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;false&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;                      hostNameComparisonMode=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;StrongWildcard&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; maxBufferPoolSize=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;524288&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;                      maxReceivedMessageSize=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;65536&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; messageEncoding=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Text&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; textEncoding=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;utf-8&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;                      useDefaultWebProxy=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;true&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; allowCookies=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;false&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;                      &amp;lt;readerQuotas maxDepth=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;32&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; maxStringContentLength=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;8192&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; maxArrayLength=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;16384&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;                          maxBytesPerRead=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;4096&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; maxNameTableCharCount=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;16384&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;                      &amp;lt;reliableSession ordered=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;true&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; inactivityTimeout=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;00:10:00&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; enabled=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;false&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;                      &amp;lt;security mode=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Message&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;                          &amp;lt;transport clientCredentialType=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Windows&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; proxyCredentialType=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;None&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;                            realm=&lt;span style="color: #800000;"&gt;""&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;                          &amp;lt;message clientCredentialType=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Windows&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; negotiateServiceCredential=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;true&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;                              algorithmSuite=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Default&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt;                      &amp;lt;/security&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt;                  &amp;lt;/binding&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;              &amp;lt;/wsHttpBinding&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;          &amp;lt;/bindings&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt;          &amp;lt;client&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt;              &amp;lt;endpoint address=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;http://localhost:7200/Example/ExampleService/&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt;                  binding=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;wsHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; bindingConfiguration=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WSHttpBinding_IExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;65&lt;/span&gt;                  contract=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;ExampleServiceReference.IExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;66&lt;/span&gt;                  name=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WSHttpBinding_IExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;67&lt;/span&gt;                  &amp;lt;identity&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;68&lt;/span&gt;                      &amp;lt;dns value=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;localhost&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;69&lt;/span&gt;                  &amp;lt;/identity&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;70&lt;/span&gt;              &amp;lt;/endpoint&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;71&lt;/span&gt;          &amp;lt;/client&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;72&lt;/span&gt;      &amp;lt;/system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;73&lt;/span&gt;  &amp;lt;/configuration&amp;gt;&lt;/div&gt;&lt;p&gt;&lt;span class="sentence"&gt;注意观察运行结果，异步调用服务时，回调函数都是运行于CLR线程池的I/O线程当中。&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011819025958.jpg" alt="" width="546" height="177" /&gt;&lt;span id="xn46_b1466be5e739e8e14ac31a4d25c68e4b" class="sentence"&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;a name="t6"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;六、异步 SqlCommand&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;从ADO.NET 2.0开始，SqlCommand就新增了几个异步方法执行SQL命令。相对于同步执行方式，它使主线程不需要等待数据库的返回结果，在使用复杂性查询或批量插入时将有效提高主线程的效率。使用异步SqlCommand的时候，请注意把ConnectionString 的&amp;nbsp;Asynchronous Processing 设置为 true 。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;strong&gt;&lt;em&gt;注意：SqlCommand异步操作的特别之处在于线程并不依赖于CLR线程池，而是由Windows内部提供，这比使用异步委托更有效率。但如果需要使用回调函数的时候，回调函数的线程依然是来自于CLR线程池的工作者线程。&lt;/em&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;SqlCommand有以下几个方法支持异步操作：&lt;/p&gt;&lt;p&gt;&lt;span style="color: #000000;"&gt;public IAsyncResult BeginExecuteNonQuery (......)&lt;/span&gt;&lt;br /&gt;public int EndExecuteNonQuery(IAsyncResult)&lt;/p&gt;&lt;p&gt;public IAsyncResult BeginExecuteReader(......)&lt;br /&gt;public SqlDataReader EndExecuteReader(IAsyncResult)&lt;/p&gt;&lt;p&gt;public IAsyncResult BeginExecuteXmlReader (......)&lt;br /&gt;public XmlReader EndExecuteXmlReader(IAsyncResult）&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;由于使用方式相似，此处就以 BeginExecuteNonQuery 为例子，介绍一下异步SqlCommand的使用。首先建立connectionString,注意把Asynchronous Processing设置为true来启动异步命令，然后把SqlCommand.CommandText设置为 WAITFOR DELAY "0:0:3" 来虚拟数据库操作。再通过BeginExecuteNonQuery启动异步操作，利用轮询方式监测操作情况。最后在操作完成后使用EndExecuteNonQuery完成异步操作。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把Asynchronous Processing设置为true&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; connectionString = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Data Source=LESLIE-PC;Initial Catalog=Business;&amp;ldquo;+&lt;/span&gt;&lt;span style="color: #800000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                                          &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Integrated Security=True;Asynchronous Processing=true&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把CLR线程池最大线程数设置为1000&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用WAITFOR DELAY命令来虚拟操作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             SqlConnection connection = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; SqlConnection(connectionString);&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             SqlCommand command = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; SqlCommand(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WAITFOR DELAY '0:0:3';&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, connection);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             connection.Open();&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;启动异步SqlCommand操作，利用轮询方式监测操作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             IAsyncResult result = command.BeginExecuteNonQuery();&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BeginRead&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;while&lt;/span&gt; (!result.AsyncWaitHandle.WaitOne(&lt;span style="color: #800080;"&gt;500&lt;/span&gt;))&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main thread do work........&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;结束异步SqlCommand&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; count= command.EndExecuteNonQuery(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;\nCompleted&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  CurrentThreadId is {1}\n  "+&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                    &lt;span style="color: #800000;"&gt;"WorkerThreads is:{2}  CompletionPortThreads is :{3}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                    data, Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;注意运行结果，SqlCommand的异步执行线程并不属于CLR线程池。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011417562736.jpg" alt="" width="560" height="301" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;如果觉得使用轮询方式过于麻烦，可以使用回调函数，但要注意当调用回调函数时，线程是来自于CLR线程池的工作者线程。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把Asynchronous Processing设置为true&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; connectionString = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Data Source=LESLIE-PC;Initial Catalog=Business;&amp;rdquo;+&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;                                          &lt;span style="color: #800000;"&gt;&amp;ldquo;Integrated Security=True;Asynchronous Processing=true&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把CLR线程池最大线程数设置为1000&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用WAITFOR DELAY命令来虚拟操作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             SqlConnection connection = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; SqlConnection(connectionString);&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             SqlCommand command = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; SqlCommand(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WAITFOR DELAY '0:0:3';&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, connection);&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             connection.Open();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;启动异步SqlCommand操作，并把SqlCommand对象传递到回调函数&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             IAsyncResult result = command.BeginExecuteNonQuery(&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                                        &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(AsyncCallbackMethod),command);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AsyncCallbackMethod(IAsyncResult result)&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;200&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             ThreadPoolMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;AsyncCallback&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             SqlCommand command = (SqlCommand)result.AsyncState;&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; count=command.EndExecuteNonQuery(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             command.Connection.Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  CurrentThreadId is {1}\n  &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WorkerThreads is:{2}  CompletionPortThreads is :{3}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                   data, Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果：&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011418163336.jpg" alt="" width="542" height="151" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;a name="t7"&gt;&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;七、并行编程与PLINQ&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;要使用多线程开发，必须非常熟悉Thread的使用，而且在开发过程中可能会面对很多未知的问题。为了简化开发，.NET 4.0 特别提供一个并行编程库System.Threading.Tasks，它可以简化并行开发，你无需直接跟线程或线程池打交道，就可以简单建立多线程应用程序。此外，.NET还提供了新的一组扩展方法PLINQ，它具有自动分析查询功能，如果并行查询能提高系统效率，则同时运行，如果查询未能从并行查询中受益，则按原顺序查询。下面将详细介绍并行操作的方式。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;7.1 泛型委托&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;使用并行编程可以同时操作多个委托,在介绍并行编程前先简单介绍一下两个泛型委托System.Func&amp;lt;&amp;gt;与System.Action&amp;lt;&amp;gt;。&lt;/p&gt;&lt;p&gt;Func&amp;lt;&amp;gt;是一个能接受多个参数和一个返回值的泛型委托，它能接受0个到4个输入参数, 其中 T1,T2,T3,T4 代表自定的输入类型，TResult为自定义的返回值。&lt;br /&gt;public delegate TResult Func&amp;lt;TResult&amp;gt;（）&lt;br /&gt;public delegate TResult Func&amp;lt;T1，TResult&amp;gt;（T1 arg1）&lt;br /&gt;public delegate TResult Func&amp;lt;T1，T2, TResult&amp;gt;（T1 arg1,T2 arg2）&lt;br /&gt;public delegate TResult Func&amp;lt;T1，T2, T3, TResult&amp;gt;（T1 arg1,T2 arg2,T3 arg3）&lt;br /&gt;public delegate TResult Func&amp;lt;T1，T2, T3, ,T4, TResult&amp;gt;（T1 arg1,T2 arg2,T3 arg3,T4 arg4）&lt;/p&gt;&lt;p&gt;Action&amp;lt;&amp;gt;与Func&amp;lt;&amp;gt;十分相似，不同在于Action&amp;lt;&amp;gt;的返回值为void，Action能接受1~16个参数&lt;br /&gt;public delegate void Action&amp;lt;T1&amp;gt;（）&lt;br /&gt; public delegate void Action&amp;lt;T1，T2&amp;gt;（T1 arg1,T2 arg2）&lt;br /&gt; public delegate void Action&amp;lt;T1，T2, T3&amp;gt;（T1 arg1,T2 arg2, T3 arg3）&lt;br /&gt;.............&lt;br /&gt; public delegate void Action&amp;lt;T1，T2, T3, ,T4, ...... ,T16&amp;gt;（T1 arg1,T2 arg2,T3 arg3,T4 arg4，...... ,T16 arg16）&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;7.2 任务并行库（TPL）&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;System.Threading.Tasks中的类被统称为任务并行库（Task Parallel Library，TPL），TPL使用CLR线程池把工作分配到CPU，并能&lt;span&gt;自动处理工作分区、线程调度、取消支持、状态管理以及其他低级别的细节操作&lt;/span&gt;，极大地简化了多线程的开发。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;strong&gt;&lt;em&gt;注意：&lt;strong&gt;&lt;em&gt;TPL比Thread更具智能性，当它判断任务集并没有从并行运行中受益，就会选择按顺序运行。&lt;/em&gt;&lt;/strong&gt;但并非所有的项目都适合使用并行开发，创建过多并行任务可能会损害程序的性能，降低运行效率。&lt;/em&gt;&lt;/strong&gt;&lt;/div&gt;&lt;p&gt;TPL包括常用的数据并行与任务并行两种执行方式：&lt;/p&gt;&lt;p&gt;&lt;strong&gt;7.2.1 数据并行&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;数据并行的核心类就是System.Threading.Tasks.Parallel，它包含两个静态方法 Parallel.For 与 Parallel.ForEach, 使用方式与for、foreach相仿。通过这两个方法可以并行处理System.Func&amp;lt;&amp;gt;、System.Action&amp;lt;&amp;gt;委托。&lt;/p&gt;&lt;p&gt;以下一个例子就是利用 public static ParallelLoopResult For( int from, int max, Action&amp;lt;int&amp;gt;) 方法对List&amp;lt;Person&amp;gt;进行并行查询。&lt;br /&gt;假设使用单线程方式查询3个Person对象，需要用时大约6秒，在使用并行方式，只需使用2秒就能完成查询，而且能够避开Thread的繁琐处理。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;设置最大线程数&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;并行查询&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             Parallel.For(&lt;span style="color: #800080;"&gt;0&lt;/span&gt;, &lt;span style="color: #800080;"&gt;3&lt;/span&gt;,n =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                     Thread.Sleep(&lt;span style="color: #800080;"&gt;2000&lt;/span&gt;);  &lt;span style="color: #008000;"&gt;//模拟查询&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                     ThreadPoolMessage(GetPersonList()[n]);&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                 });&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;模拟源数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Person&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person();&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             person1.ID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             person1.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             person1.Age = &lt;span style="color: #800080;"&gt;30&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             personList.Add(person1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             ...........&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(Person person)&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Person  ID:{0} Name:{1} Age:{2}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CurrentThreadId is {3}\n  WorkerThreads is:{4}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CompletionPortThreads is :{5}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                   person.ID, person.Name, person.Age,&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                   Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;观察运行结果，对象并非按照原排列顺序进行查询，而是使用并行方式查询。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011921343830.jpg" alt="" width="551" height="205" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;若想停止操作，可以利用ParallelLoopState参数，下面以ForEach作为例子。&lt;br /&gt;public static ParallelLoopResult ForEach&amp;lt;TSource&amp;gt;( IEnumerable&amp;lt;TSource&amp;gt; source, Action&amp;lt;TSource, ParallelLoopState&amp;gt; action)&lt;br /&gt;其中source为数据集，在Action&amp;lt;TSource,ParallelLoopState&amp;gt;委托的ParallelLoopState参数当中包含有Break（）和 Stop（）两个方法都可以使迭代停止。Break的使用跟传统for里面的使用方式相似，但因为处于并行处理当中，使用Break并不能保证所有运行能立即停止，在当前迭代之前的迭代会继续执行。若想立即停止操作，可以使用Stop方法，它能保证立即终止所有的操作，无论它们是处于当前迭代的之前还是之后。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;设置最大线程数&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;              ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;并行查询&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;              Parallel.ForEach(GetPersonList(), (person, state) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                  {&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                      &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (person.ID == &lt;span style="color: #800080;"&gt;2&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                          state.Stop();&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                      ThreadPoolMessage(person);&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                  });&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;              Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;模拟源数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Person&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person();&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;              person1.ID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;              person1.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;              person1.Age = &lt;span style="color: #800080;"&gt;30&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;              personList.Add(person1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;              ..........&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(Person person)&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;              ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Person  ID:{0} Name:{1} Age:{2}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                    &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CurrentThreadId is {3}\n  WorkerThreads is:{4}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                    &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CompletionPortThreads is :{5}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;                    person.ID, person.Name, person.Age,&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;                    Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;              Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;      }&lt;/div&gt;&lt;p&gt;观察运行结果，当Person的ID等于2时，运行将会停止。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011922134049.jpg" alt="" width="550" height="165" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;当要在多个线程中调用本地变量，可以使用以下方法：&lt;br /&gt;public static ParallelLoopResult ForEach&amp;lt;TSource, TLocal&amp;gt;(IEnumerable&amp;lt;Of TSource&amp;gt;, Func&amp;lt;Of TLocal&amp;gt;, Func&amp;lt;Of TSource,ParallelLoopState,TLocal,TLocal&amp;gt;, Action&amp;lt;Of TLocal&amp;gt;)&lt;br /&gt;其中第一个参数为数据集;&lt;br /&gt;第二个参数是一个Func委托，用于在每个线程执行前进行初始化;&lt;br /&gt;第 三个参数是委托Func&amp;lt;Of T1,T2,T3,TResult&amp;gt;,它能对数据集的每个成员进行迭代，当中T1是数据集的成员，T2是一个ParallelLoopState对 象，它可以控制迭代的状态，T3是线程中的本地变量;&lt;br /&gt;第四个参数是一个Action委托，用于对每个线程的最终状态进行最终操作。&lt;/p&gt;&lt;p&gt;在以下例子中，使用ForEach计算多个Order的总体价格。在ForEach方法中，首先把参数初始化为0f，然后用把同一个Order的多个OrderItem价格进行累加，计算出Order的价格，最后把多个Order的价格进行累加，计算出多个Order的总体价格。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Order&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; ID;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;float&lt;/span&gt; Price;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderItem&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; ID;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Goods;&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; OrderID;&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;float&lt;/span&gt; Price;&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Count;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;设置最大线程数&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;float&lt;/span&gt; totalPrice = 0f;&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;并行查询&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; parallelResult = Parallel.ForEach(GetOrderList(),&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;                      () =&amp;gt; 0f,   &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把参数初始值设为0&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;                      (order, state, orderPrice) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;                      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;                          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算单个Order的价格&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;                          orderPrice = GetOrderItem().Where(item =&amp;gt; item.OrderID == order.ID)&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                               .Sum(item =&amp;gt; item.Price * item.Count);&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;                          order.Price = orderPrice;&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;                          ThreadPoolMessage(order);&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;                          &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;                          &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderPrice;&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;                      },&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                     (finallyPrice) =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                         totalPrice += finallyPrice;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算多个Order的总体价格&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;                 );&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;while&lt;/span&gt; (!parallelResult.IsCompleted)&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Doing Work!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Total Price is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + totalPrice);&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//虚拟数据&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; IList&amp;lt;Order&amp;gt; GetOrderList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;             IList&amp;lt;Order&amp;gt; orderList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Order&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;             Order order1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Order();&lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;             order1.ID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;             orderList.Add(order1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;             ............&lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//虚拟数据&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; IList&amp;lt;OrderItem&amp;gt; GetOrderItem()&lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;             IList&amp;lt;OrderItem&amp;gt; itemList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;OrderItem&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt;             OrderItem orderItem1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderItem();&lt;br /&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt;             orderItem1.ID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;65&lt;/span&gt;             orderItem1.Goods = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;iPhone 4S&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;66&lt;/span&gt;             orderItem1.Price = &lt;span style="color: #800080;"&gt;6700&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;67&lt;/span&gt;             orderItem1.Count = &lt;span style="color: #800080;"&gt;2&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;68&lt;/span&gt;             orderItem1.OrderID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;69&lt;/span&gt;             itemList.Add(orderItem1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;70&lt;/span&gt;             ...........&lt;br /&gt;&lt;span style="color: #008080;"&gt;71&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; itemList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;72&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;73&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;74&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;75&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(Order order)&lt;br /&gt;&lt;span style="color: #008080;"&gt;76&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;77&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;78&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;79&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;OrderID:{0}  OrderPrice:{1}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;80&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CurrentThreadId is {2}\n  WorkerThreads is:{3}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;81&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CompletionPortThreads is:{4}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;82&lt;/span&gt;                   order.ID, order.Price,&lt;br /&gt;&lt;span style="color: #008080;"&gt;83&lt;/span&gt;                   Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;84&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;85&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;86&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;87&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012020313524550.jpg" alt="" width="549" height="177" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;strong&gt;7.2.2 任务并行&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在TPL当中还可以使用Parallel.Invoke方法触发多个异步任务,其中 actions 中可以包含多个方法或者委托，parallelOptions用于配置Parallel类的操作。&lt;br /&gt;public static void Invoke(Action[] actions )&lt;br /&gt;public static void Invoke(ParallelOptions parallelOptions, Action[] actions )&lt;br /&gt;下面例子中利用了Parallet.Invoke并行查询多个Person，actions当中可以绑定方法、lambda表达式或者委托，注意绑定方法时必须是返回值为void的无参数方法。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;设置最大线程数&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;任务并行&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             Parallel.Invoke(option,&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                 PersonMessage, &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                 ()=&amp;gt;ThreadPoolMessage(GetPersonList()[&lt;span style="color: #800080;"&gt;1&lt;/span&gt;]),  &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt;(){&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                     ThreadPoolMessage(GetPersonList()[&lt;span style="color: #800080;"&gt;2&lt;/span&gt;]);&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 });&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; PersonMessage()&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             ThreadPoolMessage(GetPersonList()[&lt;span style="color: #800080;"&gt;0&lt;/span&gt;]);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(Person person)&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Person  ID:{0} Name:{1} Age:{2}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CurrentThreadId is {3}\n  WorkerThreads is:{4}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CompletionPortThreads is :{5}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;                   person.ID, person.Name, person.Age,&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;                   Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;模拟源数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Person&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person();&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;             person1.ID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;             person1.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;             person1.Age = &lt;span style="color: #800080;"&gt;30&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;             personList.Add(person1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;             ..........&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012020319105490.jpg" alt="" width="555" height="207" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;7.3 Task简介&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;以Thread创建的线程被默认为前台线程，当然你可以把线程IsBackground属性设置为true，但TPL为此提供了一个更简单的类Task。&lt;br /&gt;Task存在于System.Threading.Tasks命名空间当中，它可以作为异步委托的简单替代品。&lt;br /&gt;通过Task的Factory属性将返回TaskFactory类，以TaskFactory.StartNew（Action）方法可以创建一个新线程，所创建的线程默认为后台线程。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             Task.Factory.StartNew(() =&amp;gt; ThreadPoolMessage());&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage()&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;CurrentThreadId is:{0}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                 &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;CurrentThread IsBackground:{1}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                 &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;WorkerThreads is:{2}\nCompletionPortThreads is:{3}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                  Thread.CurrentThread.ManagedThreadId,&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                  Thread.CurrentThread.IsBackground.ToString(),&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                  a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012020515044559.jpg" alt="" width="554" height="115" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;若要取消处理，可以利用CancellationTakenSource对象，在TaskFactory中包含有方法&lt;br /&gt;public Task StartNew( Action action, CancellationToken cancellationToken )&lt;br /&gt;在方法中加入CancellationTakenSource对象的CancellationToken属性，可以控制任务的运行，调用CancellationTakenSource.Cancel时任务就会自动停止。下面以图片下载为例子介绍一下TaskFactory的使用。&lt;/p&gt;&lt;p&gt;服务器端页面&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;html &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;xmlns&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="http://www.w3.org/1999/xhtml"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;head &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;title&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;script &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;type&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="text/C#"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        private static List&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;string&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; url&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; List&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;string&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&amp;gt;&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        protected &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; Page_Load(object sender, EventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;if&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; (&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;!&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;Page.IsPostBack)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;                url.Clear();&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;                Application[&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;Url&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;] &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;null&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        protected &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; CheckBox_CheckedChanged(object sender, EventArgs e)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        {&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            CheckBox checkBox &lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; (CheckBox)sender;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;if&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; (checkBox.Checked)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;                url.Add(checkBox.Text);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;span style="background-color: #f5f5f5; color: #0000ff;"&gt;else&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;                url.Remove(checkBox.Text);&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;            Application[&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;Url&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;"&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;]&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt;=&lt;/span&gt;&lt;span style="background-color: #f5f5f5; color: #000000;"&gt; url;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt; &lt;span style="background-color: #f5f5f5; color: #000000;"&gt;        }&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;script&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;head&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;form &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;id&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="form1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;align&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="left"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;align&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="center"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; style&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="float: left;"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Image &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Image1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; ImageUrl&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="~/Images/A.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:CheckBox &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox1"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; AutoPostBack&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="True"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;span style="color: #ff0000;"&gt;               oncheckedchanged&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox_CheckedChanged"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; Text&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="A.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;align&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="center"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; style&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="float: left"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Image &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Image2"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; ImageUrl&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="~/Images/B.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:CheckBox &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox2"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; AutoPostBack&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="True"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt; &lt;span style="color: #ff0000;"&gt;               oncheckedchanged&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox_CheckedChanged"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; Text&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="B.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;align&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="center"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; style&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="float: left"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Image &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Image3"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; ImageUrl&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="~/Images/C.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:CheckBox &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox3"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; AutoPostBack&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="True"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt; &lt;span style="color: #ff0000;"&gt;               oncheckedchanged&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox_CheckedChanged"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; Text&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="C.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;align&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="center"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; style&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="float: left"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Image &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Image4"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; ImageUrl&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="~/Images/D.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:CheckBox &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox4"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; AutoPostBack&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="True"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt; &lt;span style="color: #ff0000;"&gt;               oncheckedchanged&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox_CheckedChanged"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; Text&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="D.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;div &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;align&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="center"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; style&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="float: left"&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:Image &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="Image5"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; ImageUrl&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="~/Images/E.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;br &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000;"&gt;asp:CheckBox &lt;/span&gt;&lt;span style="color: #ff0000;"&gt;ID&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox5"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; runat&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="server"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; AutoPostBack&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="True"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt; &lt;span style="color: #ff0000;"&gt;               oncheckedchanged&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="CheckBox_CheckedChanged"&lt;/span&gt;&lt;span style="color: #ff0000;"&gt; Text&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;="E.jpg"&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;        &lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;div&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;form&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;body&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000;"&gt;html&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&amp;gt;&lt;/span&gt;&lt;/div&gt;&lt;p&gt;首先在服务器页面中显示多个*.jpg图片，每个图片都有对应的CheckBox检测其选择情况。&lt;br /&gt;所选择图片的路径会记录在Application["Url"]当中传递到Handler.ashx当中。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;strong&gt;&lt;em&gt;注意：Application是一个全局变量，此处只是为了显示Task的使用方式，在ASP.NET开发应该慎用Application。&lt;/em&gt;&lt;/strong&gt;&lt;/div&gt;&lt;p&gt;Handler.ashx 处理图片的下载，它从 Application["Url"] 当中获取所选择图片的路径，并把图片转化成byte[]二进制数据。&lt;br /&gt;再把图片的数量，每副图片的二进制数据的长度记录在OutputStream的头部。&lt;br /&gt;最后把图片的二进制数据记入 OutputStream 一并输出。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Handler : IHttpHandler &lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ProcessRequest(HttpContext context)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取图片名，把图片数量写OutputStream&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         List&amp;lt;String&amp;gt; urlList = (List&amp;lt;&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&amp;gt;)context.Application[&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Url&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;];&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         context.Response.OutputStream.Write(BitConverter.GetBytes(urlList.Count), &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, &lt;span style="color: #800080;"&gt;4&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把图片转换成二进制数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         List&amp;lt;&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&amp;gt; imageList = GetImages(urlList);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把每副图片长度写入OutputStream&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; image &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; imageList)&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] imageByte=Convert.FromBase64String(image);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             context.Response.OutputStream.Write(BitConverter.GetBytes(imageByte.Length),&lt;span style="color: #800080;"&gt;0&lt;/span&gt;,&lt;span style="color: #800080;"&gt;4&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把图片写入OutputStream&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; image &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; imageList)&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] imageByte = Convert.FromBase64String(image);&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             context.Response.OutputStream.Write(imageByte,&lt;span style="color: #800080;"&gt;0&lt;/span&gt;,imageByte.Length);&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取多个图片的二进制数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; List&amp;lt;&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&amp;gt; GetImages(List&amp;lt;&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&amp;gt; urlList)&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         List&amp;lt;&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&amp;gt; imageList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; url &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; urlList)&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             imageList.Add(GetImage(url));&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; imageList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;     &lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取单副图片的二进制数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; GetImage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; url)&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; path = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;E:/My Projects/Example/WebSite/Images/&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+url;&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;         FileStream stream = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; FileStream(path, FileMode.Open, FileAccess.Read);&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] imgBytes = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[&lt;span style="color: #800080;"&gt;10240&lt;/span&gt;];&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; imgLength = stream.Read(imgBytes, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, &lt;span style="color: #800080;"&gt;10240&lt;/span&gt;);       &lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; Convert.ToBase64String(imgBytes,&lt;span style="color: #800080;"&gt;0&lt;/span&gt;,imgLength);&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt; IsReusable&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;{ &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;false&lt;/span&gt;;}&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;客户端&lt;/p&gt;&lt;p&gt;建立一个WinForm窗口，里面加入一个WebBrowser连接到服务器端的Default.aspx页面。&lt;br /&gt;当按下Download按键时，系统就会利用TaskFactory.StartNew的方法建立异步线程，使用WebRequest方法向Handler.ashx发送请求。&lt;br /&gt;接收到回传流时，就会根据头文件的内容判断图片的数量与每副图片的长度，把二进制数据转化为*.jpg文件保存。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012020516260851.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;系统利用TaskFactory.StartNew(action,cancellationToken) 方式异步调用GetImages方法进行图片下载。 &lt;br /&gt;当用户按下Cancel按钮时，异步任务就会停止。值得注意的是，在图片下载时调用了CancellationToken.ThrowIfCancellationRequested方法，目的在检查并行任务的运行情况，在并行任务被停止时释放出OperationCanceledException异常，确保用户按下Cancel按钮时，停止所有并行任务。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;partial&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Form1 : Form&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; CancellationTokenSource tokenSource = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; CancellationTokenSource();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Form1()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             InitializeComponent();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; downloadToolStripMenuItem_Click(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; sender, EventArgs e)&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;              Task.Factory.StartNew(GetImages,tokenSource.Token);&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; cancelToolStripMenuItem_Click(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; sender, EventArgs e)&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             tokenSource.Cancel();&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; GetImages()&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;发送请求，获取输出流&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             WebRequest webRequest = HttpWebRequest.Create(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Http://localhost:5800/Handler.ashx&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;); &lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             Stream responseStream=webRequest.GetResponse().GetResponseStream();&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[] responseByte = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;byte&lt;/span&gt;[&lt;span style="color: #800080;"&gt;81960&lt;/span&gt;];&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             IAsyncResult result=responseStream.BeginRead(responseByte,&lt;span style="color: #800080;"&gt;0&lt;/span&gt;,&lt;span style="color: #800080;"&gt;81960&lt;/span&gt;,&lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;,&lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; responseLength = responseStream.EndRead(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取图片数量&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; imageCount = BitConverter.ToInt32(responseByte, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取每副图片的长度&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;[] lengths = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;[imageCount];&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; n &amp;lt; imageCount; n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; length = BitConverter.ToInt32(responseByte, (n + &lt;span style="color: #800080;"&gt;1&lt;/span&gt;) * &lt;span style="color: #800080;"&gt;4&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                 lengths[n] = length;&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;                 &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;保存图片&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; n &amp;lt; imageCount; n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;                 {&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; path = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;E:/My Projects/Example/Test/Images/pic{0}.jpg&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, n);&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;                     FileStream file = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; FileStream(path, FileMode.Create, FileAccess.ReadWrite);&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;                     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算字节偏移量&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; offset = (imageCount + &lt;span style="color: #800080;"&gt;1&lt;/span&gt;) * &lt;span style="color: #800080;"&gt;4&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;                     &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; a &amp;lt; n; a++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;                         offset += lengths[a];&lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;                     file.Write(responseByte, offset, lengths[n]);&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;                     file.Flush();&lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;                     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;模拟操作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt;                     Thread.Sleep(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;                     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;检测CancellationToken变化&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;                     tokenSource.Token.ThrowIfCancellationRequested();&lt;br /&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt;                 }&lt;br /&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (OperationCanceledException ex)&lt;br /&gt;&lt;span style="color: #008080;"&gt;65&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;66&lt;/span&gt;                 MessageBox.Show(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Download cancel!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;67&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;68&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;69&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;7.4 并行查询（PLINQ）&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;span id="mt5" class="sentence" data-guid="1aa66ef20f1c51de6dcfb564a328e630" data-source="Parallel LINQ (PLINQ) is a parallel implementation of the LINQ pattern."&gt;并行 LINQ (PLINQ) 是 LINQ 模式的并行实现，&lt;/span&gt;&lt;span id="mt8" class="sentence" data-guid="b8bb25776bfbf48ac72fcdef0306f18e" data-source="The primary difference is that PLINQ attempts to make full use of all the processors on the system."&gt;主要区别在于 PLINQ 尝试充分利用系统中的所有处理器。&lt;/span&gt; &lt;span id="mt9" class="sentence" data-guid="3b0f84d179d033b16db31773d82e4d5e" data-source="It does this by partitioning the data source into segments, and then executing the query on each segment on separate worker threads in parallel on multiple processors."&gt;它利用所有处理器的方法，把数据源分成片段，然后在多个处理器上对单独工作线程上的每个片段并行执行查询，&lt;/span&gt; &lt;span id="mt10" class="sentence" data-guid="723bdc77d118604475dfef20f2cb0da2" data-source="In many cases, parallel execution means that the query runs significantly faster."&gt;在许多情况下，并行执行意味着查询运行速度显著提高。但这并不说明所有PLINQ都会使用并行方式，当系统测试要并行查询会对系统性能造成损害时，那将自动化地使用同步执行。&lt;br /&gt;在System.Linq.ParallelEnumerable类中，包含了并行查询的大部分方法。&lt;/span&gt;&lt;br /&gt;&amp;nbsp;&lt;/p&gt;&lt;table style="width: 700px;" border="1" cellspacing="3"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="font-size: 12px;"&gt;方法成员　&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/td&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;&lt;span style="font-size: 12px;"&gt;说明&lt;/span&gt;&lt;/strong&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;            AsParallel          &lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt29" class="sentence" data-source="The entry point for PLINQ." data-guid="7cc0db4cadc2c42507021cbbeab87281"&gt;PLINQ 的入口点。&lt;/span&gt; &lt;span id="mt30" class="sentence" data-source="Specifies that the rest of the query should be parallelized, if it is possible." data-guid="bf6281d7be373167af134145a17a30b4"&gt;指定如果可能，应并行化查询的其余部分。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;            AsSequential&lt;span&gt;(Of &lt;/span&gt;TSource&lt;span&gt;)&lt;/span&gt;          &lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt31" class="sentence" data-source="Specifies that the rest of the query should be run sequentially, as a non-parallel LINQ query." data-guid="ee2a3f16d7860ec39903c9afc4c2922e"&gt;指定查询的其余部分应像非并行 LINQ 查询一样按顺序运行。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;            AsOrdered          &lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt32" class="sentence" data-source="Specifies that PLINQ should preserve the ordering of the source sequence for the rest of the query, or until the ordering is changed, for example by the use of an orderby (Order By in Vlsual Basic) clause." data-guid="2388bf20a69191549ce34c33bbf6f616"&gt;指定 PLINQ 应保留查询的其余部分的源序列排序，直到例如通过使用 orderby（在 Visual Basic 中为 Order By）子句更改排序为止。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;            AsUnordered&lt;span&gt;(Of &lt;/span&gt;TSource&lt;span&gt;)&lt;/span&gt;          &lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt33" class="sentence" data-source="Specifies that PLINQ for the rest of the query is not required to preserve the ordering of the source sequence." data-guid="eeebec79eae5f16c63444c8f537f85f0"&gt;指定查询的其余部分的 PLINQ 不需要保留源序列的排序。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;            WithCancellation&lt;span&gt;(Of &lt;/span&gt;TSource&lt;span&gt;)&lt;/span&gt;          &lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt34" class="sentence" data-source="Specifies that PLINQ should periodically monitor the state of the provided cancellation token and cancel execution if it is requested." data-guid="b05fe423cfe2e79f702dc2588fe86be0"&gt;指定 PLINQ 应定期监视请求取消时提供的取消标记和取消执行的状态。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;            WithDegreeOfParallelism&lt;span&gt;(Of &lt;/span&gt;TSource&lt;span&gt;)&lt;/span&gt;          &lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt35" class="sentence" data-source="Specifies the maximum number of processors that PLINQ should use to parallelize the query." data-guid="5a23e32ba3ba3946ddf95a66642590ab"&gt;指定 PLINQ 应当用来并行化查询的处理器的最大数目。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;            WithMergeOptions&lt;span&gt;(Of &lt;/span&gt;TSource&lt;span&gt;)&lt;/span&gt;          &lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt36" class="sentence" data-source="Provides a hint about how PLINQ should, if it is possible, merge parallel results back into just one sequence on the consuming thread. " data-guid="34ebc0559e478599a495d1af106f078d"&gt;提供有关 PLINQ 应当如何（如果可能）将并行结果合并回到使用线程上的一个序列的提示。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;            WithExecutionMode&lt;span&gt;(Of &lt;/span&gt;TSource&lt;span&gt;)&lt;/span&gt;          &lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt37" class="sentence" data-source="Specifies whether PLINQ should parallelize the query even when the default behavior would be to run it sequentially." data-guid="edb307d2c77973a51ca9f9b07bd1a856"&gt;指定 PLINQ 应当如何并行化查询（即使默认行为是按顺序运行查询）。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;            ForAll&lt;span&gt;(Of &lt;/span&gt;TSource&lt;span&gt;)&lt;/span&gt;          &lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt38" class="sentence" data-source="A multithreaded enumeration method that, unlike iterating over the results of the query, enables results to be processed in parallel without first merging back to the consumer thread." data-guid="302e5da9b3a30ad8cd3a855a73d9bcb0"&gt;多线程枚举方法，与循环访问查询结果不同，它允许在不首先合并回到使用者线程的情况下并行处理结果。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;p&gt;&lt;span&gt;Aggregate&lt;/span&gt; 重载&lt;/p&gt;&lt;/td&gt;&lt;td&gt;&lt;p&gt;&lt;span id="mt40" class="sentence" data-source="An overload that is unique to PLINQ and enables intermediate aggregation over thread-local partitions, plus a final aggregation function to combine the results of all partitions." data-guid="f951306e2e229317f266af55ab6a60d7"&gt;对于 PLINQ 唯一的重载，它启用对线程本地分区的中间聚合以及一个用于合并所有分区结果的最终聚合函数。&lt;/span&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&lt;span class="sentence" data-guid="723bdc77d118604475dfef20f2cb0da2" data-source="In many cases, parallel execution means that the query runs significantly faster."&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span class="sentence" data-guid="723bdc77d118604475dfef20f2cb0da2" data-source="In many cases, parallel execution means that the query runs significantly faster."&gt;&lt;strong&gt;7.4.1 AsParallel&lt;/strong&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span id="mt10" class="sentence" data-guid="723bdc77d118604475dfef20f2cb0da2" data-source="In many cases, parallel execution means that the query runs significantly faster."&gt;通常&lt;span id="mt11" class="sentence SentenceHover" data-guid="f4aa85aeb2cbafe6c0efd7bc9a09f4bf" data-source="Through parallel execution, PLINQ can achieve significant performance improvements over legacy code for certain kinds of queries, often just by adding the &amp;lt;span&amp;gt;&amp;lt;span class=&amp;quot;nolink&amp;quot;&amp;gt;AsParallel&amp;lt;/span&amp;gt;&amp;lt;/span&amp;gt; query operation to the data source."&gt;想要实现并行查询，只需向数据源添加 &lt;span&gt;&lt;span class="nolink"&gt;AsParallel&lt;/span&gt;&lt;/span&gt; 查询操作即可。&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList=GetPersonList().AsParallel() &lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                    .Where(x=&amp;gt;x.Age&amp;gt;&lt;span style="color: #800080;"&gt;30&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;模拟源数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Person&amp;gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             person1.ID = &lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             person1.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             person1.Age = &lt;span style="color: #800080;"&gt;30&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             personList.Add(person1);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             ...........&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personList;&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;7.4.2 AsOrdered&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;span id="mt56" class="sentence" data-guid="4d0e4fc4584ea154fe9a2518f50486c2" data-source="In some queries, a query operator must produce results that preserve the ordering of the source sequence."&gt;若要使查询结果必须保留源序列排序方式，可以使用AsOrdered方法。&lt;/span&gt; &lt;br /&gt;AsOrdered依然使用并行方式，只是在查询过程加入额外信息，在并行结束后把查询结果再次进行排列。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList=GetPersonList().AsParallel().AsOrdered()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 .Where(x=&amp;gt;x.Age&amp;lt;&lt;span style="color: #800080;"&gt;30&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #000000;"&gt;IList&amp;lt;Person&amp;gt;&lt;/span&gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         {......}&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;strong&gt;7.4.3 WithDegreeOfParallelism&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;默认情况下，PLINQ 使用主机上的所有处理器，这些处理器的数量最多可达 64 个。&lt;br /&gt;通过使用 WithDegreeOfParallelism(Of TSource) 方法，可以指示 PLINQ 使用不多于指定数量的处理器。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; personList=GetPersonList().AsParallel().WithDegreeOfParallelism(2)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 .Where(x=&amp;gt;x.Age&amp;lt;&lt;span style="color: #800080;"&gt;30&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         {.........}&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;7.4.4 ForAll&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;如果要对并行查询结果进行操作，一般会在for或foreach中执行，执行枚举操作时会使用同步方式。&lt;br /&gt;有见及此，PLINQ中包含了ForAll方法，它可以使用并行方式对数据集进行操作。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             GetPersonList().AsParallel().ForAll(person =&amp;gt;{&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 ThreadPoolMessage(person);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             });&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         {.......}&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(Person person)&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Person  ID:{0} Name:{1} Age:{2}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CurrentThreadId is {3}\n  WorkerThreads is:{4}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CompletionPortThreads is :{5}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                   person.ID, person.Name, person.Age,&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                   Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012020711430967.jpg" alt="" width="539" height="200" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;7.4.5 WithCancellation&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;如果需要停止查询，可以使用 WithCancellation(Of TSource) 运算符并提供 CancellationToken 实例作为参数。 &lt;br /&gt;与第三节Task的例子相似，如果标记上的 IsCancellationRequested 属性设置为 true，则 PLINQ 将会注意到它，并停止所有线程上的处理，然后引发 OperationCanceledException。这可以保证并行查询能够立即停止。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; CancellationTokenSource tokenSource = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; CancellationTokenSource();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Task.Factory.StartNew(Cancel);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                 GetPersonList().AsParallel().WithCancellation(tokenSource.Token)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                     .ForAll(person =&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                         ThreadPoolMessage(person);&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                     });&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (OperationCanceledException ex)&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             { }&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在10~50毫秒内发出停止信号&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Cancel()&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             Random random = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Random();&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             Thread.Sleep(random.Next(&lt;span style="color: #800080;"&gt;10&lt;/span&gt;,&lt;span style="color: #800080;"&gt;50&lt;/span&gt;));&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             tokenSource.Cancel();&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetPersonList()&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         {......}&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(Person person)&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Person  ID:{0} Name:{1} Age:{2}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CurrentThreadId is {3}\n  WorkerThreads is:{4}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                   &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  CompletionPortThreads is :{5}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;                   person.ID, person.Name, person.Age,&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;                   Thread.CurrentThread.ManagedThreadId, a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;          &lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a name="t8"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;八、定时器与锁&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;8.1定时器&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;若要长期定时进行一些工作，比如像邮箱更新，实时收听信息等等，可以利用定时器Timer进行操作。&lt;br /&gt;在System.Threading命名空间中存在Timer类与对应的TimerCallback委托，它可以在后台线程中执行一些长期的定时操作，使主线程不受干扰。&lt;br /&gt;Timer类中最常用的构造函数为 public Timer( timerCallback , object , int , int )&lt;br /&gt;timerCallback委托可以绑定执行方法，执行方法必须返回void，它可以是无参数方法，也可以带一个object参数的方法。&lt;br /&gt;第二个参数是为 timerCallback 委托输入的参数对象。&lt;br /&gt;第三个参数是开始执行前等待的时间。&lt;br /&gt;第四个参数是每次执行之间的等待时间。&lt;/p&gt;&lt;p&gt;开发实例&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             TimerCallback callback = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TimerCallback(ThreadPoolMessage);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             Timer t = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Timer(callback,&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello Jack! &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #800080;"&gt;0&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程池现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadPoolMessage(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a, b;&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             ThreadPool.GetAvailableThreads(&lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; a, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; b);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n   CurrentThreadId is:{1}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                 &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;   CurrentThread IsBackground:{2}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                 &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;   WorkerThreads is:{3}\n   CompletionPortThreads is:{4}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                  data + &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Time now is &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + DateTime.Now.ToLongTimeString(),&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                  Thread.CurrentThread.ManagedThreadId,&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                  Thread.CurrentThread.IsBackground.ToString(),&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                  a.ToString(), b.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;注意观察运行结果，每次调用Timer绑定的方法时不一定是使用同一线程，但线程都会是来自工作者线程的后台线程。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012020713095890.jpg" alt="" width="546" height="277" /&gt;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;&lt;strong&gt;8.2 锁&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在使用多线程开发时，存在一定的共用数据，为了避免多线程同时操作同一数据，.NET提供了lock、Monitor、Interlocked等多个锁定数据的方式。&lt;/p&gt;&lt;p&gt;&lt;strong&gt;8.2.1 lock&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;lock的使用比较简单，如果需要锁定某个对象时，可以直接使用lock(this)的方式。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method()&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;lock&lt;/span&gt;(&lt;span style="color: #0000ff;"&gt;this&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;           &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在此进行的操作能保证在同一时间内只有一个线程对此对象操作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;如果操作只锁定某段代码，可以事先建立一个object对象，并对此对象进行操作锁定，这也是.net提倡的锁定用法。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Control&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; obj=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;       &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;lock&lt;/span&gt;(obj)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             {.......}&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;8.2.2 Montior&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Montior存在于System.Thread命名空间内，相比lock，Montior使用更灵活。&lt;br /&gt;它存在 Enter, Exit 两个方法，它可以对对象进行锁定与解锁，比lock使用更灵活。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Control&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; obj=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt;();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Monitor.Enter(obj);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             {......}&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;(Excetion ex)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             {......}&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;finally&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 Monitor.Exit(obj);&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;          &lt;/div&gt;&lt;p&gt;使用try的方式，能确保程序不会因死锁而释放出异常！&lt;br /&gt;而且在finally中释放obj对象能够确保无论是否出现死锁状态，系统都会释放obj对象。&lt;br /&gt;而且Monitor中还存在Wait方法可以让线程等待一段时间，然后在完成时使用Pulse、PulseAll等方法通知等待线程。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;8.2.3 Interlocked&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Interlocked存在于System.Thread命名空间内，它的操作比Monitor使用更简单。&lt;br /&gt;它存在CompareExchange、Decrement、Exchange、Increment等常用方法让参数在安全的情况进行数据交换。&lt;/p&gt;&lt;p&gt;Increment、Decrement 可以使参数安全地加1或减1并返回递增后的新值。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Example&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; a=&lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AddOne()&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; newA=Interlocked.Increment(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; a);&lt;br /&gt;&lt;span style="color: #008080;"&gt;8&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt;9&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;Exchange可以安全地变量赋值。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; SetData()&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;       Interlocked.Exchange(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; a,&lt;span style="color: #800080;"&gt;100&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;CompareExchange使用特别方便，它相当于if的用法，当a等于1时，则把100赋值给a。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; CompareAndExchange()&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;     Interlocked.CompareExchange(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; a,&lt;span style="color: #800080;"&gt;100&lt;/span&gt;,&lt;span style="color: #800080;"&gt;1&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;结束语&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;熟悉掌握多线程开发，对提高系统工作效率非常有帮助，尤其是回调方法与最近火热的并行编程更应该引起各位的重视。&lt;br /&gt;在下用了较长的时间总结所过的多线程开发方式，希望本篇文章能对各位的学习研究有所帮助，当中有所错漏的地方敬请点评。&lt;br /&gt;对.NET开发有兴趣的朋友请加入博客园讨论小组&lt;span style="color: #0000ff;"&gt;&lt;a href="http://home.cnblogs.com/group/102576/" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&amp;ldquo;.NET高级编程&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; 一起探讨！&lt;/p&gt;&lt;p&gt;&lt;span style="color: #ff0000;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;C#综合揭秘&lt;/span&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说进程、应用程序域与上下文&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;细说多线程（上）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说多线程（下）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说事务&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;深入分析委托与事件&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="float: right; text-align: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;a id="Editor_Edit_hlEntryLink" title="view: C#综合揭秘&amp;mdash;&amp;mdash;细说多线程（下）" href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; &lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;a title="http://www.cnblogs.com/leslies2" href="http://www.cnblogs.com/leslies2"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2320914.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html</id><title type="text">C#综合揭秘——细说多线程（上）</title><summary type="text">本文主要从线程的基础用法，CLR线程池当中工作者线程与I/O线程的开发，并行操作PLINQ等多个方面介绍多线程的开发。其中委托的BeginInvoke方法以及回调函数最为常用。而 I/O线程可能容易遭到大家的忽略，其实在开发多线程系统，更应该多留意I/O线程的操作。特别是在ASP.NET开发当中，可能更多人只会留意在客户端使用Ajax或者在服务器端使用UpdatePanel。其实合理使用I/O线程在通讯项目或文件下载时，能尽可能地减少IIS压力。并行编程是Framework4.0中极力推广的异步操作方式，更值得更深入地学习。</summary><published>2012-02-07T07:17:00Z</published><updated>2012-02-07T07:17:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html"/><content type="html">&lt;p&gt;&lt;script type="text/javascript"&gt;// &lt;![CDATA[   function showMessage(){      alert("非常抱歉，此博文尚未完成！");   }// ]]&gt;&lt;/script&gt;&lt;/p&gt;&lt;p&gt;&lt;a name="t0"&gt;&lt;/a&gt;引言&lt;/p&gt;&lt;p&gt;本文主要从线程的基础用法，CLR线程池当中工作者线程与I/O线程的开发，并行操作PLINQ等多个方面介绍多线程的开发。&lt;br /&gt;其中委托的BeginInvoke方法以及回调函数最为常用。&lt;br /&gt;而 I/O线程可能容易遭到大家的忽略，其实在开发多线程系统，更应该多留意I/O线程的操作。特别是在ASP.NET开发当中，可能更多人只会留意在客户端使用Ajax或者在服务器端使用UpdatePanel。其实合理使用I/O线程在通讯项目或文件下载时，能尽可能地减少IIS的压力。&lt;br /&gt;并行编程是Framework4.0中极力推广的异步操作方式，更值得更深入地学习。&lt;br /&gt;希望本篇文章能对各位的学习研究有所帮助，当中有所错漏的地方敬请点评。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;目录&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t1"&gt;&lt;span style="color: #0000ff;"&gt;一、线程的定义&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t2"&gt;&lt;span style="color: #0000ff;"&gt;二、线程的基础知识&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t3"&gt;&lt;span style="color: #0000ff;"&gt;三、以ThreadStart方式实现多线程&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t4"&gt;&lt;span style="color: #0000ff;"&gt;四、CLR线程池的工作者线程&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html#t5"&gt;&lt;span style="color: #0000ff;"&gt;五、CLR线程池的I/O线程&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html#t6"&gt;&lt;span style="color: #0000ff;"&gt;六、异步 SqlCommand&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html#t7"&gt;&lt;span style="color: #0000ff;"&gt;七、并行编程与PLINQ&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html#t8"&gt;&lt;span style="color: #0000ff;"&gt;八、计时器与锁&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a name="t1"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;一、线程的定义&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&amp;nbsp;1. 1 进程、应用程序域与线程的关系&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;进程（Process）是Windows系统中的一个基本概念，它包含着一个运行程序所需要的资源。进程之间是相对独立的，一个进程无法访问另一个进程的数据（除非利用分布式计算方式），一个进程运行的失败也不会影响其他进程的运行，Windows系统就是利用进程把工作划分为多个独立的区域的。进程可以理解为一个程序的基本边界。&lt;/p&gt;&lt;p&gt;应用程序域（AppDomain）是一个程序运行的逻辑区域，它可以视为一个轻量级的进程，.NET的程序集正是在应用程序域中运行的，一个进程可以包含有多个应用程序域，一个应用程序域也可以包含多个程序集。在一个应用程序域中包含了一个或多个上下文context，使用上下文CLR就能够把某些特殊对象的状态放置在不同容器当中。&lt;/p&gt;&lt;p&gt;线程（Thread）是进程中的基本执行单元，在进程入口执行的第一个线程被视为这个进程的主线程。在.NET应用程序中，都是以Main()方法作为入口的，当调用此方法时系统就会自动创建一个主线程。线程主要是由CPU寄存器、调用栈和线程本地存储器（Thread Local Storage，TLS）组成的。CPU寄存器主要记录当前所执行线程的状态，调用栈主要用于维护线程所调用到的内存与数据，TLS主要用于存放线程的状态信息。&lt;/p&gt;&lt;p&gt;进程、应用程序域、线程的关系如下图，一个进程内可以包括多个应用程序域，也有包括多个线程，线程也可以穿梭于多个应用程序域当中。但在同一个时刻，线程只会处于一个应用程序域内。&lt;/p&gt;&lt;p&gt;&lt;a name="a1"&gt;&lt;/a&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="border: 1px ridge #808080; display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2012/64989/2012010713392540.jpg" alt="" width="502" height="264" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;br /&gt;由于本文是以介绍多线程技术为主题，对进程、应用程序域的介绍就到此为止。关于进程、线程、应用程序域的技术，在&amp;ldquo;&lt;span style="color: #0000ff;"&gt;&lt;a id="cb_post_title_url" href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;C#综合揭秘&amp;mdash;&amp;mdash;细说进程、应用程序域与上下文&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&amp;rdquo;会有详细介绍。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1.2 多线程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在单CPU系统的一个单位时间（time slice）内，CPU只能运行单个线程，运行顺序取决于线程的优先级别。如果在单位时间内线程未能完成执行，系统就会把线程的状态信息保存到线程的本地存储器（TLS） 中，以便下次执行时恢复执行。而多线程只是系统带来的一个假像，它在多个单位时间内进行多个线程的切换。因为切换频密而且单位时间非常短暂，所以多线程可被视作同时运行。&lt;/p&gt;&lt;p&gt;适当使用多线程能提高系统的性能，比如：在系统请求大容量的数据时使用多线程，把数据输出工作交给异步线程，使主线程保持其稳定性去处理其他问题。但需要注意一点，因为CPU需要花费不少的时间在线程的切换上，所以过多地使用多线程反而会导致性能的下降。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a name="t2"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;返回目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;二、线程的基础知识&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.1 System.Threading.Thread类&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;System.Threading.Thread是用于控制线程的基础类，通过Thread可以控制当前应用程序域中线程的创建、挂起、停止、销毁。&lt;/p&gt;&lt;p&gt;它包括以下常用公共属性：&lt;/p&gt;&lt;table class="memberListTable" style="font-size: 14px; width: 600px;"&gt;&lt;colgroup&gt; &lt;col width="30%" /&gt; &lt;col width="70%" /&gt; &lt;/colgroup&gt;&lt;tbody&gt;&lt;tr&gt;&lt;th&gt;&lt;span style="font-size: 12px;"&gt;属性名称&lt;/span&gt;&lt;/th&gt;&lt;th&gt;&lt;span style="font-size: 12px;"&gt;说明&lt;/span&gt;&lt;/th&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;CurrentContext&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取线程正在其中执行的当前上下文。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;CurrentThread&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取当前正在运行的线程。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td valign="middle"&gt;&lt;span style="font-size: 12px;"&gt;ExecutionContext&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取一个 ExecutionContext 对象，该对象包含有关当前线程的各种上下文的信息。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;IsAlive&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取一个值，该值指示当前线程的执行状态。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;IsBackground&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取或设置一个值，该值指示某个线程是否为后台线程。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;IsThreadPoolThread&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取一个值，该值指示线程是否属于托管线程池。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;ManagedThreadId&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取当前托管线程的唯一标识符。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Name&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取或设置线程的名称。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Priority&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取或设置一个值，该值指示线程的调度优先级。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;ThreadState&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;获取一个值，该值包含当前线程的状态。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.1.1 线程的标识符&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;ManagedThreadId是确认线程的唯一标识符，程序在大部分情况下都是通过Thread.ManagedThreadId来辨别线程的。而Name是一个可变值，在默认时候，Name为一个空值 Null，开发人员可以通过程序设置线程的名称，但这只是一个辅助功能。&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.1.2 线程的优先级别&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;.NET为线程设置了Priority属性来定义线程执行的优先级别，里面包含5个选项，其中Normal是默认值。除非系统有特殊要求，否则不应该随便设置线程的优先级别。&lt;/p&gt;&lt;div&gt;&lt;table id="memberList" style="width: 600px;" border="0" cellpadding="1"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;th class="nameColumn"&gt;&lt;span style="font-size: 12px;"&gt;成员名称&lt;/span&gt;&lt;/th&gt;&lt;th class="descriptionColumn"&gt;&lt;span style="font-size: 12px;"&gt;说明&lt;/span&gt;&lt;/th&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span class="selflink" style="font-size: 12px;"&gt;Lowest&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;        &lt;span id="xn2_3e53547e0e9a509aff4a76382e494083" class="sentence"&gt;可以将 Thread 安排在具有任何其他优先级的线程之后。&lt;/span&gt;      &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span class="selflink" style="font-size: 12px;"&gt;BelowNormal&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;        &lt;span id="xn3_f979b4a5dfbb5a35942312092b2cd47a" class="sentence"&gt;可以将 Thread 安排在具有 &lt;span class="input"&gt;Normal&lt;/span&gt; 优先级的线程之后，在具有 &lt;span class="input"&gt;Lowest&lt;/span&gt; 优先级的线程之前。&lt;/span&gt;      &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span class="selflink" style="font-size: 12px;"&gt;Normal&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;        &lt;span id="xn4_8b94d9644aacd17640f4971fc6e79dc7" class="sentence"&gt;默认选择。可以将 Thread 安排在具有 &lt;span class="input"&gt;AboveNormal&lt;/span&gt; 优先级的线程之后，在具有 &lt;span class="input"&gt;BelowNormal&lt;/span&gt; 优先级的线程之前&lt;/span&gt;&lt;span id="xn5_6fa67ded483ad3d242ea365f0ac225c4" class="sentence"&gt;。&lt;/span&gt;  &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span class="selflink" style="font-size: 12px;"&gt;AboveNormal&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;        &lt;span id="xn6_d067edb8ea0b5bfd51a2591334b86fd7" class="sentence"&gt;可以将 Thread 安排在具有 &lt;span class="input"&gt;Highest&lt;/span&gt; 优先级的线程之后，在具有 &lt;span class="input"&gt;Normal&lt;/span&gt; 优先级的线程之前。&lt;/span&gt;      &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span class="selflink" style="font-size: 12px;"&gt;Highest&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;        &lt;span id="xn7_fc7a0e931c772d08fc98b6de2c82ab3c" class="sentence"&gt;可以将 Thread 安排在具有任何其他优先级的线程之前。&lt;/span&gt;      &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;p&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.1.3 线程的状态&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;通过ThreadState可以检测线程是处于Unstarted、Sleeping、Running 等等状态，它比 IsAlive 属性能提供更多的特定信息。&lt;/p&gt;&lt;p&gt;前面说过，一个应用程序域中可能包括多个上下文，而通过CurrentContext可以获取线程当前的上下文。&lt;/p&gt;&lt;p&gt;CurrentThread是最常用的一个属性，它是用于获取当前运行的线程。&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.1.4 System.Threading.Thread的方法&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Thread 中包括了多个方法来控制线程的创建、挂起、停止、销毁，以后来的例子中会经常使用。&lt;/p&gt;&lt;table class="memberListTable" style="font-size: 14px; width: 600px;"&gt;&lt;colgroup&gt; &lt;col width="30%" /&gt; &lt;col width="70%" /&gt; &lt;/colgroup&gt;&lt;tbody&gt;&lt;tr&gt;&lt;th&gt;&lt;span style="font-size: 12px;"&gt;方法名称&lt;/span&gt;&lt;/th&gt;&lt;th&gt;&lt;span style="font-size: 12px;"&gt;说明&lt;/span&gt;&lt;/th&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Abort()&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;终止本线程。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;GetDomain()&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;返回当前线程正在其中运行的当前域。 &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;GetDomainId()&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;返回当前线程正在其中运行的当前域Id。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Interrupt()&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;中断处于 WaitSleepJoin 线程状态的线程。 &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Join()&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;已重载。 阻塞调用线程，直到某个线程终止时为止。 &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt; Resume()&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;继续运行已挂起的线程。 &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Start()&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;执行本线程。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Suspend()&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;挂起当前线程，如果当前线程已属于挂起状态则此不起作用&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Sleep()&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;把正在运行的线程挂起一段时间。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.1.5 开发实例&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;以下这个例子，就是通过Thread显示当前线程信息&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;             Thread thread = Thread.CurrentThread;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;             thread.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; threadMessage = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Thread ID:{0}\n    Current AppDomainId:{1}\n    &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                 &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Current ContextId:{2}\n    Thread Name:{3}\n    &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Thread State:{4}\n    Thread Priority:{5}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                 thread.ManagedThreadId, Thread.GetDomainID(), Thread.CurrentContext.ContextID,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 thread.Name, thread.ThreadState, thread.Priority);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             Console.WriteLine(threadMessage);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012010718230274.jpg" alt="" width="553" height="148" /&gt;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.2&amp;nbsp; System.Threading 命名空间&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在System.Threading命名空间内提供多个方法来构建多线程应用程序,其中ThreadPool与Thread是多线程开发中最常用到的，在.NET中专门设定了一个CLR线程池专门用于管理线程的运行，这个CLR线程池正是通过ThreadPool类来管理。而Thread是管理线程的最直接方式，下面几节将详细介绍有关内容。&lt;/p&gt;&lt;table class="memberListTable" style="width: 600px;"&gt;&lt;tbody&gt;&lt;tr valign="top"&gt;&lt;td style="text-align: center; width: 30%;"&gt;&lt;span style="font-size: 12px;"&gt;&lt;strong&gt;类&lt;/strong&gt;&lt;/span&gt;&lt;/td&gt;&lt;td style="text-align: center; width: 70%;"&gt;&lt;span style="font-size: 12px;"&gt;&lt;strong&gt;说明&lt;/strong&gt;&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;AutoResetEvent&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;通知正在等待的线程已发生事件。无法继承此类。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;ExecutionContext&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;管理当前线程的执行上下文。无法继承此类。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Interlocked&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;为多个线程共享的变量提供原子操作。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Monitor&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;提供同步对对象的访问的机制。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Mutex&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;一个同步基元，也可用于进程间同步。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Thread&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;创建并控制线程，设置其优先级并获取其状态。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;ThreadAbortException&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;在对 Abort 方法进行调用时引发的异常。无法继承此类。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td valign="middle"&gt;&lt;span style="font-size: 12px;"&gt;ThreadPool&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;提供一个线程池，该线程池可用于发送工作项、处理异步 I/O、代表其他线程等待以及处理计时器。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Timeout&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;包含用于指定无限长的时间的常数。无法继承此类。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;Timer&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;提供以指定的时间间隔执行方法的机制。无法继承此类。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;WaitHandle&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;封装等待对共享资源的独占访问的操作系统特定的对象。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&lt;br /&gt;在System.Threading中的包含了下表中的多个常用委托，其中ThreadStart、ParameterizedThreadStart是最常用到的委托。&lt;br /&gt;由ThreadStart生成的线程是最直接的方式，但由ThreadStart所生成并不受线程池管理。&lt;br /&gt;而ParameterizedThreadStart是为异步触发带参数的方法而设的，在下一节将为大家逐一细说。&lt;/p&gt;&lt;table class="memberListTable" style="width: 600px; font-size: 14px;"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;th style="text-align: center;" align="left"&gt;&lt;span style="font-size: 12px;"&gt;委托&lt;/span&gt;&lt;/th&gt;&lt;th style="text-align: center;" align="left"&gt;&lt;span style="font-size: 12px;"&gt;说明&lt;/span&gt;&lt;/th&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;ContextCallback&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;表示要在新上下文中调用的方法。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;ParameterizedThreadStart&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;表示在 Thread 上执行的方法。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;ThreadExceptionEventHandler&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;表示将要处理 Application 的 ThreadException 事件的方法。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;ThreadStart&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;表示在 Thread 上执行的方法。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;TimerCallback&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;表示处理来自 Timer 的调用的方法。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;WaitCallback&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;表示线程池线程要执行的回调方法。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;WaitOrTimerCallback&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 12px;"&gt;表示当 WaitHandle 超时或终止时要调用的方法。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.3 线程的管理方式&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;通过ThreadStart来创建一个新线程是最直接的方法，但这样创建出来的线程比较难管理，如果创建过多的线程反而会让系统的性能下载。有见及此，.NET为线程管理专门设置了一个CLR线程池，使用CLR线程池系统可以更合理地管理线程的使用。所有请求的服务都能运行于线程池中，当运行结束时线程便会回归到线程池。通过设置，能控制线程池的最大线程数量，在请求超出线程最大值时，线程池能按照操作的优先级别来执行，让部分操作处于等待状态，待有线程回归时再执行操作。&lt;/p&gt;&lt;p&gt;基础知识就为大家介绍到这里，下面将详细介绍多线程的开发。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a name="t3"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;返回目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;三、以ThreadStart方式实现多线程&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.1 使用ThreadStart委托&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;这里先以一个例子体现一下多线程带来的好处，首先在Message类中建立一个方法ShowMessage()，里面显示了当前运行线程的Id，并使用Thread.Sleep（int ) 方法模拟部分工作。在main()中通过ThreadStart委托绑定Message对象的ShowMessage（）方法，然后通过Thread.Start（）执行异步方法。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Message&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowMessage()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;           {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;               &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async threadId is :{0}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                                               Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;               Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;   &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;               &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; n &amp;lt; &lt;span style="color: #800080;"&gt;10&lt;/span&gt;; n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;               {&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                   Thread.Sleep(&lt;span style="color: #800080;"&gt;300&lt;/span&gt;);   &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                   Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;The number is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + n.ToString()); &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;               }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;           }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;   &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;           {&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;               Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main threadId is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                                 Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;               Message message=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Message();&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;               Thread thread = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Thread(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ThreadStart(message.ShowMessage));&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;               thread.Start();&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;               Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Do something ..........!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;               Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main thread working is complete!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;               &lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;           }&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;       }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;请注意运行结果，在调用Thread.Start()方法后，系统以异步方式运行Message.ShowMessage()，而主线程的操作是继续执行的，在Message.ShowMessage()完成前，主线程已完成所有的操作。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012010721572365.jpg" alt="" width="565" height="254" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.2 使用ParameterizedThreadStart委托&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;ParameterizedThreadStart委托与ThreadStart委托非常相似，但ParameterizedThreadStart委托是面向带参数方法的。注意ParameterizedThreadStart 对应方法的参数为object，此参数可以为一个值对象，也可以为一个自定义对象。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Person&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Name&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Age&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Message&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowMessage(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; person)&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (person != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                 Person _person = (Person)person;&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;\n{0}'s age is {1}!\nAsync threadId is:{2}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                     _person.Name,_person.Age,Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                 Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; n &amp;lt; &lt;span style="color: #800080;"&gt;10&lt;/span&gt;; n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;                 Thread.Sleep(&lt;span style="color: #800080;"&gt;300&lt;/span&gt;);   &lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;The number is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + n.ToString()); &lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;         {     &lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main threadId is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;             Message message=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Message();&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;绑定带参数的异步方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;             Thread thread = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Thread(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ParameterizedThreadStart(message.ShowMessage));&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;             Person person = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person();&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;             person.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Jack&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;             person.Age = &lt;span style="color: #800080;"&gt;21&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;             thread.Start(person);  &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;启动异步线程 &lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Do something ..........!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main thread working is complete!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;              &lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;运行结果：&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012010722462070.jpg" alt="" width="561" height="262" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.3 前台线程与后台线程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;注意以上两个例子都没有使用Console.ReadKey（）,但系统依然会等待异步线程完成后才会结束。这是因为使用Thread.Start()启动的线程默认为前台线程，而系统必须等待所有前台线程运行结束后，应用程序域才会自动卸载。&lt;/p&gt;&lt;p&gt;在第二节曾经介绍过线程Thread有一个属性IsBackground，通过把此属性设置为true，就可以把线程设置为后台线程！这时应用程序域将在主线程完成时就被卸载，而不会等待异步线程的运行。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.4 挂起线程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;为了等待其他后台线程完成后再结束主线程，就可以使用Thread.Sleep()方法。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Message&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowMessage()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;\nAsync threadId is:{0}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;                                            Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; n &amp;lt; &lt;span style="color: #800080;"&gt;10&lt;/span&gt;; n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                 Thread.Sleep(&lt;span style="color: #800080;"&gt;300&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;The number is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + n.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         {     &lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main threadId is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                               Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             Message message=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Message();&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             Thread thread = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Thread(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ThreadStart(message.ShowMessage));&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             thread.IsBackground = &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             thread.Start();&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Do something ..........!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main thread working is complete!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main thread sleep!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;5000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果如下，此时应用程序域将在主线程运行5秒后自动结束&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012010723153675.jpg" alt="" width="542" height="268" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;但系统无法预知异步线程需要运行的时间，所以用通过Thread.Sleep（int）阻塞主线程并不是一个好的解决方法。有见及此，.NET专门为等待异步线程完成开发了另一个方法thread.Join()。把上面例子中的最后一行Thread.Sleep（5000）修改为 thread.Join() 就能保证主线程在异步线程thread运行结束后才会终止。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.5 Suspend 与 Resume （慎用）&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Thread.Suspend（）与 Thread.Resume（）是在Framework1.0 就已经存在的老方法了，它们分别可以挂起、恢复线程。但在Framework2.0中就已经明确排斥这两个方法。这是因为一旦某个线程占用了已有的资源，再使用Suspend（）使线程长期处于挂起状态，当在其他线程调用这些资源的时候就会引起死锁！所以在没有必要的情况下应该避免使用这两个方法。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3.6 终止线程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;若想终止正在运行的线程，可以使用Abort（）方法。在使用Abort（）的时候，将引发一个特殊异常 ThreadAbortException 。&lt;br /&gt;若想在线程终止前恢复线程的执行，可以在捕获异常后 ,在catch（ThreadAbortException ex）{...} 中调用Thread.ResetAbort（）取消终止。&lt;br /&gt;而使用Thread.Join（）可以保证应用程序域等待异步线程结束后才终止运行。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;         static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;              Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main threadId is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; +&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;                                Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;              Thread thread = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Thread(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ThreadStart(AsyncThread));&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;              thread.IsBackground = &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;              thread.Start();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;              thread.Join();&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;          }     &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;          &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;以异步方式调用&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AsyncThread()&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;\nAsync threadId is:{0}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                     Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                  Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; n &amp;lt; &lt;span style="color: #800080;"&gt;10&lt;/span&gt;; n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                  {&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;                      &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;当n等于4时，终止线程&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;                      &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (n &amp;gt;= &lt;span style="color: #800080;"&gt;4&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;                      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;                          Thread.CurrentThread.Abort(n);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;                      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;                      Thread.Sleep(&lt;span style="color: #800080;"&gt;300&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                      Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;The number is:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + n.ToString());&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;                  }&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (ThreadAbortException ex)&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;                  &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;输出终止线程时n的值&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (ex.ExceptionState != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                      Console.WriteLine(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Thread abort when the number is: {0}!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                                                       ex.ExceptionState.ToString()));&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                 &lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;                  &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;取消终止，继续执行线程&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;                  Thread.ResetAbort();&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;                  Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Thread ResetAbort!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;线程结束&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;              Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Thread Close!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;          }&lt;/div&gt;&lt;p&gt;运行结果如下&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012010919274011.jpg" alt="" width="554" height="194" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a name="t4"&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;返回目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="font-size: 16px;"&gt;四、CLR线程池的工作者线程&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.1 关于CLR线程池&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;使用ThreadStart与ParameterizedThreadStart建立新线程非常简单，但通过此方法建立的线程难于管理，若建立过多的线程反而会影响系统的性能。&lt;br /&gt;有见及此，.NET引入CLR线程池这个概念。CLR线程池并不会在CLR初始化的时候立刻建立线程，而是在应用程序要创建线程来执行任务时，线程池才初始化一个线程。线程的初始化与其他的线程一样。在完成任务以后，该线程不会自行销毁，而是以挂起的状态返回到线程池。直到应用程序再次向线程池发出请求时，线程池里挂起的线程就会再度激活执行任务。这样既节省了建立线程所造成的性能损耗，也可以让多个任务反复重用同一线程，从而在应用程序生存期内节约大量开销。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;em&gt;注意&lt;/em&gt;：&lt;em&gt;通过CLR线程池所建立的线程总是默认为后台线程，优先级数为ThreadPriority.Normal。&lt;/em&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.2 工作者线程与I/O线程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;CLR线程池分为工作者线程（workerThreads）与I/O线程 (&lt;span class="parameter"&gt;completion&lt;/span&gt;PortThreads) 两种，工作者线程是主要用作管理CLR内部对象的运作，I/O（Input/Output) 线程顾名思义是用于与外部系统交换信息，IO线程的细节将在下一节详细说明。&lt;/p&gt;&lt;p&gt;通过ThreadPool.GetMax（out int workerThreads,out int completionPortThreads )和 ThreadPool.SetMax( int workerThreads, int completionPortThreads)两个方法可以分别读取和设置CLR线程池中工作者线程与I/O线程的最大线程数。在Framework2.0中最大线程默认为25*CPU数，在Framewok3.0、4.0中最大线程数默认为250*CPU数，在近年 I3,I5,I7 CPU出现后，线程池的最大值一般默认为1000、2000。&lt;br /&gt;若想测试线程池中有多少的线程正在投入使用，可以通过ThreadPool.GetAvailableThreads( &lt;span style="color: #000000;"&gt;out int&lt;/span&gt; workerThreads,out int completionPortThreads ) 方法。&lt;/p&gt;&lt;p&gt;使用CLR线程池的工作者线程一般有两种方式，一是直接通过 ThreadPool.QueueUserWorkItem() 方法，二是通过委托，下面将逐一细说。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.3 通过QueueUserWorkItem启动工作者线程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;ThreadPool线程池中包含有两个静态方法可以直接启动工作者线程：&lt;br /&gt;一为 ThreadPool.QueueUserWorkItem(WaitCallback)&lt;br /&gt;二为 ThreadPool.QueueUserWorkItem(WaitCallback,Object)&amp;nbsp;&lt;/p&gt;&lt;p&gt;先把WaitCallback委托指向一个带有Object参数的无返回值方法，再使用 ThreadPool.QueueUserWorkItem(WaitCallback) 就可以异步启动此方法，此时异步方法的参数被视为null 。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把CLR线程池的最大值设置为1000&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示主线程启动时线程池信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;启动工作者线程&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             ThreadPool.QueueUserWorkItem(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; WaitCallback(AsyncCallback));&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AsyncCallback(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; state)&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;200&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;AsyncCallback&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async thread do work!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  CurrentThreadId is {1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;                  data, Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011313135388.jpg" alt="" width="551" height="127" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;使用 ThreadPool.QueueUserWorkItem(WaitCallback,Object) 方法可以把object对象作为参数传送到回调函数中。&lt;br /&gt;下面例子中就是把一个string对象作为参数发送到回调函数当中。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把线程池的最大值设置为1000&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             ThreadPool.SetMaxThreads(&lt;span style="color: #800080;"&gt;1000&lt;/span&gt;, &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;           &lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             ThreadPool.QueueUserWorkItem(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; WaitCallback(AsyncCallback),&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello Elva&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AsyncCallback(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; state)&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;200&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;AsyncCallback&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data = (&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;)state;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async thread do work!\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+data);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示线程现状&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  CurrentThreadId is {1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;                  data, Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011313184468.jpg" alt="" width="540" height="151" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;通过ThreadPool.QueueUserWorkItem启动工作者线程虽然是方便，但WaitCallback委托指向的必须是一个带有Object参数的无返回值方法，这无疑是一种限制。若方法需要有返回值，或者带有多个参数，这将多费周折。有见及此，.NET提供了另一种方式去建立工作者线程，那就是委托。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.4&amp;nbsp; 委托类&lt;/strong&gt;　&lt;/p&gt;&lt;p&gt;使用CLR线程池中的工作者线程，最灵活最常用的方式就是使用委托的异步方法，在此先简单介绍一下委托类。&lt;/p&gt;&lt;p&gt;当定义委托后，.NET就会自动创建一个代表该委托的类，下面可以用反射方式显示委托类的方法成员（对反射有兴趣的朋友可以先参考一下&amp;ldquo;&lt;span style="color: #0000ff;"&gt;&lt;a id="ctl02_TitleUrl" href="http://www.cnblogs.com/leslies2/archive/2011/11/22/2257703.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;.NET基础篇&amp;mdash;&amp;mdash;反射的奥妙&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&amp;rdquo;）&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; MyDelegate();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             MyDelegate delegate1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(AsyncThread);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示委托类的几个方法成员     &lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; methods=delegate1.GetType().GetMethods();&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (methods != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (MethodInfo info &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; methods)&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                     Console.WriteLine(info.Name);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;      }&lt;/div&gt;&lt;p&gt;委托类包括以下几个重要方法&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011116562025.jpg" alt="" /&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; MyDelegate:MulticastDelegate&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; target, &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; methodPtr);&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;调用委托方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;virtual&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Invoke();&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;异步委托&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;virtual&lt;/span&gt; IAsyncResult BeginInvoke(AsyncCallback callback,&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; state);&lt;br /&gt;&lt;span style="color: #008080;"&gt;8&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;virtual&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; EndInvoke(IAsyncResult result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;9&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;当调用Invoke（）方法时，对应此委托的所有方法都会被执行。而BeginInvoke与EndInvoke则支持委托方法的异步调用，由BeginInvoke启动的线程都属于CLR线程池中的工作者线程，在下面将详细说明。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.5&amp;nbsp; 利用BeginInvoke与EndInvoke完成异步委托方法&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;首先建立一个委托对象，通过IAsyncResult BeginInvoke(string name,AsyncCallback callback,object state) 异步调用委托方法，BeginInvoke 方法除最后的两个参数外，其它参数都是与方法参数相对应的。通过 BeginInvoke 方法将返回一个实现了 System.IAsyncResult 接口的对象，之后就可以利用EndInvoke（IAsyncResult ) 方法就可以结束异步操作，获取委托的运行结果。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立委托&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             MyDelegate myDelegate = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(Hello);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;异步调用委托，获取计算结果&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             IAsyncResult result=myDelegate.BeginInvoke(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;完成主线程其他工作&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;span style="color: #008000;"&gt;&lt;span style="color: #000000;"&gt;            .............&lt;/span&gt; &lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;等待异步方法完成&lt;/span&gt;&lt;span style="color: #008000;"&gt;，调用EndInvoke(IAsyncResult)获取运行结果&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data=myDelegate.EndInvoke(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             Console.WriteLine(data);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Hello(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;2000&lt;/span&gt;);            &lt;span style="color: #008000;"&gt;//虚拟异步工作&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显示当前线程&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  ThreadId is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;                    data,Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011117481112.jpg" alt="" width="579" height="137" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.6&amp;nbsp; 善用IAsyncResult&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在以上例子中可以看见，如果在使用myDelegate.BeginInvoke后立即调用myDelegate.EndInvoke，那在异步线程未完成工作以前主线程将处于阻塞状态，等到异步线程结束获取计算结果后，主线程才能继续工作，这明显无法展示出多线程的优势。此时可以好好利用IAsyncResult 提高主线程的工作性能，IAsyncResult有以下成员：&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IAsyncResult&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; AsyncState {&lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;}            &lt;span style="color: #008000;"&gt;//获取用户定义的对象，它限定或包含关于异步操作的信息。&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;     WailHandle AsyncWaitHandle {&lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;}   &lt;span style="color: #008000;"&gt;//获取用于等待异步操作完成的 WaitHandle。&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt; CompletedSynchronously {&lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;}  &lt;span style="color: #008000;"&gt;//获取异步操作是否同步完成的指示。&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;bool&lt;/span&gt; IsCompleted {&lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;}             &lt;span style="color: #008000;"&gt;//获取异步操作是否已完成的指示。&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;通过轮询方式，使用IsCompleted属性判断异步操作是否完成，这样在异步操作未完成前就可以让主线程执行另外的工作。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立委托&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             MyDelegate myDelegate = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(Hello);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;异步调用委托，获取计算结果&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             IAsyncResult result=myDelegate.BeginInvoke(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在异步线程未完成前执行其他工作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;while&lt;/span&gt; (!result.IsCompleted)&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                 Thread.Sleep(&lt;span style="color: #800080;"&gt;200&lt;/span&gt;);      &lt;span style="color: #008000;"&gt;//虚拟操作&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main thead do work!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data=myDelegate.EndInvoke(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             Console.WriteLine(data);&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Hello(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;2000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  ThreadId is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;                    data,Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果：&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011118580960.jpg" alt="" width="575" height="284" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;除此以外，也可以使用WailHandle完成同样的工作，WaitHandle里面包含有一个方法WaitOne（int timeout），它可以判断委托是否完成工作，在工作未完成前主线程可以继续其他工作。运行下面代码可得到与使用 IAsyncResult.IsCompleted 同样的结果，而且更简单方便 。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Test&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立委托&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             MyDelegate myDelegate = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(Hello);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;异步调用委托，获取计算结果&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             IAsyncResult result=myDelegate.BeginInvoke(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;while&lt;/span&gt; (!result.AsyncWaitHandle.WaitOne(&lt;span style="color: #800080;"&gt;200&lt;/span&gt;))&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main thead do work!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data=myDelegate.EndInvoke(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             Console.WriteLine(data);&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Hello(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;2000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  ThreadId is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                    data,Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;当要监视多个运行对象的时候，使用IAsyncResult.WaitHandle.WaitOne可就派不上用场了。&lt;br /&gt;幸好.NET为WaitHandle准备了另外两个静态方法：WaitAny（waitHandle[], int）与WaitAll (waitHandle[] , int)。&lt;br /&gt;其中WaitAll在等待所有waitHandle完成后再返回一个bool值。&lt;br /&gt;而WaitAny是等待其中一个waitHandle完成后就返回一个int，这个int是代表已完成waitHandle在waitHandle[]中的数组索引。&lt;br /&gt;下面就是使用WaitAll的例子，运行结果与使用 IAsyncResult.IsCompleted 相同。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立委托&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             MyDelegate myDelegate = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(Hello);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;异步调用委托，获取计算结果&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             IAsyncResult result=myDelegate.BeginInvoke(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;此处可加入多个检测对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             WaitHandle[] waitHandleList = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; WaitHandle[] { result.AsyncWaitHandle,........ };&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;while&lt;/span&gt; (!WaitHandle.WaitAll(waitHandleList,&lt;span style="color: #800080;"&gt;200&lt;/span&gt;))&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main thead do work!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data=myDelegate.EndInvoke(result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             Console.WriteLine(data);&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Hello(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;2000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Hello &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  ThreadId is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                    data,Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;&lt;strong&gt;4.7 回调函数&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;使用轮询方式来检测异步方法的状态非常麻烦，而且效率不高，有见及此，.NET为 IAsyncResult BeginInvoke（AsyncCallback , object）准备了一个回调函数。使用 AsyncCallback 就可以绑定一个方法作为回调函数，回调函数必须是带参数 IAsyncResult 且无返回值的方法： void AsycnCallbackMethod(IAsyncResult result) 。在BeginInvoke方法完成后，系统就会调用AsyncCallback所绑定的回调函数,最后回调函数中调用 XXX EndInvoke（IAsyncResult result) 就可以结束异步方法，它的返回值类型与委托的返回值一致。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立委托&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             MyDelegate myDelegate = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(Hello);&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;异步调用委托，获取计算结果&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;             myDelegate.BeginInvoke(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(Completed), &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在启动异步线程后，主线程可以继续工作而不需要等待&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; n &amp;lt; &lt;span style="color: #800080;"&gt;6&lt;/span&gt;; n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  Main thread do work!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;""&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Hello(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;2000&lt;/span&gt;);             &lt;span style="color: #008000;"&gt;\\模拟异步操作&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;\nHello &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Completed(IAsyncResult result)&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async Completed&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取委托对象，调用EndInvoke方法获取运行结果&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;             AsyncResult _result = (AsyncResult)result;&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;             MyDelegate myDelegate = (MyDelegate)_result.AsyncDelegate;&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data = myDelegate.EndInvoke(_result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             Console.WriteLine(data);&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  ThreadId is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;                    data, Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;可以看到，主线在调用BeginInvoke方法可以继续执行其他命令，而无需再等待了，这无疑比使用轮询方式判断异步方法是否完成更有优势。&lt;br /&gt;在异步方法执行完成后将会调用AsyncCallback所绑定的回调函数，注意一点，回调函数依然是在异步线程中执行，这样就不会影响主线程的运行，这也使用回调函数最值得青昧的地方。&lt;br /&gt;在回调函数中有一个既定的参数IAsyncResult,把IAsyncResult强制转换为AsyncResult后，就可以通过 AsyncResult.AsyncDelegate 获取原委托，再使用EndInvoke方法获取计算结果。&lt;br /&gt;运行结果如下：&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011323313036.jpg" alt="" width="572" height="267" /&gt;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;如果想为回调函数传送一些外部信息，就可以利用BeginInvoke(AsyncCallback,object)的最后一个参数object,它允许外部向回调函数输入任何类型的参数。只需要在回调函数中利用 AsyncResult.AsyncState 就可以获取object对象。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Person&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Name;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Age;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;delegate&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; MyDelegate(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立委托&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             MyDelegate myDelegate = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDelegate(Hello);&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;建立Person对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             Person person = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person();&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             person.Name = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Elva&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;             person.Age = &lt;span style="color: #800080;"&gt;27&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;异步调用委托，输入参数对象person, 获取计算结果&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             myDelegate.BeginInvoke(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Leslie&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AsyncCallback(Completed), person);            &lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;           &lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在启动异步线程后，主线程可以继续工作而不需要等待&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;for&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;; n &amp;lt; &lt;span style="color: #800080;"&gt;6&lt;/span&gt;; n++)&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;                 Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  Main thread do work!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;""&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; Hello(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name)&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;             Thread.Sleep(&lt;span style="color: #800080;"&gt;2000&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;\nHello &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + name;&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Completed(IAsyncResult result)&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;             ThreadMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Async Completed&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取委托对象，调用EndInvoke方法获取运行结果&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;             AsyncResult _result = (AsyncResult)result;&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;             MyDelegate myDelegate = (MyDelegate)_result.AsyncDelegate;&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data = myDelegate.EndInvoke(_result);&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取Person对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;             Person person = (Person)result.AsyncState;&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = person.Name + &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;'s age is &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + person.Age.ToString();&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;             Console.WriteLine(data+&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ThreadMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; message = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}\n  ThreadId is:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt;                    data, Thread.CurrentThread.ManagedThreadId);&lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;             Console.WriteLine(message);&lt;br /&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;运行结果:&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012011323434221.jpg" alt="" width="566" height="281" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;关于I/O线程、SqlCommand多线程查询、PLINQ、定时器与锁的内容将在&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;C#综合揭秘&amp;mdash;&amp;mdash;细说多线程（下）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;中详细介绍。&lt;br /&gt;对.NET开发有兴趣的朋友请加入博客园讨论小组&lt;span style="color: #0000ff;"&gt;&lt;a href="http://home.cnblogs.com/group/102576/" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&amp;ldquo;.NET高级编程&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; 一起探讨！&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;C#综合揭秘&lt;/span&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说进程、应用程序域与上下文&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;细说多线程（上）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说多线程（下）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说事务&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;深入分析委托与事件&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="float: right; text-align: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;br /&gt;&lt;a id="Editor_Edit_hlEntryLink" title="view: C#综合揭秘&amp;mdash;&amp;mdash;细说多线程（上）" href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html&lt;/span&gt;&lt;/a&gt; &lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;a title="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html" href="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2310495.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/leslies2/archive/2012/01/10/2317523.html</id><title type="text">反流程升职记</title><summary type="text">其实为啥这是 “反流程” 升职记，就是因为 “升职” 不应该只是等待，而应该是自己争取。“命运” 不应该由天来控制，而应该由自己去创造。“升职” 并不是一个已经有的流程，而是由我们自己的努力而创造的 “奇迹” 。</summary><published>2012-01-10T02:55:00Z</published><updated>2012-01-10T02:55:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2012/01/10/2317523.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2012/01/10/2317523.html"/><content type="html">&lt;p&gt;以下内容纯属虚构，如有雷同，实属巧合！&lt;/p&gt;&lt;p&gt;到了年末，又是一年一度写 &amp;ldquo;年终总结&amp;rdquo; 的时候了。浪子正坐在办公室里瞎呆着：究竟在2011年里，自己做些了什么? 又真正能得到了些什么呢? 左思右想，真的是毫无头绪，反正又不是读书写作文的时候，写好了也不一定要交给老板看。浪子终于把心一横：好！就写下自己的经历与教训，真正为自己的将来打算一下。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;年终总结&lt;/p&gt;&lt;p&gt;从年少无知到心思细密，从一无是处的待业青年到如今知名软件公司的副总，当中经历了无数的跌倒，又从失败和挣扎中爬起来。总结概括，本人觉得没有家庭背景，没有政治地位，没有金钱辅助的人想得到成功，必须经历以下5个阶段：&lt;/p&gt;&lt;p&gt;&lt;strong&gt;一、明确目标，脚踏实地，从低做起&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;世上没有不劳而获的事情，要想从一个寻常的老百姓开始做起，得到广阔的发展空间，必须比其他人加入多倍的努力。做IT行业也是如此，无论你的理想是从事技术的开发，还是从事业务的管理，都必须从低做起，脚踏实地工作。在工作的过程中了解行业的现状，业务的动向，客户的需求，未来的方向，并为自己定立一个长期的发展目标。只有有理想、有目标、有方向的人才不会在激烈的社会竞争中迷途。&lt;/p&gt;&lt;/div&gt;&lt;p&gt;写到这里，不禁让浪子想起一个故事：古时候，一位学医的年轻人为了研制一种毒药的解药配方，不禁以身试毒，然后到深山里采集山药，以研制配方。越往山里走，他越发现有很多山药都有着其独特的功能，当他把药采回药馆研究的时候，却忘记了为自己的毒药寻找配方的事，最后不幸毒发身亡。&lt;/p&gt;&lt;p&gt;其实对初入社会的人来说也是如此，很多人面对这个复杂的社会会感到迷途，有时候可能会被一些眼前的利益所蒙骗而忘记了自己的目标。虽然每个人的背景，现状都不相同，每个人都有着自己的目标和抱负。但有一点是一样的，只有坚持自己目标，努力奋斗的人才会得到成功，反之，那些随波逐流，半途而废的人最终只会面对失败。&lt;/p&gt;&lt;p&gt;想到这里，浪子脸上露出了一丝微笑，他似乎有些自喜，自喜自己是个有抱负，有目标的人。自喜他能面向着目标，一如既往地奋斗，虽然道路是坎坷的，但他相信，只要他能继续努力，总会有成功的一天。这时候，浪子拿起了笔，继续写到：&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;strong&gt;二、发掘优点，提升能力&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;安于现状的人能享受知足所带来的快乐，但永远也不能突出自己特点。想在这茫茫的人海中突出自己，就应该找到自己的长处，发现自己的优势，为自己争取更广阔的发展空间。要是你口舌灵利，反应敏捷，能快速地洞察市场的走势，那你就应该把握机会，在大型的项目中好好地表现自己。要是你思维明锐，心思细密，能完成复杂的开发过程，那就应该尽量争取难度大，回报高的新型技术项目，在开发过程中吸收学习崭新的开发技术。&lt;/p&gt;&lt;/div&gt;&lt;p&gt;这个阶段真让浪子发起一段感慨：想当年，自己也是从一个小小的程序员出身，刚出来的时候什么都不懂，在工作过程中的确学到了不少的东西。但做久了，工作也只是千篇一律，用来用去都是相似的东西，难以再从中再领略到什么新知识。&lt;/p&gt;&lt;p&gt;但只要记住自己的目标，那就不再是 &amp;ldquo;为了工作而工作，为了金钱而工作&amp;rdquo;，工作只被视作是一种过程，一种实现目标的过程。在工作过程你可以了解到要做好工作需要一些什么，要表现自己还需要些什么，要体现自己比别人优胜的地方必须先做到些什么。&lt;/p&gt;&lt;p&gt;虽然，短期的学习并不能直接体现个人的优点，但经过长期的积累，你比别人优胜的地方就能逐步的展现。&lt;/p&gt;&lt;p&gt;但是光有优点还不够，还需要找到表现个人能力的机会：&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;strong&gt; 三、主动争取机会，把握每个能得到发展的机遇&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;想要得到成功必须记住：机会不是等着别人给的，而是自己争取回来的！如果每天只坐在那里，等着上级给你机会，那你的理想最终将会变成泡影。要想得到成功就必须变被动为主动，不是等着机会的到来，而是在自己有能力，有实力的时候主动地去争取机会。世上没有免费的午餐，有时候，你必须放弃面前的一些东西，才能得到机会去发展，但只要你对自己有信心，在机会到来的时候就应该大胆地尝试，放弃面前的一些小利益，以争取更大的回报。&lt;/p&gt;&lt;/div&gt;&lt;p&gt;浪子露出了一丝苦笑，想着自己以前经常被别人笑说成 &amp;ldquo;跳槽冠军&amp;rdquo;，两年期间跳了好几家大公司，但还是感到不满意。其实争取机会并不是怂恿各位去跳槽，哪家公司高薪就跳哪去，而是说应该尝试寻找一个更能发挥自己能力的地方。&lt;/p&gt;&lt;p&gt;想想哪一家公司的老板会想旗下的企业会有大型的人事变动呢？想要成功，人就要有逆向思维：如果我是老板，我希望自己的公司是怎么样的呢？我的希望是：企业能长期处于一个稳定的状态，绝对不愿意开除了哪一位管理层，然后破格提升一个小伙子。&lt;/p&gt;&lt;p&gt;当你有了突出的能力却到了瓶颈的位置，长期呆在一家公司做着乏味的工作的时候，就更应该大胆地尝试，为自己的发展谋求一条合适的道路。正所谓，赛翁失马，焉知非福！不敢放弃现有的，也就失去了进一步发展的机会。&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;strong&gt;四、提升管理能力，提高综合素质&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;无论从事技术还是业务，无论你是技术总监还是业务总监，都只是单方面的能力。想要成为出色的人才，这是远远不够的。企业是一个运营的团体，想要一家企业能够得到长远的发展，就必须有完善的管理能力，知人善用。一个成功的企业家往往并不是样样皆能，而是他有妥善的管理才能，能有效地控制企业的日常运作，把握人才，充分发挥企业的独有优势。&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;浪子第一时间想起最爱看的一部惊世名著：三国演义，古人云：得民心者得天下。回望三国，刘备虽无大才，文不能安邦，武不能定国，但却从一没落的市井草席之人成为一方之主，就是因为他能知人善用。卧龙凤雏皆倾心辅助，五虎上将皆俯首称臣，令他终成霸业。当今作为企业的领导者也该有此发掘人才能力，注重人才的管理，通过沟通提高人才对企业的了解程度，唤醒其工作热诚。&lt;/p&gt;&lt;p&gt;想想刘备虽然出身寒微，但在屡经挫折后，身边却是人才济济，最终能得一席之地。回想孔明，堂堂西蜀丞相，自比管仲乐毅，为了振兴西蜀可说是鞠躬尽瘁，但六出祁山却是 "蜀中无大将，廖化当先锋"。可以看出，单单有某方面的突出才能, 把所有的问题都一个人扛着，最终也难以成就大事。无论你有多么聪明的才智，但缺乏综合管理的能力，也难成一方之主。&lt;/p&gt;&lt;p&gt;管理是一种综合能力，要通过出色管理让一家不知名的小企业华丽变身成为一家上市集团更是一种艺术。这绝对不仅仅是通过技术或业务等单方面的学习就能掌握的，这必须经过长期的累积与学习，多方面的了解与实践才能从中领悟。提高个人的综合管理能力，是一个成功人士的必要条件。&lt;/p&gt;&lt;p&gt;这时候，让浪子眼里回放出近期看过的一部电影：杜拉拉升职记，剧中女主角拉拉经历了不断的努力与尝试，终于从一不知名的小员工提升到跨国企业的部门主管，当中经过了多少的波折与考验。但即便如此，拉拉也不过是年薪五十万左右，但区区的五十万年薪，又能干些什么呢？要想真正达到发展的目标，最重要的是第五点：&lt;/p&gt;&lt;div style="background: #f4f4f4; border: 1px solid #808080; width：80%;margin: 20px; padding: 20px;"&gt;&lt;p&gt;&lt;strong&gt;五、囤积资源，建立社会关系网&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;现今社会，光有钱并不足以成事。最重要的是必须拥有一个完善的关系网，在市场的调研，项目的研发，产品的包装，业务的推广上都必须有对应企业的支持，那产品才有可能成功地提出市场，得到丰厚的回报。所以在企业建立前，必须建立自己的人际关系网。而这资源，不单单是指钱，更重要的是市场关系，人才资源，产品信息。只有把握市场动向，了解产品信息，团结人才队伍，抢在技术前线的企业才会得到最终的成功。&lt;/p&gt;&lt;/div&gt;&lt;p&gt;自主创业，是浪子最终想要到达的目标，到这里，浪子终于想到年终报告里面2012年的目标是什么了，那就是洞察市场发展，注视产品路线，发掘有用人才，团积社会关系。在创业之前一定要拥有一个完善的发展渠道，建立成熟的社会关系网，那自主创业才可能得到成功。&lt;/p&gt;&lt;p&gt;正所谓创业难，守业更难，在创业后，必须密切观察市场的走势，制定企业长期的发展路线，那企业才能得到迅速的发展与壮大。&lt;/p&gt;&lt;p&gt;&lt;strong&gt;其实为啥这是 &amp;ldquo;反流程&amp;rdquo; 升职记，就是因为 &amp;ldquo;升职&amp;rdquo; 不应该只是等待，而应该是自己争取。&amp;ldquo;命运&amp;rdquo; 不应该由天父来控制，而应该由自己去把握。&amp;ldquo;升职&amp;rdquo; 并不是一个已有的流程，而是由我们通过自己的努力而创造的一个 &amp;ldquo;奇迹&amp;rdquo; 。&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;div style="float: right; text-align: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;br /&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/01/10/2317523.html"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2012/01/10/2317523.html&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;a title="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html" href="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;div id="BlogPostCategory"&gt;&amp;nbsp;&lt;/div&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2317523.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/01/10/2317523.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html</id><title type="text">C#综合揭秘——细说事务</title><summary type="text">事务是在数据层、服务层、业务逻辑层多处地方都会使用到的东西，在本篇文章将会为大家一一细说。在软件系统当中可以看到无论在数据库、Web服务、WCF、文件系统都存在着数据参与到事务运作当中，我们把管理这些数据的工具称为资源管理器RM（Resources Manager）。而事务管理器TM（Transaction Manager）就是协调多个资源管理器的工作，保证数据完整性的工具。</summary><published>2012-01-05T02:23:00Z</published><updated>2012-01-05T02:23:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html"/><content type="html">&lt;p id="t0"&gt;引言&lt;/p&gt;&lt;p&gt;其实事务在数据层、服务层、业务逻辑层多处地方都会使用到，在本篇文章将会为大家一一细说。&lt;/p&gt;&lt;p&gt;其中前面四节是事务的基础，后面的三节是事务的重点，对事务有基础的朋友可以跳过前面四节。&lt;/p&gt;&lt;p&gt;文章有错漏的地方欢迎各位点评。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;目录&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t1"&gt;&lt;span style="color: #0000ff;"&gt; 一、事务的定义&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t2"&gt;&lt;span style="color: #0000ff;"&gt;二、事务管理器&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#t3"&gt;&lt;span style="color: #0000ff;"&gt;三、在ADO.NET中实现事务&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 14px; color: #0000ff;"&gt;&lt;a href="#t4"&gt;&lt;span style="color: #0000ff;"&gt;四、隐式事务 TransactionScope&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p id="t1"&gt;&lt;a href="#t5"&gt;&lt;span style="color: #0000ff;"&gt;五、在WCF中实现事务&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#t6"&gt;&lt;span style="color: #0000ff;"&gt;六、嵌套式事务&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#t7"&gt;&lt;span style="color: #0000ff;"&gt;七、异步事务&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;一、事务的定义&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;所谓事务,它是一个操作集合，这些操作要么都执行，要么都不执行，它是一个不可分割的工作单位。典型的例子就像从网上银行系统的帐户A转帐到帐户B，它经过两个阶段：1.从帐户A取出款项。2.把款项放入帐户B中。这两个过程要么同时成功，要么同时失败,这一系列的操作就被称为事务性(Transactional)操作。&lt;/p&gt;&lt;p&gt;在一个事务性操作的环境下，操作有着以下的4种特性，被称为ACID特性&lt;/p&gt;&lt;table style="border-color: #464646; border-style: solid; border-width: 1px; width: 600px; height: 160px;" border="1 " cellspacing="10" cellpadding="1" align="left"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td style="width: 160px;"&gt;&lt;span style="font-size: 14px;"&gt;原子性（Atomicity）&lt;/span&gt;&lt;/td&gt;&lt;td style="text-align: left;"&gt;&lt;span style="font-size: 14px;"&gt;当事务结束，它对所有资源状态的改变都被视为一个操作，这些操作要不同时成功，要不同时失败&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;一致性（Consistency）&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;操作完成后，所有数据必须符合业务规则，否则事务必须中止&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;隔离性（Isolation）&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;事务以相互隔离的方式执行，事务以外的实体无法知道事务过程中的中间状态&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;持久性（Durable）&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;事务提交后，数据必须以一种持久性方式存储起来&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p id="t2"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;二、事务管理器&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;在软件系统当中可以看到无论在数据库、Web服务、WCF、文件系统都存在着数据参与到事务运作当中，我们把管理这些数据的工具称为资源管理器RM（Resources Manager）。而事务管理器TM（Transaction Manager）就是协调多个资源管理器的工作，保证数据完整性的工具。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="border: 1px ridge #808080; display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011121518184687.jpg" alt="" width="645" height="459" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;由上图可以看到事务的管理流程，系统通知事务管理器TM来启动事务，事务管理器TM控制向多个资源管理器RM并协调RM之间的事务操作。图中存在两个持久化RM，分别管理数据库和文件系统，这些事务操作要不同时成功，要不同时失败。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;事务管理器一般分为三类：轻量级事务管理器（LTM）、核心事务管理器（KTM）、分布式事务协调器（DTC）&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. 轻量级事务管理器 （LTM）&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;它是包括在System.Transactions 命名空间内的一个事务管理框架，它只能管理单个应用程序域内的事务。LTM 可以管理多个易变的RM，但只能管理一个持久化RM。若事务试图加入第二个持久化RM，那轻量级事务管理器LTM将提升级别。LTM是性能最高的事务管理器，在可选择的情况下应该尽可能地使用 LTM 事务管理器。&lt;/p&gt;&lt;p&gt;这里易变RM是指它参与会引发 &amp;ldquo;未确定状态&amp;rdquo; 的2PC事务时候，不需要恢复服务，更多时候，易变RM的数据只存储在内存当中。&lt;/p&gt;&lt;p&gt;而持久化RM是指它参与会引发 &amp;ldquo;未确定状态&amp;rdquo; 的2PC事务时候，它需要恢复服务，持久化RM管理的数据是在于硬盘当中。所以，参与2PC事务的的持久RM必须有新旧两个版本，如果事务引发 &amp;ldquo;未确定状态&amp;rdquo; 的时候，那么它就会联系持久化RM，恢复到其中一个版本。&lt;/p&gt;&lt;ul&gt;&lt;li&gt;&lt;em&gt;2PC说明 (&lt;span style="color: #0000ff;"&gt;&lt;a href="http://blogs.msdn.com/b/diegumzone/archive/2006/08/14/699219.aspx" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://blogs.msdn.com/b/diegumzone/archive/2006/08/14/699219.aspx&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;)&lt;br /&gt;&lt;/em&gt;&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;&lt;em&gt;2PC 是2 Phase Commit的缩写，代表事务的2阶段提交验证算法：在数据提交时，第一阶段：应用程序记录每个数据源并执行更新请求，TM通知每个RM来执行分布式事 务，然后每个RM都对数据执行本地的事务，在事务将提交前，TM会与各个RM进行信息交换，以获知更新是否成功。第二阶段，如果其中任何一个RM表示更新 失败，TM就会通知所有的RM事务操作失败，实现数据回滚。如果所有RM的操作都成功，那么整个TM事务就宣告成功。&lt;/em&gt;&lt;/p&gt;&lt;p&gt;&lt;em&gt;&lt;br /&gt;&lt;/em&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2. 核心事务管理器 （KTM）&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;KTM是用于Windows Vista和Windows Server 2008 系统中的轻量级事务管理器，与LTM相像，它可以管理多个易变的RM，但只能管理一个持久化RM。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3. 分布式事务协调器（DTC）&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;分布式事务协调器DTC（Distributed Transaction Coordinator）能管理多个持久化RM中的事务，事务可以跨越应用程序域、进程、硬件、域等所有的边界。在Windows Server 2008当中，DTC支持OleDB、XA、WS-AtomicTransaction、WSCoordination、WS-BusinessActivity等多个协议。由于分布式事务需要在多个参与方之间实现多次通讯，所以是一种巨大的开销，因此，&lt;strong&gt;在可以使用LTM和KTM的时候，应该尽量避免使用DTC&lt;/strong&gt;。在上面图片中的事务同时启动了两个RM分别处理数据库数据与文件数据，当中启动的就是DTC分布式事务。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.事务类 System.Transactioins.Transaction&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Transaction是由Framework 2.0 就开始引入，用于显示管理事务的一个类。通过Transaction可以直接管理事务的中止、释放，也可以获取、克隆当前的环境事务类。&lt;/p&gt;&lt;ul&gt;&lt;li&gt;Transaction的公用属性&lt;/li&gt;&lt;/ul&gt;&lt;div style="padding-left: 40px;"&gt;&lt;p&gt;其中Transaction.Current 比较常用，它可以指向一个当前运行环境中的事务，如果环境事务不存在，系统将返回一个null&lt;/p&gt;&lt;p&gt;Transaction transaction=Transaction.Current;&lt;/p&gt;&lt;table style="border-color: #464646; border-style: solid; width: 500px; height: 80px; border-width: 1px;" border="1 " align="left"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;th style="text-align: center;" align="left"&gt;&lt;span style="font-size: 14px;"&gt;属性&lt;/span&gt;&lt;/th&gt;&lt;th&gt;&lt;span style="font-size: 14px;"&gt;说明&lt;/span&gt;&lt;/th&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td style="text-align: left;"&gt;&lt;span style="font-size: 14px;"&gt;Current&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;获取或设置环境事务。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;IsolationLevel&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;获取事务的隔离级别。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;TransactionInformation&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;检索有关某个事务的附加信息。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;ul&gt;&lt;li&gt;Transaction的常用公用方法&lt;/li&gt;&lt;/ul&gt;&lt;div style="padding-left: 40px;"&gt;&lt;p&gt;其中Rollback、Dispose方法可以控制事务中止、释放，而Clone、DependentClone方法在多线程操作中经常用到，在&lt;a href="#t7"&gt; &lt;span style="color: #0000ff;"&gt;&amp;ldquo;异步事务&amp;rdquo;&lt;/span&gt;&lt;/a&gt; 一节中将详细说明&lt;/p&gt;&lt;table style="border-color: #464646; border-style: solid; width: 500px; height: 80px; border-width: 1px;" border="1 " align="left"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;th style="text-align: center;" align="left"&gt;&lt;span style="font-size: 14px;"&gt;方法&lt;/span&gt;&lt;/th&gt;&lt;th&gt;&lt;span style="font-size: 14px;"&gt;说明&lt;/span&gt;&lt;/th&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td style="text-align: left;"&gt;&lt;span style="font-size: 14px;"&gt;Rollback&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;中止事务、回滚。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;Dispose&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;释放事务对象。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;Clone&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;创建事务克隆&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;DependentClone&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;创建事务的依赖克隆。 &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;/div&gt;&lt;ul&gt;&lt;li&gt;Transaction的事件&lt;/li&gt;&lt;/ul&gt;&lt;div style="padding-left: 40px;"&gt;&lt;p&gt;在事务完成后，会触发TransactionCompleted事件，开发人员可以在此事件的过程监测其状态&lt;/p&gt;&lt;table style="border-color: #464646; border-style: solid; width: 500px; height: 60px; border-width: 1px;" border="1 " align="left"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;th style="text-align: center;" align="left" width="220px"&gt;&lt;span style="font-size: 14px;"&gt;事件&lt;/span&gt;&lt;/th&gt;&lt;th&gt;&lt;span style="font-size: 14px;"&gt;说明&lt;/span&gt;&lt;/th&gt;&lt;/tr&gt;&lt;tr valign="top"&gt;&lt;td style="text-align: left;"&gt;&lt;span style="font-size: 14px;"&gt;TransactionCompleted&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;在事务完成后执行&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;strong&gt;5. 事务状态 TransactionInformation&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;上面讲解过事务分为本地事务与分布式事务，而Transaction类的TransactionInformation是事务状态的记录，它可以跟踪事务动作，分辨事务现处的状态，记录本地事务与分布式事务的Guid。&lt;/p&gt;&lt;p&gt;TransactionInformation有两个重要成员&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; TransactionInformation&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;       &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;返回分布式事务标识符&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Guid DistributedIdentifier &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;       {&lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;}&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;       &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;返回本地事务标识符&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; LocalIdentifier&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;       {&lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;}&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;LocalIndentifier是本地事务的标识符，它可以获取本地事务管理器（LTM）的ID，并且注意只要事务存在，它的值就永远不会是null。它包含两个部分，一个是LTM的Guid，它是应用程序中的唯一值，代表了现存应用程序域分配的LTM。另一部分是一个可变量，代表了当时该应用程序域中的事务数量。&lt;/p&gt;&lt;p&gt;例如：3427dec9-4abc-34cc-9edf-30ad835c33k3:3&lt;/p&gt;&lt;p&gt;其中3427dec9-4abc-34cc-9edf-30ad835c33k3是此本地事务管理器的Guid,在事务启动后，此值都是不变的，而 &amp;ldquo;3&amp;rdquo; 代表此刻该应用程序域中存在 &amp;ldquo;3&amp;rdquo; 个本地事务。&lt;/p&gt;&lt;p&gt;&lt;br /&gt;DistributedIndentifier是分布式事务的标识符，在普通情况下DistributedIndentifier的值都为Guid.Empty。但当LTM或KTM事务被提升到分布式事务时，DistributedIndentifier就会产生。最重的是，在同一个分布式事务管理器当中，即使事务跨越服务边界，分布式ID都是一致的。DistributedIndentifier是分布式事务的唯一标识符，它的使用方法在后面 &lt;a href="#t5@1"&gt;&lt;span style="color: #0000ff;"&gt;&amp;ldquo;事务的传播&amp;rdquo;&lt;/span&gt;&lt;/a&gt; 一节将详细介绍。&lt;/p&gt;&lt;p&gt;在TransactionManager类中，还提供了一个事件DistributedTransactionStarted专门用于测试分布式事务的变化。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 TransactionManager.DistributedTransactionStarted += OnDistributedTransactionStarted;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;                 ............&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 scope.Complete();&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;当执行分布式事务是就会启动此方法显示事务信息&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; OnDistributedTransactionStarted(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; sender, TransactionEventArgs args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             Transaction transaction = args.Transaction;&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Distributed Transaction Started!\n  DistributedIndentifier:&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                  +transaction.TransactionInformation.DistributedIdentifier);&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;     }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;基础知识就先讲到这里，下面开始介绍一下事务的具体用法。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p id="t3"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;三、在ADO.NET中实现事务&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. ADO.NET事务的主要成员&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;需要使用事务管理的情况很多，在数据层使用得特别广泛，几乎每一个系统的数据层都会实现事务。数据层的事务都是继承自DBTransaction，派生自IDbTransaction的。下面介绍一下IDbTransaction的基本成员：&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IDbTransaction：IDisposable&lt;br /&gt;&lt;span style="color: #008080;"&gt;2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;3&lt;/span&gt;       IDbConnection Connection {&lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;}     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;返回Connection对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;4&lt;/span&gt;       IsolationLevel IsolationLevel{&lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;;}   &lt;br /&gt;&lt;span style="color: #008080;"&gt;5&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Commit();      &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;数据提交，把所有改变数据保存到持久化数据库&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;6&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Rollback();     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;数据回滚，把所有数据恢复原值&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;7&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;其中Connection属性是返回初始化此事务时所引用的连接对象的。Commit（）方法应该在完成所有数据操作后才调用，调用该方法后，已经改变的数据将会保存到持久化数据库当中。而Rollback（）是出现错误时调用的，调用后数据将返回初始值。IsolationLevel是指定遇到其它并行事务时的处理方式。&lt;/p&gt;&lt;p&gt;ADO.NET当中有多个子类都继续自DBTransaction，其中SqlTransaction是比较常用的，SqlTransaction中还定义了一个Save（）方法，这个方法允许开发人员把失败的事务回滚到上一个保存点而不回滚整个事务。而在DataContext类里面，Transaction属性会返回DBTransaction对象。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="border: 1px ridge #808080; display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011121613381163.jpg" alt="" width="369" height="224" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.开发实例&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在传统的ADO.NET中使用事务，方法如下：&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Execute(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; connectionString)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (SqlConnection connection = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; SqlConnection(connectionString))&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         connection.Open();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;         SqlCommand command = connection.CreateCommand();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;         SqlTransaction transaction;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;启动事务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;         transaction = connection.BeginTransaction(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;SampleTransaction&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;设定SqlCommand的事务和连接对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;         command.Connection = connection;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;         command.Transaction = transaction;&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;             command.CommandText =&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Insert into ......&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;             command.ExecuteNonQuery();&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; 完成提交&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             transaction.Commit();&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             ......&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (Exception ex)&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;             &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;数据回滚&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;             transaction.Rollback();&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             .....&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;在DataContext中使用事务，方法极其相似，不同的是SqlCommand中事务为SqlTransaction，在DataContext中事务为DbTransaction&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt;(MyDataContext context=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; MyDataContext())&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;           context.Connection.Open();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;           context.Transaction=context.Connection.BeginTransaction();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;           &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;更新数据&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;           .........&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;           context.SubmitChanges();&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;           &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;事务提交&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;           context.Transaction.Commit();&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt;(Excetion ex)&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;数据回滚&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;          context.Transaction.Rollback();&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;          &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;错误处理&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;          .........&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p id="t4"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;四、隐式事务 TransactionScope&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. TransactionScope的概念&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;TransactionScope存在于&lt;span class="selflink"&gt;System.Transactions&lt;/span&gt; 命名空间中， 它是从Framework 2.0开始引入的一个事务管理类,它也是微软推荐使用的一个事务管理类。在TransactionScope的构造函数中会自动创建了一个新的LTM（轻量级事务管理器），并通过Transaction.Current 隐式把它设置为环境事务。在使用隐式事务时，事务完成前程序应该调用TransactionScope的Complete（）方法，把事务提交，最后利用Dispose（）释放事务对象。若执行期间出现错误，事务将自动回滚。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; TransactionScope:IDisposable&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;多个构造函数&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; TransactionScope();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; TransactionScope(Transaction)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; TransactionScope(TransactionScopeOption)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;     ......&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Complete();   &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;提交事务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Dispose();     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;释放事务对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt; &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;调用方式&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt;(TransactionScope scope=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;      &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;执行事务型工作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;      ............&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;      scope.Complete();&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2. TransactionScope的构造函数 TransactionScope（transactionScopeOption）&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;TransactionScopeOption&lt;span&gt;&lt;span&gt;&lt;span id="xn2_7681afa12378f27badec8620731bd04c" class="sentence"&gt; 是枚举的一个实例，它主要用于TransactionScope的构造函数内，定义事务生成的状态要求。&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span&gt;&lt;span&gt;&lt;span id="xn2_7681afa12378f27badec8620731bd04c" class="sentence"&gt;在MSDN里面可以找到它的定义：&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://msdn.microsoft.com/zh-cn/library/system.transactions.transactionscopeoption.aspx" target="_blank"&gt;&lt;span class="sentence" style="color: #0000ff;"&gt;http://msdn.microsoft.com/zh-cn/library/system.transactions.transactionscopeoption.aspx&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="text-algin: left;"&gt;&lt;table style="width: 600px; height: 150px;" border="1" cellspacing="10" cellpadding="10" align="left"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;th class="nameColumn" style="text-align: center; width: 100px;"&gt;&lt;span style="font-size: 14px;"&gt;成员名称&lt;/span&gt;&lt;/th&gt;&lt;th class="descriptionColumn"&gt;&lt;span style="font-size: 14px;"&gt;说明&lt;/span&gt;&lt;/th&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span class="selflink" style="font-size: 14px;"&gt;Required&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;        &lt;span id="xn2_249076cc5fb69f26f0df3427ededc4b3" class="sentence"&gt;该范围需要一个事务。&lt;/span&gt;  &lt;span id="xn3_a943943eab7d4fde5e68b830f6b0da92" class="sentence"&gt;如果已经存在环境事务，则使用该环境事务。&lt;/span&gt;  &lt;span id="xn4_af635b4d1aa273e46b8543c8587e9349" class="sentence"&gt;否则，在进入范围之前创建新的事务。&lt;/span&gt;  &lt;span id="xn5_b0ae412cb2aae30ae74f10920dec5d81" class="sentence"&gt;这是默认值。&lt;/span&gt;  &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span class="selflink" style="font-size: 14px;"&gt;RequiresNew&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;        &lt;span id="xn6_1a8f8afd2e8ade831537a1918e927fc9" class="sentence"&gt;总是为该范围创建新事务。&lt;/span&gt;      &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span class="selflink" style="font-size: 14px;"&gt;Suppress&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;        &lt;span id="xn7_0e314e54da8c82a63fd3354d25a0b313" class="sentence"&gt;环境事务上下文在创建范围时被取消。&lt;/span&gt;  &lt;span id="xn8_84144a9d5427ddc252701579256f180e" class="sentence"&gt;范围中的所有操作都在无环境事务上下文的情况下完成。&lt;/span&gt;  &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;这里Suppress有点特别，当使用Suppress范围内，所有的操作都将在无事务的上下文中执行，即当中的程序不再受到事务的保护，这大多数在嵌套式事务中使用。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; DoWork()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt;(TransactionScope scope=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;           &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在事务环境中执行操作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;           ......  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;           NoTransaction();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;           scope.Complete();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;  }&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; NoTransaction()&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;      &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;在无事务环境中执行&lt;/span&gt;&lt;span style="color: #008000;"&gt;操作&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt;(TransactionScope scope=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope(TransactionScopeOption.Suppress)）&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;          ......&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;  }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;3. 应用实例，在Entity Framework中使用TransactionScope&lt;/strong&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Order GetOrder(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;      BusinessContext _context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; BusinessContext();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;      Order order = &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;          { &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;数据操作&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br style="color: #008000;" /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; list = _context.Order.Include(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;OrderItem&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                  .Where(x =&amp;gt; x.ID == id);&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (list.Count() &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                  order = list.First();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                  order = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Order();&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;              scope.Complete();      &lt;span style="color: #008000;"&gt;//事务提交&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (Exception ex)&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;          ......&lt;span style="color: #008000;"&gt; //&lt;/span&gt;&lt;span style="color: #008000;"&gt;出错处理，并返回一个空对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;          order=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Order（）;   &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;      _context.Dispose();&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; order;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;  }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p id="t5"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;五、在WCF中实现事务&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. WCF服务中事务的边界&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;把WCF的事务边界独立成一节，是想大家注意这一点，WCF服务中，事务是以方法为边界的，每个WCF服务的方法可以有独立事务的执行模式。而事务可以在多个服务中传播，也可以在服务端与客户端之间传播，介时事务管理器的级数将会晋升。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.简单的事务使用方式&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;TransactionScopeRequired与TransactionAutoComplete是WCF事务的基本元素。&lt;/p&gt;&lt;p&gt;当TransactionScopeRequired等于true时，代表在此WCF服务的方法中启动事务。反之，当此值为false时代表此方法不执行事务。&lt;/p&gt;&lt;p&gt;当TransactionAutoComplete等于true时，代表该方法使用隐式事务，这也是微软推荐使用的方法。即当该方法在运行过程中没有抛出Exception，操作就默认为完成，事务将自动提交。如果期间出现任何异常，事务就会自动回滚。如果TransactionAutoComplete等于false时，该方法即为显式事务，即需要在方法完成时利用OperationContext.Current.SetTransactionComplete () 显式提交事务。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; [ServiceContract(SessionMode=SessionMode.Required)]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;      [OperationContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method1();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;      [OperationContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method2();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;  }&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Service : IService&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;     &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;隐式事务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;     [OperationBehavior(TransactionScopeRequired=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;,TransactionAutoComplete=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;)]&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method1()&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;         ...........&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;      &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;显式事务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;      [OperationBehavior(TransactionScopeRequired=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;,TransactionAutoComplete=&lt;span style="color: #0000ff;"&gt;false&lt;/span&gt;)]&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method2()&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;         ...........&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;         OperationContext.Current.SetTransactionComplete();&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;  }&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;strong&gt;3. 事务的传播&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在同一个应用程序域中，事务默认能相互传播，在上面的例子当中，当方法Method1（）直接调用Mehtod2（）的时候，事务也能够成功流转。&lt;/p&gt;&lt;p&gt;事务也能够在服务端与客户端之间传播，还能跨越服务边界，在多个系统当中流转，在WCF里把服务中的事务传播称作事务流（Transaction Flow）。如果事务流需要在服务端和客户端成功传播或使用分布式事务，必须具备以下条件：&lt;/p&gt;&lt;ul&gt;&lt;li&gt;绑定必须支持事务，在WCF内并非所有绑定都支持事务，像常用的BasicHttpBinding就不支持事务的传播。只有以下几个绑定才能支持事务流的运转：NetTcpBinding、WSHttpBinding、WSDualHttpBinding、WSFederationHttpBinding、NetNamedPipeBinding。&lt;/li&gt;&lt;li&gt;服务方法必须设置好TransactionScopeRequired与TransactionAutoComplete两个事务的基本元素，要成功启动事务，这是基础条件。&lt;/li&gt;&lt;li&gt;把TransactionFlow设置为true，这代表启动事务流，允许在SOAP头部放置事务的信息。一般情况下TransactionFlow的默认值为false ，这表示事务只能在服务器的同一应用程序域内流转，而不能实现服务端与客户端之间的传播。&lt;/li&gt;&lt;li&gt;把服务契约的TransactionFlowOption设置为Allowed，这代表允许客户端的事务传播到服务端。&lt;/li&gt;&lt;li&gt;客户端必须启动一个事务，在最后使用TransactionScope.Complete ( ) 提交事务。&lt;/li&gt;&lt;/ul&gt;&lt;div style="padding-top: 10px; padding-left: 70px;"&gt;&lt;em&gt;&lt;strong&gt;TransactionFlowOption说明&lt;/strong&gt; &lt;br /&gt;TransactionFlowOption有三个选项：&lt;/em&gt;&lt;br /&gt;&lt;em&gt;一为NotAllowed，这代表了禁止客户端传播事务流到服务端，即使客户端启动了事务，该事务也会被忽略; &lt;/em&gt;&lt;br /&gt;&lt;em&gt;二为Allowed，这代表允许客户端的事务传播到服务端，但服务器端不一定会引用到此事务; &lt;/em&gt;&lt;br /&gt;&lt;em&gt;三为Mandatory，这代表服务端与客户端必须同时启动事务流，否则就会抛出InvalidOperationException异常。&lt;/em&gt;&lt;/div&gt;&lt;p id="t5@1"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;下面举几个例子来讲解一下事务流的使用方式。&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&amp;nbsp;3.1 在服务端与客户端之间传播事务&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;这是事务流的基本使用方式，首先在服务端使用wsHttpBinding绑定建立一个服务契约，在方法中利用TransactionInformation对象检测一下事务的状态。然后设置好TransactionScopeRequired与TransactionAutoComplete属性来启动事务，在*.config中把TransactionFlow设置为true。再把服务的TransactionFlowOption设置为Allowed，最后在客户端通过TransactionScope.Complete（）的方法提交事务。&lt;/p&gt;&lt;p&gt;服务端：&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Example&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;      [ServiceContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IExampleService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;          [OperationContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method1();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; ExampleService : IExampleService&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用隐式事务，并把TransactionFlowOption设置为Allowed打开事务流&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;          [OperationBehavior(TransactionAutoComplete=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;,TransactionScopeRequired=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;)]&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;          [TransactionFlow(TransactionFlowOption.Allowed)]&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method1()&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;通过TransactionInformation检测事务状态&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;              Transaction transaction = Transaction.Current;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; info=&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  DistributedIndentifier:{0} \n  LocalIndentifier:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                  transaction.TransactionInformation.DistributedIdentifier,&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                  transaction.TransactionInformation.LocalIdentifier);&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;              Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Method1: \n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+info);&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;               &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;启动服务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;              ServiceHost exampleHost = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ServiceHost(&lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(Example.ExampleService));&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;              exampleHost.Open();&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;              Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;service start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;              Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;              Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;service end&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;              exampleHost.Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;  }&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;  &amp;lt;configuration&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;      &amp;lt;system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;        &amp;lt;bindings&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;          &amp;lt;wsHttpBinding&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;             &amp;lt;!--启动事务流--&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;            &amp;lt;binding name=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;defaultWSHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; transactionFlow=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;true&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;          &amp;lt;/wsHttpBinding&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;        &amp;lt;/bindings&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;          &amp;lt;behaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;              &amp;lt;serviceBehaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;51&lt;/span&gt;                  &amp;lt;behavior name=&lt;span style="color: #800000;"&gt;""&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;52&lt;/span&gt;                      &amp;lt;serviceMetadata httpGetEnabled=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;true&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;53&lt;/span&gt;                      &amp;lt;serviceDebug includeExceptionDetailInFaults=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;false&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;54&lt;/span&gt;                  &amp;lt;/behavior&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;55&lt;/span&gt;              &amp;lt;/serviceBehaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;56&lt;/span&gt;          &amp;lt;/behaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;57&lt;/span&gt;          &amp;lt;services&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;58&lt;/span&gt;              &amp;lt;service name=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Example.ExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;59&lt;/span&gt;                  &amp;lt;!--使用支持事务流的wsHttpBinding绑定--&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;60&lt;/span&gt;                  &amp;lt;endpoint address=&lt;span style="color: #800000;"&gt;""&lt;/span&gt; binding=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;wsHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; bindingConfiguration=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;defaultWSHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;61&lt;/span&gt;                                       contract=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Example.IExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;62&lt;/span&gt;                      &amp;lt;identity&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;63&lt;/span&gt;                          &amp;lt;dns value=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;localhost&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;64&lt;/span&gt;                      &amp;lt;/identity&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;65&lt;/span&gt;                  &amp;lt;/endpoint&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;66&lt;/span&gt;                  &amp;lt;endpoint address=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;mex&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; binding=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;mexHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; contract=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;IMetadataExchange&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;67&lt;/span&gt;                  &amp;lt;host&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;68&lt;/span&gt;                      &amp;lt;baseAddresses&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;69&lt;/span&gt;                          &amp;lt;add baseAddress=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;http://localhost:7200/Example/ExampleService/&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;70&lt;/span&gt;                      &amp;lt;/baseAddresses&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;71&lt;/span&gt;                  &amp;lt;/host&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;72&lt;/span&gt;              &amp;lt;/service&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;73&lt;/span&gt;          &amp;lt;/services&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;74&lt;/span&gt;      &amp;lt;/system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;75&lt;/span&gt;  &amp;lt;/configuration&amp;gt;&lt;/div&gt;&lt;p&gt;客户端：&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;  &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;  {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope(TransactionScopeOption.Required))&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;                 ShowTransactionMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 ExampleServiceReference.ExampleServiceClient exampleService1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                                         ExampleServiceReference.ExampleServiceClient();&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                 exampleService1.Method1();&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                 ShowTransactionMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;exampleService started&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                 exampleService1.Close(); &lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 &lt;span style="color: #008000;"&gt;//事务提交&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                 scope.Complete();  &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;             }   &lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;检查事务的状态&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowTransactionMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (Transaction.Current != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;                 Transaction transaction = Transaction.Current;&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; info = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  DistributedIndentifier:{0} \n  LocalIndentifier:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;                transaction.TransactionInformation.DistributedIdentifier,&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;                transaction.TransactionInformation.LocalIdentifier);&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;                 Console.WriteLine(data+&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt; \n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + info);&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;图中上面代表服务端，下面代表客户端。可以看到，在客户端刚启动事务时，事务只一般的LTM轻量级事务，DistributedIndentifier为空值。当调用ExampleService服务后，事务的级别便提升为分布式事务。而服务端与客户端的事务正是通过DistributedIndentifier为标识的。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2011/64989/2011123113365443.jpg" alt="" width="788" height="401" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;br /&gt;&lt;strong&gt;3.2使用分布式事务协调多个服务端的操作&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在分布式系统当中，单个客户端可能引用多个服务，分布式事务能协调多方的操作。多个系统中的操作要不同时成功，要不同时失败。下面的例子中，客户端同时引用了ExampleService服务和ExtensionService服务，并启动了分布式事务。而在客户端与两个服务端的事务都是通过DistributedIndentifier 作为事务的标识的。&lt;/p&gt;&lt;p&gt;服务端：&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt;  1&lt;/span&gt; &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;*******************************ExampleService*************************************************************************&lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;  2&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Example&lt;br /&gt;&lt;span style="color: #008080;"&gt;  3&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;  4&lt;/span&gt;       [ServiceContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt;  5&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IExampleService&lt;br /&gt;&lt;span style="color: #008080;"&gt;  6&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt;  7&lt;/span&gt;           [OperationContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt;  8&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method1();&lt;br /&gt;&lt;span style="color: #008080;"&gt;  9&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 10&lt;/span&gt;   &lt;br /&gt;&lt;span style="color: #008080;"&gt; 11&lt;/span&gt;       &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; ExampleService : IExampleService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 12&lt;/span&gt;       {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 13&lt;/span&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用隐式事务，并把TransactionFlowOption设置为Allowed &lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 14&lt;/span&gt;           [OperationBehavior(TransactionAutoComplete=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;,TransactionScopeRequired=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;)]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 15&lt;/span&gt;           [TransactionFlow(TransactionFlowOption.Allowed)]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 16&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method1()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 17&lt;/span&gt;           {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 18&lt;/span&gt;               &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;通过TransactionInformation检测事务状态&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 19&lt;/span&gt;               Transaction transaction = Transaction.Current;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 20&lt;/span&gt;               &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; info=&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  DistributedIndentifier:{0} \n  LocalIndentifier:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 21&lt;/span&gt;                   transaction.TransactionInformation.DistributedIdentifier,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 22&lt;/span&gt;                   transaction.TransactionInformation.LocalIdentifier);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 23&lt;/span&gt;               Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Method1: \n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;+info);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 24&lt;/span&gt;           }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 25&lt;/span&gt;   &lt;br /&gt;&lt;span style="color: #008080;"&gt; 26&lt;/span&gt;           &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 27&lt;/span&gt;           {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 28&lt;/span&gt;                &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;启动服务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 29&lt;/span&gt;               ServiceHost exampleHost = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ServiceHost(&lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(Example.ExampleService));&lt;br /&gt;&lt;span style="color: #008080;"&gt; 30&lt;/span&gt;   &lt;br /&gt;&lt;span style="color: #008080;"&gt; 31&lt;/span&gt;               exampleHost.Open();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 32&lt;/span&gt;   &lt;br /&gt;&lt;span style="color: #008080;"&gt; 33&lt;/span&gt;               Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;service start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 34&lt;/span&gt;               Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 35&lt;/span&gt;               Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;service end&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 36&lt;/span&gt;   &lt;br /&gt;&lt;span style="color: #008080;"&gt; 37&lt;/span&gt;               exampleHost.Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 38&lt;/span&gt;           }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 39&lt;/span&gt;       }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 40&lt;/span&gt;   }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 41&lt;/span&gt;   &lt;br /&gt;&lt;span style="color: #008080;"&gt; 42&lt;/span&gt;   &amp;lt;configuration&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 43&lt;/span&gt;       &amp;lt;system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 44&lt;/span&gt;         &amp;lt;bindings&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 45&lt;/span&gt;           &amp;lt;wsHttpBinding&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 46&lt;/span&gt;              &amp;lt;!--启动事务流--&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 47&lt;/span&gt;             &amp;lt;binding name=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;defaultWSHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; transactionFlow=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;true&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 48&lt;/span&gt;           &amp;lt;/wsHttpBinding&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 49&lt;/span&gt;         &amp;lt;/bindings&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 50&lt;/span&gt;           &amp;lt;behaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 51&lt;/span&gt;               &amp;lt;serviceBehaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 52&lt;/span&gt;                   &amp;lt;behavior name=&lt;span style="color: #800000;"&gt;""&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 53&lt;/span&gt;                       &amp;lt;serviceMetadata httpGetEnabled=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;true&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 54&lt;/span&gt;                       &amp;lt;serviceDebug includeExceptionDetailInFaults=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;false&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 55&lt;/span&gt;                   &amp;lt;/behavior&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 56&lt;/span&gt;               &amp;lt;/serviceBehaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 57&lt;/span&gt;           &amp;lt;/behaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 58&lt;/span&gt;           &amp;lt;services&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 59&lt;/span&gt;               &amp;lt;service name=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Example.ExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 60&lt;/span&gt;                   &amp;lt;!--使用支持事务流的wsHttpBinding绑定--&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 61&lt;/span&gt;                   &amp;lt;endpoint address=&lt;span style="color: #800000;"&gt;""&lt;/span&gt; binding=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;wsHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"   &lt;span style="color: #000000;"&gt;contract=&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Example.IExampleService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 62&lt;/span&gt;                                 bindingConfiguration=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;defaultWSHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;  &amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 63&lt;/span&gt;                       &amp;lt;identity&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 64&lt;/span&gt;                           &amp;lt;dns value=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;localhost&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 65&lt;/span&gt;                       &amp;lt;/identity&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 66&lt;/span&gt;                   &amp;lt;/endpoint&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 67&lt;/span&gt;                   &amp;lt;endpoint address=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;mex&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; binding=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;mexHttpBinding&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; contract=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;IMetadataExchange&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 68&lt;/span&gt;                   &amp;lt;host&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 69&lt;/span&gt;                       &amp;lt;baseAddresses&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 70&lt;/span&gt;                           &amp;lt;add baseAddress=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;http://localhost:7200/Example/ExampleService/&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; /&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 71&lt;/span&gt;                       &amp;lt;/baseAddresses&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 72&lt;/span&gt;                   &amp;lt;/host&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 73&lt;/span&gt;               &amp;lt;/service&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 74&lt;/span&gt;           &amp;lt;/services&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 75&lt;/span&gt;       &amp;lt;/system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 76&lt;/span&gt;   &amp;lt;/configuration&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 77&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 78&lt;/span&gt; &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;*************************************Extension**************************************************************&lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 79&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Extension&lt;br /&gt;&lt;span style="color: #008080;"&gt; 80&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 81&lt;/span&gt;     [ServiceContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 82&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IExtensionService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 83&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 84&lt;/span&gt;         [OperationContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 85&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; DoWork();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 86&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 87&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 88&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; ExtensionService : IExtensionService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 89&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 90&lt;/span&gt;         [OperationBehavior(TransactionAutoComplete=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;,TransactionScopeRequired=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;)]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 91&lt;/span&gt;         [TransactionFlow(TransactionFlowOption.Allowed)]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 92&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; DoWork()&lt;br /&gt;&lt;span style="color: #008080;"&gt; 93&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 94&lt;/span&gt;             Transaction transaction = Transaction.Current;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 95&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; info = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  DistributedIndentifier:{0} \n  LocalIndentifier:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 96&lt;/span&gt;                 transaction.TransactionInformation.DistributedIdentifier,&lt;br /&gt;&lt;span style="color: #008080;"&gt; 97&lt;/span&gt;                 transaction.TransactionInformation.LocalIdentifier);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 98&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;DoWork: \n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + info);&lt;br /&gt;&lt;span style="color: #008080;"&gt; 99&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;100&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;101&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt;102&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;103&lt;/span&gt;             Console.WriteLine(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;extension service start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;104&lt;/span&gt;             ServiceHost host = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; ServiceHost(&lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(ExtensionService));&lt;br /&gt;&lt;span style="color: #008080;"&gt;105&lt;/span&gt;             host.Open();&lt;br /&gt;&lt;span style="color: #008080;"&gt;106&lt;/span&gt;             Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;107&lt;/span&gt;             host.Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt;108&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;109&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;110&lt;/span&gt; }&lt;br /&gt;&lt;span style="color: #008080;"&gt;111&lt;/span&gt; &amp;lt;configuration&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;112&lt;/span&gt;      &amp;lt;!--略--&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;113&lt;/span&gt;      ...................  &lt;br /&gt;&lt;span style="color: #008080;"&gt;114&lt;/span&gt; &amp;lt;/configuration&amp;gt;&lt;/div&gt;&lt;p&gt;客户端&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Test&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;     &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;     {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope(TransactionScopeOption.RequiresNew))&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                 ShowTransactionMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;start&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                 ExampleServiceReference.ExampleServiceClient exampleService1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                                         ExampleServiceReference.ExampleServiceClient();&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                 exampleService1.Method1();&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;                 ShowTransactionMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;exampleService started&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                 ExtensionServiceReference.ExtensionServiceClient extensionService = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                                         ExtensionServiceReference.ExtensionServiceClient();&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                 extensionService.DoWork();&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                 ShowTransactionMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;extensionService started&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;         &lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                 exampleService1.Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                 extensionService.Close();&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                 &lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;                 scope.Complete();&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;                 &lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;              Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;         &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;检查事务的状态&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;         &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowTransactionMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;         {&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;             &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (Transaction.Current != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;             {&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;                 Transaction transaction = Transaction.Current;&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;                 &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; info = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;  DistributedIndentifier:{0} \n  LocalIndentifier:{1}&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                      transaction.TransactionInformation.DistributedIdentifier,&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                      transaction.TransactionInformation.LocalIdentifier);&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                 Console.WriteLine(data+&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt; \n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; + info);&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;             }&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;         }&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;     }&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;从测试结果可以看到在多个不同的服务端与客户端之间，都是通过DistributedIndentifier分布式事务ID来进行信息沟通的。一旦任何一出现问题，事务都会共同回滚，这对分布式开发是十分重要的。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2011/64989/2011123114232981.jpg" alt="" width="735" height="496" /&gt;&lt;/p&gt;&lt;p&gt;值得注意的一点，事务必须由客户端提交，当客户端调用无事务状态时，两个服务端的事务则无法进行辨认，即其中一方出错，事务出现回滚，另一方也无法感知，这样容易引起逻辑性错误。试着把客户端代码改为 using (TransactionScope scope = new TransactionScope(TransactionScopeOption.Suppress)){...}，再运作一下，可以看到以下结果。事务都是由两个服务端分别管理，系统并无启动分布式事务。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2011/64989/2011123114333580.jpg" alt="" width="667" height="357" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;应该注意：分布式事务会耗费较大的资源，在没必要的情况下，应该尽量使用LTM级量级事务管理器，而避免使用DTC分布式事务管理。&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4.事务的的隔离性&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;事务的隔离性是通过TransactionIsolationLevel来定义的，它存在以下几个级别：&lt;/p&gt;&lt;table style="border-color: #464646; border-style: solid; border-width: 1px; width: 600px; height: 160px;" border="1 " cellspacing="10" cellpadding="1" align="left"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td style="width: 160px;"&gt;&lt;span style="font-size: 14px;"&gt;Unspecified&lt;/span&gt;&lt;/td&gt;&lt;td style="text-align: left;"&gt;&amp;nbsp;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;ReadUncommitted&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;在读取数据时保持共享锁以避免读取已修改的数据，但在事务结束前这些数据可能已更改，因此会导致不可重复的读取和虚假数据。&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;ReadCommitted&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;发出共享锁定并允许非独占方式的锁定。 &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;RepeatableRead&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;在查询中使用的所有数据上放置锁，以防止其他用户更新这些数据。这防止了不可重复的读取，但仍有可能产生虚假行。 &lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;Serializable&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;默认级别，也是最高级别。表示事务完成前禁止外界更新数据&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;Chaos&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;不使用隔离&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;Snapshot&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&amp;nbsp;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;需要注意服务端与客户端必须使用同一级别的隔离模式，否则系统将会抛出FaultException异常。&lt;/p&gt;&lt;p&gt;服务类必须在至少一个方法开启了事务后才可以设置隔离模式&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;    {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;        [OperationContract]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;    }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;    &lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;    [ServiceBehavior(TransasctionIsolationLevel=IsolationLevel.ReadCommitted)]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Service : IService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;    {&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;       &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;隐式事务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;        [OperationBehavior(TransactionScopeRequired=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;,TransactionAutoComplete=&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;)]&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method()&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;        {..........}&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;    }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5.事务的超时&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;当事务实现隔离时，资源将会被锁定，如果一些事务长期占有资源，那将容易造成死锁，为了避免这个问题，事务有一个超时限制，这个超时默认值为60s。如果事务超过此时间，即使没有发生异常，也会自动中止。&lt;/p&gt;&lt;p&gt;超时时候可以通过特性设置，也可使用*.config文件设置。下面的两段代码有着相同的效果，就是把超时时间设置为10s。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; [ServiceBehavior(TransactionTimeout=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;00:00:10&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;)]&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Service:IService&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt; {......}&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;  &amp;lt;configuration&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;        ........&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;       &amp;lt;system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;            ........&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;            &amp;lt;services&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                 &amp;lt;service name=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;MyService&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; behaviorConfiguration=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;myBehavior&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;                        ......&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;                 &amp;lt;/service&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;            &amp;lt;/services&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;            &amp;lt;behaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                 &amp;lt;serviceBehaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                     &amp;lt;behavior name=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;myBehavior&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt; transactionTimeout=&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;00:00:10&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;/&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                &amp;lt;/serviceBehaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;            &amp;lt;/behaviors&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;       &amp;lt;/system.serviceModel&amp;gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt; &amp;lt;/configuration&amp;gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p id="t6"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;六、嵌套式事务&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;嵌套式事务经常会出现在项目中，但往往容易被大家忽略，下面介绍一下 嵌套式事务的用法：&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope1 = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())            &lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;        ..............               &lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope2=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope(TransactionScopeOption.RequiresNew))&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;        {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;               ..............&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;               scope2.Complete();   &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;只完成嵌套式的内部事务，但事务并未正式提交&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;        }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;        scope1.Complete();  &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;代表完成所有事务&lt;/span&gt;&lt;span style="color: #008000;"&gt;，事务正式提交&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt; }&lt;/div&gt;&lt;p&gt;一般项目中，大家都只会把事务用在DAL层，用于管理数据的CRUD，但其实在一些操作中，某些数据的操作必须具有一致性。比如在订单管理中，当插入一条OrderItem时，Order表内的总体价格，商品数量等也会随之改变。很多人把两个表的操作合成一个方法，放在OrderDAL中完成。但其实这样做违返设计的原则，因为计算Order的总体价格时可能会包含商品优惠、客户等级、客户积分等等业务逻辑，而在DAL层不应该包含任何的业务逻辑存在的，所以这样操作应该放在业务层完成。这时候，业务层的方法内就需要同时调用OrderItemDAL的AddOrderItem（OrderItem） 方法和OrderDAL的UpdateOrder（Order）方法，为了保证数据的一致性更新，就需要使用嵌套式事务。但这往往容易被开发人员所忽略，当Order表的更新成功而OrderItem表的插入失败时，系统不能保证数据的同步回滚，那就会造成数据的逻辑性错误。&lt;/p&gt;&lt;p&gt;下面的例子就是为了保证数据一致性更新而使用的嵌套式事务，&lt;strong&gt;在使用嵌套式事务的时候要应该注意及其把对象释放，避免做成死锁&lt;/strong&gt;。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; DAL&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt; {     &lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderDAL&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; UpdateOrder(Order order)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;                   ......         &lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;                   scope.Complete();&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderItemDAL&lt;br /&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AddOrderItem(OrderItem orderItem)&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;                  ......&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;                  scope.Complete();&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;  }&lt;br /&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt; &lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; BLL&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt; {&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderManager&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AddOrderItem(OrderItem item)&lt;br /&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;                  OrderItemDAL orderItemDAL=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderItemDAL();&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;                  orderItemDAL.AddOrderItem(item);&lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;                  OrderDAL orderDAL=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderDAL();&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;                  ........&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;                  orderDAL.UpdateOrder(order);&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;                  scope.Complete();&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;      }&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt; }&lt;/div&gt;&lt;p id="t7"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;七、异步事务&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;记得在第二节的时候曾经提起过事务类Transaction的方法中包含方法&lt;/p&gt;&lt;p&gt;public DependentTransaction DependentClone（DependentCloneOption）&lt;/p&gt;&lt;p&gt;此方法作用是克隆当前的事务，它在多线程调用同一事务的情况下使用经常使用。其中DependentCloneOption包含有两个选项：&lt;/p&gt;&lt;p&gt;一为BlockCommitUntilComplete，这表示在依赖事务未完成前，事务将处于阻塞状态，只有在所有依赖事务完成后，事务才能执行提交;&lt;/p&gt;&lt;p&gt;二为RollbackInNotComplete，这表示依赖事务必须在事务完成前调用Complete（），否则事务会被视为失败。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;在普通情况下，事务都会通过Transaction.Current 来获取，但此方法只能获取当前线程下的事务对象，在异步方法当中，这只会返回一个空值 null 。此时就需要使用DependentClone 方法获取依赖事务对象 DependentTransaction ，再把此对象作为参数传递到回调函数中。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #008080;"&gt; 1&lt;/span&gt;      &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;&lt;span style="color: #008080;"&gt; 2&lt;/span&gt;      {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 3&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;&lt;span style="color: #008080;"&gt; 4&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt; 5&lt;/span&gt;              Method();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 6&lt;/span&gt;              Console.ReadKey();&lt;br /&gt;&lt;span style="color: #008080;"&gt; 7&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt; 8&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt; 9&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Method()&lt;br /&gt;&lt;span style="color: #008080;"&gt;10&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;11&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;&lt;span style="color: #008080;"&gt;12&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;13&lt;/span&gt;                  ShowMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Main Thread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;14&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;15&lt;/span&gt;                  &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取一个依赖事务，把依赖事务作为回调参数传到回调函数中&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;16&lt;/span&gt;                  DependentTransaction dependentTransaction=&lt;br /&gt;&lt;span style="color: #008080;"&gt;17&lt;/span&gt;                     Transaction.Current.DependentClone(DependentCloneOption.BlockCommitUntilComplete);&lt;br /&gt;&lt;span style="color: #008080;"&gt;18&lt;/span&gt;                  ThreadPool.QueueUserWorkItem(&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; WaitCallback(AsyncThread), dependentTransaction);&lt;br /&gt;&lt;span style="color: #008080;"&gt;19&lt;/span&gt;                  ........&lt;br /&gt;&lt;span style="color: #008080;"&gt;20&lt;/span&gt;                  scope.Complete(); &lt;span style="color: #008000;"&gt;//完成主线程事务，在依赖事务完成前，事务提交将处于阻塞状态&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #008080;"&gt;21&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;22&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;23&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;24&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; AsyncThread(&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; transaction)&lt;br /&gt;&lt;span style="color: #008080;"&gt;25&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;26&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取依赖事务，利用TransactionScope（Transaction）构造函数生成隐式事务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;27&lt;/span&gt;              DependentTransaction dependentTransaction = (DependentTransaction)transaction;&lt;br /&gt;&lt;span style="color: #008080;"&gt;28&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope(dependentTransaction))&lt;br /&gt;&lt;span style="color: #008080;"&gt;29&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;30&lt;/span&gt;                  ShowMessage(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;AsyncThread&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;&lt;span style="color: #008080;"&gt;31&lt;/span&gt;                  ..........&lt;br /&gt;&lt;span style="color: #008080;"&gt;32&lt;/span&gt;                  scope.Complete();  &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;完成异步事务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;33&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;34&lt;/span&gt;              &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;完成依赖事务&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #008080;"&gt;35&lt;/span&gt;              dependentTransaction.Complete();&lt;br /&gt;&lt;span style="color: #008080;"&gt;36&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;37&lt;/span&gt;  &lt;br /&gt;&lt;span style="color: #008080;"&gt;38&lt;/span&gt;          &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; ShowMessage(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; data)&lt;br /&gt;&lt;span style="color: #008080;"&gt;39&lt;/span&gt;          {&lt;br /&gt;&lt;span style="color: #008080;"&gt;40&lt;/span&gt;              &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (Transaction.Current != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;&lt;span style="color: #008080;"&gt;41&lt;/span&gt;              {&lt;br /&gt;&lt;span style="color: #008080;"&gt;42&lt;/span&gt;                  Transaction transaction = Transaction.Current;&lt;br /&gt;&lt;span style="color: #008080;"&gt;43&lt;/span&gt;                  &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; info = &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;{0}:{1}\nTransaction:\n  DistributedIndentifier:{2} \n  LocalIndentifier:{3}\n&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;br /&gt;&lt;span style="color: #008080;"&gt;44&lt;/span&gt;                      data,Thread.CurrentThread.ManagedThreadId.ToString(),&lt;br /&gt;&lt;span style="color: #008080;"&gt;45&lt;/span&gt;                      transaction.TransactionInformation.DistributedIdentifier,&lt;br /&gt;&lt;span style="color: #008080;"&gt;46&lt;/span&gt;                      transaction.TransactionInformation.LocalIdentifier);&lt;br /&gt;&lt;span style="color: #008080;"&gt;47&lt;/span&gt;                  Console.WriteLine(info);&lt;br /&gt;&lt;span style="color: #008080;"&gt;48&lt;/span&gt;              }&lt;br /&gt;&lt;span style="color: #008080;"&gt;49&lt;/span&gt;          }&lt;br /&gt;&lt;span style="color: #008080;"&gt;50&lt;/span&gt;      }&lt;/div&gt;&lt;p&gt;首先在主线程中利用Transaction.DependentClone(DependentCloneOption.BlockCommitUntilComplete) 方法生成一个依赖事务，注意方法使用了BlockCommitUntilComplete的方式生成，即事务将在所有依赖事务使用Complete（）后才能执行提交。&lt;/p&gt;&lt;p&gt;然后利用ThreadPool.QueueUserWorkItem（WaitCallback，Object）方法把依赖事务作为回调参数传递到回调函数中。&lt;/p&gt;&lt;p&gt;最后在回调函数中使用TransactionScope（transaction）构造函数生成对象，这代表把参数transaction作为当前的环境事务对象。观察下面的运行结果，两个线程中的事务都是同一个事务。&lt;/p&gt;&lt;p&gt;&lt;img src="http://pic002.cnblogs.com/images/2012/64989/2012010114313127.jpg" alt="" width="646" height="231" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;结束语&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;事务是在多个层次都会使用到的，但很多项目当中往往会忽略了这一点而只在数据层使用，在大型的系统当中这样可能会影响到系统的一致性。特别是在分布式系统当中，操作往往同时存在于多个不同的系统当中，事务的处理更显示出其重要性。&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;希望这篇文章能对大家的工作有帮助，对.NET开发有兴趣的朋友请加入博客园讨论小组&lt;span style="color: #0000ff;"&gt;&lt;a href="http://home.cnblogs.com/group/102576/" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&amp;ldquo;.NET高级编程&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; 一起探讨！&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;&lt;a href="#t0"&gt;&lt;span style="color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;C#综合揭秘&lt;/span&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/06/2379235.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说进程、应用程序域与上下文&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/07/2310495.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;细说多线程（上）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/02/08/2320914.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说多线程（下）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;细说事务&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/03/22/2389318.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;深入分析委托与事件&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="float: right; text-align: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;br /&gt;&lt;a title="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html" href="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html&lt;/span&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;a title="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html" href="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2289106.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2012/01/05/2289106.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/leslies2/archive/2011/12/12/2272722.html</id><title type="text">结合领域驱动设计的SOA分布式软件架构</title><summary type="text">领域驱动设计DDD的总体结构，Repository层使用ORM映射或SQL命令等方式把持久化数据转化为领域对象，然后根据业务逻辑设计对应领域层服务Domain Service 。接着应用层进行操作上的协调，利用Repository、领域模型、领域层服务Domain Service 完成业务需要，再通过数据转换器把领域对象Domain Object转化为数据传输对象DTO。最后，利用远程通讯技术把应用层的服务（Application Service）对外开放。注意留意的是SOA系统中，UI表现层与Application Service应用层服务是实现分离的，表现层可以同时调用多方的远程服务来完成工作。</summary><published>2011-12-12T01:49:00Z</published><updated>2011-12-12T01:49:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2011/12/12/2272722.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2011/12/12/2272722.html"/><content type="html">&lt;p id="t0" style="text-align: left;"&gt;引言&lt;/p&gt;&lt;p&gt;本文主要是参考Martion Fowler所著的《企业应用架构模式》与Eric Evans所著的《领域驱动设计》这两本泰山之作，加上本人在近年实际的工作过程中开发SOA系统所认识到的问题所写的一篇文章，欢迎各位点评。&lt;/p&gt;&lt;p&gt;最后两节&amp;nbsp; &lt;span style="color: #0000ff;"&gt;&lt;a href="#t7"&gt;&lt;span style="color: #0000ff;"&gt;细说应用层&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; 、&lt;a href="#t8"&gt;&lt;span style="color: #0000ff;"&gt;系统总体架构&amp;nbsp;&lt;/span&gt;&lt;/a&gt;是本文的重点，着重说明领域驱动设计与SOA之间的关系，对DDD有一定基础的朋友可以越过前面的几节，直接查看第七、八节。&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://files.cnblogs.com/leslies2/Business.rar"&gt;&lt;span style="color: #0000ff;"&gt;源代码下载&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; （数据库可以在.edmx文件根据模型生成）&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="color: #0000ff;"&gt;目录&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t1"&gt;&lt;span style="color: #0000ff;"&gt;一、SOA与DDD的定义&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t2"&gt;&lt;span style="color: #0000ff;"&gt;二、DDD的分层结构&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a style="color: #0000ff;" href="#t3"&gt;三、把业务关系转化为领域模型 &lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a style="color: #0000ff;" href="#t4"&gt;四、细说Repository &lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t5"&gt;&lt;span style="color: #0000ff;"&gt;五、领域层的服务&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t6"&gt;&lt;span style="color: #0000ff;"&gt;六、工厂模式Factory&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="#t7"&gt;&lt;span style="color: #0000ff;"&gt;七、细说应用层&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#t8"&gt;&lt;span style="color: #0000ff;"&gt;八、系统总体架构&amp;nbsp;&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p id="t1"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;一、SOA与DDD的定义&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;SOA与DDD都是常用的系统架构，但两者之间所针对的核心是不同的。&lt;/p&gt;&lt;p&gt;SOA（面向服务架构）由Gartner 在1996年提出来，它是一种分布式的软件架构，它可以根据需求通过网络对松散耦合的粗粒度应用组件进行部署、组合和使用。简单来说，SOA就是一种大型系统开发的体系架构，在基于SOA架构的系统中，具体应用程序的功能是由一些松耦合并且具有统一接口的组件（也就是service）组合构建起来的，它是针对多核心多平台之间的数据交换。&lt;/p&gt;&lt;p&gt;DDD（领域驱动设计）由Eric Evans在2004提出，它的核心内容是&amp;ldquo;如何将业务领域概念映射到软件工程当中&amp;rdquo;。它推翻了&amp;ldquo;软件从数据层开发设计&amp;rdquo;的旧习惯，强调领域模型在软件中发挥的强大力量，注重如何把企业内部复杂的业务流程转化为软件。&lt;/p&gt;&lt;p&gt;也许可以认为SOA针对的是大型系统的总体架构，注重如何把系统进行项目分离，隔离开发，最后实现系统合并。而DDD是针对单个项目的开发管理过程，注重如何利用领域模型把业务需求转化为软件。两者之间并没有存在理论上的冲突，能把两者结合，各展所长，更能发挥各自的优势。&lt;/p&gt;&lt;p id="t2"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;二、DDD的分层结构&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. 概念&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;从概念上来说，领域驱动设计架构主要分为基础设施层、领域层、应用层、表现层4个概念层。&lt;/p&gt;&lt;p&gt;基础结构层：是为各层提供各项通用技术能力而构建的，它可以为领域层提供像Hibernate、LINQ、ADO.NET等持久化机制，为应用层传递消息，为表现层提供插件等等。&lt;/p&gt;&lt;p&gt;领域层：它是系统的核心部分，代表业务的逻辑概念。它会根据业务的实际流程定制了业务信息以及业务规则，并按一定的关系制定领域模型。领域模型尽管需要依赖基础结构层进行保存，但领域模型之间的逻辑关系是跟基础结构层相隔离的。即使基础结构层从NHibernate技术转换成LINQ技术，也不会影响到领域层的结构。领域模型只会依赖实际的业务逻辑，它只会根据业务的转变而灵活变动。&lt;/p&gt;&lt;p&gt;应用层：它的任务是协调领域层与表现层之间的关系，也可以作为系统与外界沟通的桥梁，在这层里面不会包括任何的业务逻辑。&lt;strong&gt;在SOA面向服务架构，这一层起着重要的作用&lt;/strong&gt;，在第七节将详细说明&lt;strong&gt;。&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;表现层：它是常用的界面开发，可以以页面（ASP.NET、JSP），窗口（WinForm、WPF、Swing）等形式表现，它的主要职责是负责与用户进行信息沟通。(注意：在一般的项目开发中，Web服务会作为与外界通讯的接口放置在表现层中，但在SOA中，Web服务会大多置于应用层中，下面将会作进一步解释）&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011120311070087.gif" alt="" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2. 开发实例&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在此先举个常见的订单管理例子，&lt;strong&gt;在下面的章节里都会以这个实例为参考&lt;/strong&gt;：&lt;/p&gt;&lt;p&gt;每个用户在Person表里面都会有一个对应的帐户，里面记录了用户的姓名、地址、电话、积分（Point）等基本信息。&lt;/p&gt;&lt;p&gt;在Order表里记录的是每次交易的过程，每次商品的送货费（Freightage）为10元，当商品价格（Price）超过98元可免费送货，当用户Person积分（Point）超过2000分可获7折优惠（Favorable），1000~2000分可获8折，1000分以下可有9折，最后总体价格为为（TotalPrice）。&lt;/p&gt;&lt;p&gt;在最后结单的时候Order表里会产生订单号码OrderNumber和下订日期Delivery，Person表的积分也会加上订单总价的点数。&lt;/p&gt;&lt;p&gt;最后OrderItem表包含了物品Goods、物品价格Price、购买数量Count等属性，它主要记录每次订单的详细交易状况。&lt;/p&gt;&lt;p&gt;上面的业务逻辑跟淘宝、当当等等大型购物网基本相似。之所以用这样一个例子作为参考，是想表现一下DDD是如果利用领域模型去适应多变的业务逻辑关系。&lt;/p&gt;&lt;p id="t3"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;三、&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;把业务关系转化为&lt;/strong&gt;&lt;/span&gt;领域模型&lt;/strong&gt;&lt;/span&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. 概念&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;模型驱动设计设计（MODEL-DRIVEN-DESIGN）是DDD里面的核心，它代表的是各个对象之间的关系，把复杂的逻辑关系转化为模型。&lt;/p&gt;&lt;p&gt;模型主要分为实体（Entity）、值对象（Value Object）与服务（Service）三种。&lt;/p&gt;&lt;p&gt;实体：实体所包含的不单止是一连串的属性，更重要的是与事件的联系，在一个生命周期中环境的变化与事件发生，将引起实体内部产生变化。好像在实体Order里面，Person的积分（Point）和OrderItem的价格（Price）都会直接影响总体价格（TotalPrice）的大小，而总体价格也会影响到运费Freightage的多少等等。在Order实体的一切，都会受到Person、OrderItem等这些外部因数的影响，这样的对象被视为实体。在不同的时刻，实体会有不同的状态，所以在开发过程中我们需要为实体加上一个&amp;ldquo;标识符&amp;rdquo;来区分对象的身份，它是实体的生命周期里的唯一标志。&lt;/p&gt;&lt;p&gt;值对象：当所用到的对象只有属性而没有其他逻辑关系的时候，我们就可以把它视为是值对象。值对象没有状态，也不需要有 &amp;ldquo;标识符&amp;rdquo;。在多数情况下它可以作为一个属性存在于一个实体的内部。一般情况下值对象的属性是不可改变的，当需要更改属性时，可以把整个对象删除，然后重新加入一个新对象。&lt;/p&gt;&lt;p&gt;服务：当实体之间存在某些操作，它们并不单一地附属于某一个实体，而是跟多个实体都有关联的时候，就可以使用服务来封装这些操作。值得注意的是&lt;strong&gt;服务并非单独指Web Service, 也并非单单存在于领域层&lt;/strong&gt;，而是在各个层当中都会存在服务，每一层的服务都有着不同的职能。在基础结构层服务可能是用于构建身份验证、电子邮件、错误处理等等操作；在领域层，服务更多时候是一种操作，它用于协调多个实体之间的关系，处理各类的业务问题;在应用层（特别是在分布式开发系统内），服务多以Web Service、TCP/IP套接字、MSMQ等等方式实现，服务在此处会作为一个与外界通讯的接口;&lt;/p&gt;&lt;ul&gt;&lt;li style="padding-right: 20px;"&gt;备注 ：这里面也存在一定的争义，Eric 认为实体所代表的只是多个对象之间的关系，而它们的动作将会由服务来体现出来，这被称为贫血型模型。但在开发过程中，越来越多人会把动作加入到实体里面，这被称为充血型模型。其实不同的问题应该客观分析，分别对待，在这个例子里面将会以按照 Eric 的定义来开发服务，在后面的开发过程中大家也可以从中体现一下服务层所带来的好处。&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011120618345410.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2. 实例说明&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;先以ADO.NET Entity Framework实现模型，Person、Order分别属于两个实体，它们都将继承Root接口，在它们的生命周期内都会生成一个Guid作为标志。此处把OrderItem作为一个值对象置于Order实体内，这意味着OrderItem会通过Order来获取，外界不能跨越Order直接获取OrderItem。当然这应该由具体的业务情况来确定，当外界需要单独调用OrderItem类的时候，就应该考虑把OrderItem独立成为一个实体类。&lt;/p&gt;&lt;p&gt;在这里可利用分部类为实体增加Guid属性，关于分部类于分部方法的详细介绍可参考&lt;span style="color: #0000ff;"&gt;&lt;a id="ctl02_TitleUrl" href="http://www.cnblogs.com/leslies2/archive/2011/09/09/2172267.html"&gt;&lt;span style="color: #0000ff;"&gt;C#综合揭秘&amp;mdash;&amp;mdash;分部类和分部方法&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.DomainModel&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; Root {&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;partial&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Order:Root&lt;br /&gt;    {  &lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; Guid _guid;        &lt;br /&gt;        &lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Order()&lt;br /&gt;        {&lt;br /&gt;            _guid = System.Guid.NewGuid();&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;为根对象设置唯一的Guid;&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Guid GUID&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt; { &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; _guid; }&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;partial&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Person:Root&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Person()&lt;br /&gt;        {&lt;br /&gt;            _guid = System.Guid.NewGuid();&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;为根对象设置唯一的Guid;&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; Guid _guid;&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Guid GUID&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt; { &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; _guid; }&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;}&lt;/div&gt;&lt;p id="t4"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;&amp;nbsp;四、细说Repository&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1.概念&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Repository是把持久化对象转换成领域模型的一种方式，可用于获取、更新持久对象并管理它们的生命周期。它使应用程序与持久化技术实现解耦，程序无需受制于使用Oracle还是MySql数据库，也不会受到Hibernate、LINQ、ADO.NET等数据层的约束，使开发人员可以把注意力集中到领域模型当中。&lt;/p&gt;&lt;p&gt;Repository与传统三层模式的DAL层有点相似，但Repository针对的是每一个根对象来划分边界的。在这个例子当中，Person与Order都会有对应的PersonRepository、OrderRepository。而OrderItem只是Order的子属性，所以它的插入、更新、删除都会包含在OrderRepository当中。当多个对象之间建立起联系后，关系将是复杂的，特别是在LINQ里面，程序可以轻易通过Person的导航属性里获取OrderItem的值，最后很容易使代码变得混乱。所以确立Repository的边界，可以在有效管理每个Repository的职能。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2.实例说明&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;注意OrderItem的存取、删除都包含在OrderRepository里面。在获取、修改Order的时候，也会利用&amp;ldquo;显式加载&amp;rdquo; context.Order.Include("OrderItem") 的方法,使OrderItem实现同步更新。而通过PersonRepository.GetPerson（int )获取的Person对象，它内部的Order属性将是null值，这必须清晰按照领域模型的边界划分的。&lt;/p&gt;&lt;p&gt;当LINQ面世以后，数据的获取变得简单，特别在一些小型的系统开发时，很多人会不自觉地把这种领域模型的分界规则打破。但随着系统的复杂化，问题就会逐渐呈现。比如当Order对象的属性被更新，使用OrderRepository.Update（Order)更新数据库后，页面的Person对象未能同步实现更新，在Person与数据库交换数据的时候，Order又被变回旧值。&lt;/p&gt;&lt;p&gt;在混乱的数据层开发中，这种情况非常常见，所以在下会坚持Repository的原则，把Repository的职能清晰按照领域模型划分。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.IRepository&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IOrderRepository&lt;br /&gt;    {&lt;br /&gt;        Order GetOrder(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id);&lt;br /&gt;        IList&amp;lt;Order&amp;gt; GetList();&lt;br /&gt;        IList&amp;lt;Order&amp;gt; GetListByPerson(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; personID);&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddOrder(Order order);&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; DeleteOrder(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id);&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; UpdateOrder(Order order);&lt;br /&gt;      &lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddOrderItem(OrderItem orderItem);&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; DeleteOrderItem(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id);&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IPersonRepository&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddPerson(Person person);&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AttachPerson(Person person);&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; UpdatePerson(Person person);&lt;br /&gt;        Person GetPerson(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id);&lt;br /&gt;        IList&amp;lt;Person&amp;gt; GetList();&lt;br /&gt;    }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.Repository&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderRepository:IOrderRepository&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据ID获取单个Order&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Order GetOrder(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id)&lt;br /&gt;        {&lt;br /&gt;            BusinessContext _context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; BusinessContext();&lt;br /&gt;            Order order = &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;;&lt;br /&gt;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;            {&lt;br /&gt;                &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;                { &lt;br /&gt;                    &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;由于OrderItem是Order实体中的一个属性，必须通过OrderRepository同步获取&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                    &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; list = _context.Order.Include(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;OrderItem&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;)&lt;br /&gt;                        .Where(x =&amp;gt; x.ID == id);&lt;br /&gt;                    &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (list.Count() &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;                        order = list.First();&lt;br /&gt;                    &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;                        order = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Order();&lt;br /&gt;                    scope.Complete();&lt;br /&gt;                }&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (Exception ex)&lt;br /&gt;            {&lt;br /&gt;                &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;出错处理，并返回一个空对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                Business.Common.ExceptionManager.DataException.DealWith(ex);&lt;br /&gt;                order = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Order();&lt;br /&gt;            }&lt;br /&gt;            _context.Dispose();&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; order;&lt;br /&gt;        }&lt;br /&gt;        ..................&lt;br /&gt;        ..................&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; PersonRepository:IPersonRepository&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddPerson(Person person)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; LinqHelp.Add&amp;lt;Person&amp;gt;(person);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Person GetPerson(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; LinqHelp.Get&amp;lt;Person&amp;gt;(id);&lt;br /&gt;        }&lt;br /&gt;        .................&lt;br /&gt;        .................&lt;br /&gt;    }&lt;br /&gt;}&lt;/div&gt;&lt;p&gt;在更新Order这种复杂的领域模型时，如果要分辨单个OrderItem属性是新建值还是更新值，然后分别处理，那将是比较麻烦的，而且OrderItem只是一个值对象，ID编码等属性对它没有任何实在意义。所以在更新List&amp;lt;OrderItem&amp;gt;属性时都会先把它全部删除，然后重新加载，在OrderItem数量不多的时候，这是一种十分有效的方法。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.Repository&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderRepository:IOrderRepository&lt;br /&gt;    {&lt;br /&gt;         .................&lt;br /&gt;         .................&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;更新Order，因为难以别哪些是原有的OrderItem,哪些OrderItem是新插入&lt;br /&gt;        &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;使用简单的方法，会先把原有的OrderItem的删除，再重新插入&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; UpdateOrder(Order order)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; returnValue = -&lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;            BusinessContext _context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; BusinessContext();&lt;br /&gt;           &lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;            {&lt;br /&gt;                &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (TransactionScope scope = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; TransactionScope())&lt;br /&gt;                {&lt;br /&gt;                    &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; list = _context.Order.Include(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;OrderItem&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;)&lt;br /&gt;                        .Where(x =&amp;gt; x.ID == order.ID);&lt;br /&gt;                    &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (list.Count() &amp;gt; &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;                    {&lt;br /&gt;                        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;更新Order列&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                        Order _order = list.First();&lt;br /&gt;                        _order.Count = order.Count;&lt;br /&gt;                        _order.Delivery = order.Delivery;&lt;br /&gt;                        _order.Favorable = order.Favorable;&lt;br /&gt;                        _order.Freightage = order.Freightage;&lt;br /&gt;                        _order.OrderNumber = order.OrderNumber;&lt;br /&gt;                        _order.PersonID = order.PersonID;&lt;br /&gt;                        _order.Price = order.Price;&lt;br /&gt;                        _order.TotalPrice = order.TotalPrice;&lt;br /&gt;&lt;br /&gt;                        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;删除原有的订单明细项OrderItem&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                        &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (list.First().OrderItem.Count != &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;                            &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; item &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; list.First().OrderItem)&lt;br /&gt;                                DeleteOrderItem(item.ID);&lt;br /&gt;                        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;加入新的订单明细项OrderItem&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                        &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (order.OrderItem.Count != &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;                        {&lt;br /&gt;                            &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; item &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; order.OrderItem)&lt;br /&gt;                            {&lt;br /&gt;                                &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; _orderItem = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderItem();&lt;br /&gt;                                _orderItem.Count = item.Count;&lt;br /&gt;                                _orderItem.Goods = item.Goods;&lt;br /&gt;                                _orderItem.OrderID = item.OrderID;&lt;br /&gt;                                _orderItem.Price = item.Price;&lt;br /&gt;                                AddOrderItem(_orderItem);&lt;br /&gt;                            }&lt;br /&gt;                        }&lt;br /&gt;                        returnValue = _context.SaveChanges();&lt;br /&gt;                    }&lt;br /&gt;                    &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;                        returnValue = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;;&lt;br /&gt;&lt;br /&gt;                    scope.Complete();&lt;br /&gt;                }&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (Exception ex)&lt;br /&gt;            {&lt;br /&gt;                Business.Common.ExceptionManager.DataException.DealWith(ex);&lt;br /&gt;                returnValue=-&lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;            }&lt;br /&gt;&lt;br /&gt;            _context.Dispose();&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; returnValue;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;插入OrderItem&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddOrderItem(OrderItem orderItem)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; LinqHelp.Add&amp;lt;OrderItem&amp;gt;(orderItem);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;删除OrderItem&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; DeleteOrderItem(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; id)&lt;br /&gt;        {&lt;br /&gt;            EntityKey key = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; EntityKey(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BusinessContext.OrderItem&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;ID&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, id);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; LinqHelp.Delete(key);&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;}&lt;/div&gt;&lt;p id="t5"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;五、领域层的服务&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. 例子说明&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在第二节已基本介绍过服务的作用了，领域层服务的作用主要是为了解决业务上的逻辑问题，更多的时候，服务是一个与业务相关的动作。比如在上述例子中：&lt;/p&gt;&lt;p&gt;在Order表里记录的是每次交易的过程，每次商品的送货费（Freightage）为10元，当商品价格（Price）超过98元可免费送货，当用户 Person积分（Point）超过2000分可获7折优惠（Favorable），1000~2000分可获8折，1000分以下可有9折，最后总体价 格为为（TotalPrice）。&lt;/p&gt;&lt;p&gt;这复杂的业务逻辑，完全可以由一个领域服务类AccountManager来完成&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.Service.DomainService&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; AccountManager&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; Person _person;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; Order _order;&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; AccountManager(Person person, Order order)&lt;br /&gt;        {&lt;br /&gt;            _person = person;&lt;br /&gt;            _order = order;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #808080;"&gt;///&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算总体收费 &lt;/span&gt;&lt;span style="color: #808080;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Account()&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算商品数量&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            GoodsCount();&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算商品价格&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            PriceAccount();&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算优惠等级&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            FavorableAccount();&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; price1 = (_order.Price - _order.Favorable).Value;&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算运费&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            FreightageAccount(price1);&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算总体价费&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            _order.TotalPrice = price1 + _order.Freightage.Value;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算商品数量&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; GoodsCount()&lt;br /&gt;        {&lt;br /&gt;            _order.Count=&lt;span style="color: #800080;"&gt;0&lt;/span&gt;;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; OrderItem &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; _order.OrderItem)&lt;br /&gt;                _order.Count += OrderItem.Count;&lt;br /&gt;        }&lt;br /&gt; &lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;商品总体价格&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; PriceAccount()&lt;br /&gt;        {&lt;br /&gt;            _order.Price = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; OrderItem &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; _order.OrderItem)&lt;br /&gt;                _order.Price += OrderItem.Price * OrderItem.Count;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;优惠分为三等，积分小于1000有9折，小于2000分为8折，大于2000为7折&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; FavorableAccount()&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; point = (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;)_person.Point.GetInt();&lt;br /&gt;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (point &amp;lt; &lt;span style="color: #800080;"&gt;1000&lt;/span&gt;)&lt;br /&gt;                _order.Favorable = _order.Price * &lt;span style="color: #800080;"&gt;0.1&lt;/span&gt;;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (point &amp;gt;= &lt;span style="color: #800080;"&gt;1000&lt;/span&gt; &amp;amp;&amp;amp; point &amp;lt; &lt;span style="color: #800080;"&gt;2000&lt;/span&gt;)&lt;br /&gt;                _order.Favorable = _order.Price * &lt;span style="color: #800080;"&gt;0.2&lt;/span&gt;;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (point &amp;gt; &lt;span style="color: #800080;"&gt;2000&lt;/span&gt;)&lt;br /&gt;                _order.Favorable = _order.Price * &lt;span style="color: #800080;"&gt;0.3&lt;/span&gt;;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;如果价格在98元以上，可免运费。其余运费为10元&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; FreightageAccount(&lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; price)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (price &amp;gt;= &lt;span style="color: #800080;"&gt;98&lt;/span&gt;)&lt;br /&gt;                _order.Freightage = &lt;span style="color: #800080;"&gt;0&lt;/span&gt;;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;                _order.Freightage = &lt;span style="color: #800080;"&gt;10&lt;/span&gt;;&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;}&lt;/div&gt;&lt;p&gt;你可能会说，在这个业务流程中，除了积分优惠Person.Point以外，其他的业务都只与Order的属性有关，按照充血型模型的方案，完全可以把这些业务放到Order的方法当中，而把积分优惠独立成为一个服务。但在下在很多的开发过程中发现，为模型附上动作会带来一连串的问题，好像你不知道哪些操作应该在模型动作上实现，哪里应该在服务中实现......。对于这些无休止的争论不会因为这里的一个小例子而停止，但在这里我会坚持使用贫血型模型,利用服务来完成所有的动作。&lt;/p&gt;&lt;p&gt;再举一个例子：在最后结单的时候Order表里会产生订单号码OrderNumber和下订日期Delivery，Person表的积分也会加上订单总价的点数。对应这个操作，也可以单独开发一个PaymentManager服务类进行管理。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.Service.DomainService&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; PaymentManager&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;下单结算&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Payment(Order order,Person person)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;确定下单，建立订单号&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            order.OrderNumber = Guid.NewGuid().ToString();&lt;br /&gt;            order.Delivery = DateTime.Now;&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;增加积分&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (person.Point.HasValue)&lt;br /&gt;                person.Point += (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;)order.TotalPrice.GetValueOrDefault();&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;                person.Point = (&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt;)order.TotalPrice.GetValueOrDefault();&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;}&lt;/div&gt;&lt;p&gt;利用领域层的服务，使得每个Manager服务类的职能非常明确，业务管理起来也十分地方便，领域层可以随着业务的改变而灵活变动。而且领域层具有 &amp;ldquo;高内聚，低耦合&amp;rdquo; 特性，它并不依赖其它任何一层，而只是把业务逻辑包含在里面。&lt;/p&gt;&lt;p id="t6"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;六、工厂模式Factory&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;Factory是常用到软件开发模式，在网上像简单工厂、工厂方法、抽象工厂等开发模式的资料都到处可寻，可这并不是领域驱动设计的主题。在这一节里，我主要想介绍Factory的适用时机。&lt;/p&gt;&lt;p&gt;并非生成所有对象的时候，都需要用到工厂模式。在生成简单对象的时候，可以直接利用构造函数来代替工厂，也可以添加工厂方法来生成对象。但如果在生成对象时，内部属性之间存在一系统复杂的业务规则的时候，就可以把生成方法独立到一个Factory类里面。这时候客户端无需理会潜在逻辑关系，而直接通过这个Factory来生成相应的对象。&lt;/p&gt;&lt;p&gt;举个例子，在新建Order的时候，业务上规定运费是总体金额的1%，折扣规定是7.5折...... 。如果由客户端新建一个对象Order，然后为这些属性负值，那相关的业务逻辑就会暴露在外。这时候就可以使用Factory模式，把属性之间的关系封装到Factory之内，客户端通过Factory就能轻松地生成Order对象而无需要理会复杂的内部关系。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="border: 1px ridge #808080; display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011121010384258.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;至于较复杂的Factory模式，在此不多作介绍，各位可以在网上查找相关资料。&lt;/p&gt;&lt;p id="t7"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;七、细说应用层&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. SOA系统中应用层的特点&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在开发SOA分布式系统的时候，应用层是一个重点，它主要有两个作用。&lt;/p&gt;&lt;p&gt;第一，应用层主要作用是协调领域层工作，指挥领域对象解决业务问题，但应用层本身不会牵扯到业务状态。&lt;/p&gt;&lt;p&gt;第二，在SOA系统当中应用层是数据运输中心和信息发放的端口，担负着数据转换与数据收发的责任。&lt;/p&gt;&lt;p&gt;它有以下的特点：&lt;/p&gt;&lt;ul&gt;&lt;li&gt;粗粒度&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;分布式系统与普通网站和应用程序不同，因为它假定外界对系统内部是毫无了解的，用户只想输入相关数据，最后得到一系列计算结果。所以我们应该把计算结果封装在一个数据传输对象（DTO）内，实现粗粒度的传递&lt;strong&gt;，这是一般项目与SOA系统在服务层的一个最明显的差别&lt;/strong&gt;。 想想如果一个页面需要同时显示一个顾客的个人资料、某张订单的详细资料，那将要同时获取Person、Order、OrderItem三张表的信息。在普通系统的开发过程中，这并不会造成太大问题，但在使用远程服务的时候，如果用三个方法分别获取，那将会造成不少的性能损耗。特别是在分布式开发系统中，应用层与表现层之间是实现分离的，更多时候两者是由不同部门所开发的模块，表现层不会了解应用层中的逻辑关系，Person，Order，OrderItem三样东西在表现层看来，也就是同一样东西，那就是返回值。所以在系统内，应该把多张表的信息封装在一个DTO对象内，通过应用层一个远程方法一次性返还。&lt;strong&gt;使用粗粒度的数据元素是分布式系统的一个特点&lt;/strong&gt;。&lt;/p&gt;&lt;ul&gt;&lt;li&gt;传输性&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;如果你熟悉SOA系统，对DTO（Data Transfer Object 数据传输对象）这个词一定并不陌生。DTO属于一个数据传输的载体，内部并不存在任何业务逻辑，通过DTO可以把内部的领域对象与外界隔离。DTO所封装的是客户端的数据，所以它的设计更多地是针对客户端的需求，而不是业务逻辑。比如说本来Person与Order是一对多的关系，但当一个页面只要显示的是一个客户的单张订单信息，那我们就可以根据需要把DTO中的Person和Order设计为一对一的关系。如果你是使用MVC开发一般的网站，更多时候会把返回对象直接转化为Model。如果你开发是一个分布式系统，那更多时候会从系统性能与隐藏业务逻辑出发着想。而且考虑到把内部对象转化为DTO，将是一件麻烦的事，建议应该考虑DTO的兼容性，使DTO可以作为多个方法的返还载体。（注意：在SOA系统内，应该从性能出发优先考虑粗粒度元素的传输性问题）&lt;/p&gt;&lt;ul&gt;&lt;li&gt;封装性&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;在SOA系统当中应用层服务的发布并不需要复杂的模型，只需使用外观模式（Facade）把一些功能封装在少数的几个服务类里面，使用Web Service、TCP/IP套接字、MSMQ等服务方式向外界发布。&lt;/p&gt;&lt;p&gt;说到这里，我真的十分感激Martin先生带给我的帮助，在开发过程中，这些复杂的问题带给我不少的困扰，Martin先生一纸富有经验的独特见解，真的带给在下很大的启发。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2. 应用层的协调性 &lt;/strong&gt;&lt;/p&gt;&lt;p&gt;应用层服务会利用Repository，完成实体基本的插入、更新、获取等等操作，并调用领域层的服务管理的业务逻辑。注意观察，一切的业务逻辑都只会隐藏于领域层，应用层服务只起着协调作用，本身不应该包含有任何业务逻辑。&lt;/p&gt;&lt;p&gt;可以看到OrderService就是通过调用AccountManager、PaymentManager等领域层服务来完成结账、付款等一系列复杂业务逻辑的。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.Service.ApplicationService&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; PersonService&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; IPersonRepository personRepository = DataAccess.CreatePersonRepository();&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddPerson(Person person)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personRepository.AddPerson(person);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; UpdatePerson(Person person)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personRepository.UpdatePerson(person);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Person GetPerson(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; personID)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personRepository.GetPerson(personID);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; IList&amp;lt;Person&amp;gt; GetList()&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; personRepository.GetList();&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt; &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderService&lt;br /&gt; {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; IOrderRepository orderRepository = DataAccess.CreateOrderRepository();&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddOrder(Order order)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;计算Order总体费用&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            Account(order);&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;加入修改后的Order&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderRepository.AddOrder(order);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;调用领域层服务AccountManager，计算Order总体费用&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Account(Order order)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取对应Person对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            IPersonRepository personRepository = DataAccess.CreatePersonRepository();&lt;br /&gt;            Person person = personRepository.GetPerson(order.PersonID);&lt;br /&gt;&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;调用服务层的AccountManager对象，计算费用，修改Order&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            AccountManager accountManager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; AccountManager(person, order);&lt;br /&gt;            accountManager.Account();    &lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//调用领域层服务PaymentManager，&lt;/span&gt;&lt;span style="color: #008000;"&gt;确认订单&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Order Payment(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; orderID)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; order=orderRepository.GetOrder(orderID);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (order != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;            {&lt;br /&gt;                PersonRepository personRepository = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; PersonRepository();&lt;br /&gt;                &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; person=personRepository.GetPerson(order.PersonID);&lt;br /&gt;&lt;br /&gt;                PaymentManager paymentManager = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; PaymentManager();&lt;br /&gt;                paymentManager.Payment(order, person);&lt;br /&gt;&lt;br /&gt;                orderRepository.UpdateOrder(order);&lt;br /&gt;                personRepository.UpdatePerson(person);&lt;br /&gt;&lt;br /&gt;                &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; order;&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;                &lt;span style="color: #0000ff;"&gt;throw&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Exception(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Can not find order!&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; DeleteOrder(Order order)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderRepository.DeleteOrder(order.ID);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; Order GetOrder(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; orderID)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderRepository.GetOrder(orderID);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; IList&amp;lt;Order&amp;gt; GetList()&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderRepository.GetList();&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; IList&amp;lt;Order&amp;gt; GetListByPerson(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; personID)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderRepository.GetListByPerson(personID);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; UpdateOrder(Order order)&lt;br /&gt;        {&lt;br /&gt;            Account(order);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderRepository.UpdateOrder(order);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddOrderItem(OrderItem orderItem)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; index = orderRepository.AddOrderItem(orderItem);&lt;br /&gt;            Order order = orderRepository.GetOrder(orderItem.OrderID);&lt;br /&gt;            UpdateOrder(order);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; index;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; DeleteOrderItem(OrderItem orderItem)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; index = orderRepository.DeleteOrderItem(orderItem.ID);&lt;br /&gt;            Order order = orderRepository.GetOrder(orderItem.OrderID);&lt;br /&gt;            UpdateOrder(order);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; index;&lt;br /&gt;        }&lt;br /&gt;        .......................&lt;br /&gt;        .......................&lt;br /&gt;    }&lt;br /&gt;}&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3. 数据转换过程&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;前面已经解释了DTO的作用，但实现领域对象与DTO之间的转换是一件复杂的事件，因此可以建立一个数据转换器实现此功能。&lt;/p&gt;&lt;p&gt;在平常的工作里，不太多会把&amp;ldquo;订单管理系统&amp;rdquo;做成SOA的模式，因为在分布式系统中，数据的格式与定义大多数由部门之间协定，其中包含明确的规则。但由于条件的局限，在这里还是想以订单管理为例子，希望可以带给你一定的帮助。例子如下：在购物车结账，页面会包含用户基本信息，当前订单信息，订单明细信息等多个部分。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011120917082012.jpg" alt="" width="762" height="478" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;要完成数据转换，首先可以根据页面建立DTO对象，在分布式系统中，通常会把DTO对象放在一个独立的命名空间里，在这个实例里面称之为Business.TransferObject。DTO对象更多时候是面向表现层的需求而建立，这里由于表现层页面所需要的只是单个用户，单张订单的数据，所以在OrderDTO对象里会包含了用户信息和订单资料，也存在订单详细列List&amp;lt;OrderItemDTO&amp;gt;。当然，DTO的设计可以随着需求而修改。&lt;/p&gt;&lt;p&gt;在SOA系统里，DTO是远程服务数据的载体，所以会把DTO附上可序列化特性，这此例子中会使用WCF的数据契约实现OrderDTO和OrderItemDTO。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="border: 1px ridge #808080; display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011120917570171.jpg" alt="" width="711" height="402" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;如图，要实现数据转换，就应该建立数据转换器。在这里OperationAssembler就是一个数据转换器，它是数据转换的核心，它是领域对象与DTO之间实现转换的工具。要在多个对象之间实现数据转换实在是一件非常麻烦的事，所以我一直提倡注意DTO对象的兼容性，使单个DTO对象可以适用于多个外观层，以减少数据转换所带来的麻烦。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.Service.ApplicationService&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OperationAssembler&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把领域对象转换成DTO&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; OrderDTO GetOrderDTO(Order order,Person person)&lt;br /&gt;        {&lt;br /&gt;            OrderDTO orderDTO = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderDTO();&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (person != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;            {&lt;br /&gt;                orderDTO.EMail = person.EMail.GetString();&lt;br /&gt;                orderDTO.Address = person.Address.GetString();&lt;br /&gt;                orderDTO.Name = person.Name.GetString();&lt;br /&gt;                orderDTO.PersonID = person.ID;&lt;br /&gt;                orderDTO.Point = person.Point.GetInt();&lt;br /&gt;                orderDTO.Telephone = person.Telephone.GetString();&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (order != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;            {&lt;br /&gt;                orderDTO.PersonID = order.PersonID;&lt;br /&gt;                orderDTO.Count = order.Count.GetInt();&lt;br /&gt;                orderDTO.Delivery = order.Delivery.GetDateTime();&lt;br /&gt;                orderDTO.Favorable = order.Favorable.GetDouble();&lt;br /&gt;                orderDTO.Freightage = order.Freightage.GetDouble();&lt;br /&gt;                orderDTO.OrderID = order.ID;&lt;br /&gt;                orderDTO.OrderNumber = order.OrderNumber.GetString();&lt;br /&gt;                orderDTO.Price = order.Price.GetDouble();&lt;br /&gt;                orderDTO.TotalPrice = order.TotalPrice.GetDouble();&lt;br /&gt;                &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; orderItemList = order.OrderItem.ToList();&lt;br /&gt;                &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (orderItemList.Count != &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;                {&lt;br /&gt;                    &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; orderItemDTO = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;OrderItemDTO&amp;gt;();&lt;br /&gt;                    &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; orderItem &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; orderItemList)&lt;br /&gt;                        orderItemDTO.Add(GetOrderItemDTO(orderItem));&lt;br /&gt;                    orderDTO.OrderItemList = orderItemDTO;&lt;br /&gt;                }&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderDTO;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; OrderItemDTO GetOrderItemDTO(OrderItem orderItem)&lt;br /&gt;        {&lt;br /&gt;            OrderItemDTO orderItemDTO = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderItemDTO();&lt;br /&gt;            orderItemDTO.Count = orderItem.Count.GetInt();&lt;br /&gt;            orderItemDTO.Goods = orderItem.Goods.GetString();&lt;br /&gt;            orderItemDTO.OrderID = orderItem.OrderID;&lt;br /&gt;            orderItemDTO.OrderItemID = orderItem.ID;&lt;br /&gt;            orderItemDTO.Price = orderItem.Price.GetDouble();&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderItemDTO;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把DTO转换成多个对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; SetOrder(OrderDTO orderDTO, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; Person person, &lt;span style="color: #0000ff;"&gt;out&lt;/span&gt; Order order)&lt;br /&gt;        {&lt;br /&gt;            person = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Person();&lt;br /&gt;            person.EntityKey=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; System.Data.EntityKey(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BusinessContext.Person&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;ID&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,orderDTO.PersonID);&lt;br /&gt;            person.Address = orderDTO.Address;&lt;br /&gt;            person.EMail = orderDTO.EMail;&lt;br /&gt;            person.ID = orderDTO.PersonID;&lt;br /&gt;            person.Name = orderDTO.Name;&lt;br /&gt;            person.Point = orderDTO.Point;&lt;br /&gt;            person.Telephone = orderDTO.Telephone;&lt;br /&gt;&lt;br /&gt;            order = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; Order();&lt;br /&gt;            order.EntityKey=&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; System.Data.EntityKey(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BusinessContext.Order&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;ID&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;,orderDTO.OrderID);&lt;br /&gt;            order.Count = orderDTO.Count;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (orderDTO.Delivery.Year!=&lt;span style="color: #800080;"&gt;0001&lt;/span&gt;&amp;amp;&amp;amp;orderDTO.Delivery.Year!=&lt;span style="color: #800080;"&gt;9999&lt;/span&gt;)&lt;br /&gt;                order.Delivery = orderDTO.Delivery;&lt;br /&gt;            order.Favorable = orderDTO.Favorable;&lt;br /&gt;            order.Freightage = orderDTO.Freightage;&lt;br /&gt;            order.ID = orderDTO.OrderID;&lt;br /&gt;            order.OrderNumber = orderDTO.OrderNumber;&lt;br /&gt;            order.PersonID = orderDTO.PersonID;&lt;br /&gt;            order.Price = orderDTO.Price;&lt;br /&gt;            order.TotalPrice = orderDTO.TotalPrice;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; orderItemDTOList = orderDTO.OrderItemList;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (orderItemDTOList.Count() != &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;                &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; orderItemDTO &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; orderItemDTOList)&lt;br /&gt;                    order.OrderItem.Add(GetOrderItem(orderItemDTO));&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; OrderItem GetOrderItem(OrderItemDTO orderItemDTO)&lt;br /&gt;        {&lt;br /&gt;            OrderItem orderItem = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderItem();&lt;br /&gt;            orderItem.EntityKey = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; System.Data.EntityKey(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;BusinessContext.OrderItem&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;ID&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;, orderItemDTO.OrderItemID);&lt;br /&gt;            orderItem.Count = orderItemDTO.Count;&lt;br /&gt;            orderItem.Goods = orderItemDTO.Goods;&lt;br /&gt;            orderItem.ID = orderItemDTO.OrderItemID;&lt;br /&gt;            orderItem.OrderID = orderItemDTO.OrderID;&lt;br /&gt;            orderItem.Price = orderItemDTO.Price;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderItem;&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;数据传输对象 DTO&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.TransferObject&lt;br /&gt;{&lt;br /&gt;    [DataContract]&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderItemDTO&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; _orderItemID;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; _orderID;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; _goods;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; _price;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; _count;&lt;br /&gt;&lt;br /&gt;        [DataMember]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; OrderItemID&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt; { &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; _orderItemID; }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt; { _orderItemID = value; }&lt;br /&gt;        }&lt;br /&gt;        ............&lt;br /&gt;        ............&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    [DataContract]&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderDTO&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; _personID;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; _name;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; _address;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; _telephone;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; _point;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; _email;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; _orderID;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; _orderNumber;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; _count;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; _freightage;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; _favorable;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; DateTime _delivery;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; _price;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;double&lt;/span&gt; _totalPrice;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; IList&amp;lt;OrderItemDTO&amp;gt; _orderItemDTOList;&lt;br /&gt;&lt;br /&gt;        [DataMember]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; PersonID&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;get&lt;/span&gt;{&lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;this&lt;/span&gt;._personID;}&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;set&lt;/span&gt;{&lt;span style="color: #0000ff;"&gt;this&lt;/span&gt;._personID=value;}&lt;br /&gt;        }&lt;br /&gt;        ..........&lt;br /&gt;        ..........&lt;br /&gt;    }&lt;br /&gt;}&lt;/div&gt;&lt;p&gt;通过数据转换器，可以顺利实现领域模型与DTO之间的转换，协调应用层服务的运行。&lt;/p&gt;&lt;p&gt;&lt;img style="border: 1px ridge #808080; display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011120921320582.jpg" alt="" width="393" height="320" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4. 应用层的发布&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;在开发SOA系统的时候，应用层的服务需要使用远程方法对外开放，在接收到请求的时候，它可以调用领域层服务获取运算结果，然后通过数据转换器OperationAssembler把运算结果转换成DTO，最后返还到表现层。在起初，我曾尝试对应每个应用层的对象建立一个远程接口，但经过多次重构以后，我觉得行程对象就是一个简单的对外接口，对象之间不存在什么逻辑关系。所以更简单的方法是使用外观模式，建立少数的几个远程服务类，把所有的应用层对象的方法都包含在内。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="border: 1px ridge #808080; display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011121322383069.jpg" alt="" width="516" height="345" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;可以留意代码，OperationService包括了对Person模型和Order模型的所有操作。而且每个操作都只是简单地调用应用层服务 (ApplicationService) 获得计算结果，然后使用数据转换器 （OperationAssembler）转换数据，当中并不存在任何的业务逻辑。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #0000ff;"&gt;namespace&lt;/span&gt; Business.Service.ApplicationService&lt;br /&gt;{&lt;br /&gt;    [ServiceContract]&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;interface&lt;/span&gt; IOperationService&lt;br /&gt;    {&lt;br /&gt;        [OperationContract]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddOrder(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; OrderDTO orderDTO);&lt;br /&gt;&lt;br /&gt;        [OperationContract]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; DeleteOrder(OrderDTO orderDTO);&lt;br /&gt;&lt;br /&gt;        [OperationContract]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; UpdateOrder(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; OrderDTO orderDTO);&lt;br /&gt;&lt;br /&gt;        [OperationContract]&lt;br /&gt;        IList&amp;lt;OrderDTO&amp;gt; GetOrderByPerson(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; personID);&lt;br /&gt;&lt;br /&gt;        [OperationContract]&lt;br /&gt;        OrderDTO GetOrder(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; orderID);&lt;br /&gt;&lt;br /&gt;        [OperationContract]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddPerson(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; OrderDTO orderDTO);&lt;br /&gt;&lt;br /&gt;        [OperationContract]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; UpdatePerson(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; OrderDTO orderDTO);&lt;br /&gt;&lt;br /&gt;        [OperationContract]&lt;br /&gt;        OrderDTO GetPerson(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; personID);&lt;br /&gt;&lt;br /&gt;        [OperationContract]&lt;br /&gt;        IList&amp;lt;OrderDTO&amp;gt; GetPersonList();&lt;br /&gt;&lt;br /&gt;        [OperationContract]&lt;br /&gt;        OrderDTO Payment(&lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; orderID);&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OperationService:IOperationService&lt;br /&gt;    {&lt;br /&gt;        [OperationBehavior(TransactionScopeRequired = &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;, TransactionAutoComplete = &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;)]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddOrder(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; OrderDTO orderDTO)&lt;br /&gt;        {&lt;br /&gt;            OrderService orderService = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderService();&lt;br /&gt;            Order order = GetOrder(orderDTO);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = orderService.AddOrder(order);&lt;br /&gt;            orderDTO = OperationAssembler.GetOrderDTO(order, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; n;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        [OperationBehavior(TransactionScopeRequired = &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;, TransactionAutoComplete = &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;)]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; DeleteOrder(OrderDTO orderDTO)&lt;br /&gt;        {&lt;br /&gt;            OrderService orderService = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderService();&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; orderService.DeleteOrder(GetOrder(orderDTO));&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        [OperationBehavior(TransactionScopeRequired = &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;, TransactionAutoComplete = &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;)]&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; UpdateOrder(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; OrderDTO orderDTO)&lt;br /&gt;        {&lt;br /&gt;            OrderService orderService = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderService();&lt;br /&gt;            Order order = GetOrder(orderDTO);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = orderService.UpdateOrder(order);&lt;br /&gt;            orderDTO = OperationAssembler.GetOrderDTO(order, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; n;&lt;br /&gt;        }&lt;br /&gt;        ..............&lt;br /&gt;        ..............&lt;br /&gt;    }&lt;br /&gt;}&lt;/div&gt;&lt;p id="t8"&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;八、系统总体架构&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. 体现领域驱动设计的架构&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;到此总结一下领域驱动设计DDD的总体结构，Repository层使用ORM映射或SQL命令等方式把持久化数据转化为领域对象，然后根据业务逻辑设计对应领域层服务Domain Service 。接着应用层进行操作上的协调，利用Repository、领域模型、领域层服务Domain Service 完成业务需要，再通过数据转换器把领域对象Domain Object转化为数据传输对象DTO。最后，利用远程通讯技术把应用层的服务（Application Service）对外开放。&lt;/p&gt;&lt;p&gt;注意留意的是SOA系统中，UI表现层与Application Service应用层服务是实现分离的，表现层可以同时调用多方的远程服务来完成工作。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="border: 1px ridge #808080; display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011122013203997.jpg" alt="" width="613" height="560" /&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2. 体现面向服务开发的架构&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;面向服务开发SOA的架构主要体现在表现层与应用层之间通过远程通讯实现分离，表现层可以引用多方的应用服务作为基础。由此系统实现业务上的分离，不同的功能模块可以独立开发，最后通过服务在表现层共同体现。长期的发展，使不少的企业针对单个功能模块开发出一套独立的系统，再通过强大的虚拟化技术为第三方提供服务，这就是云计算的前身。&lt;/p&gt;&lt;p&gt;就像一个通讯购物的平台，其实就是综合了内部业务管理、银行转帐服务、呼叫中心、第三方接口等多方服务的综合性平台。如果你有过这方面的经验，就会知道其实银行转帐、呼叫中心不过就是银行、电信、移动等公司提供的几个简单的接口。开发人员根本无需理会其实内部的结构，只要通过几个简单的远程方法就能调用。这正是应用层服务 Application Service 的最好体现。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;img style="display: block; border: 1px ridge #808080; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011121111364321.jpg" alt="" width="677" height="259" /&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3. 结束语&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;写这篇文章目的只是想与各位分享一下我在开发过程中的一些体会，欢迎各位点评，指出其中的不足。&lt;/p&gt;&lt;p&gt;其实架构是死物，人才是有脑子的生物。每一个架构必然会有其优点，也会有不足之处，我们应该从开发之中一齐起来体验，而不是盲目地跟从，希望在下的拙见能够给大家带来帮助。可别忘了支持一下，挺一挺。&lt;/p&gt;&lt;p&gt;对软件架构开发有兴趣的朋友欢迎加入博客园讨论组&lt;span style="color: #0000ff;"&gt;&lt;a href="http://home.cnblogs.com/group/102576/" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt; &amp;ldquo;.NET高级编程&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://files.cnblogs.com/leslies2/Business.rar"&gt;&lt;span style="color: #0000ff;"&gt;源代码下载&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/strong&gt; （数据库可以在.edmx文件根据模型生成）&lt;/p&gt;&lt;p&gt;&lt;a href="#t0"&gt;&lt;span style="font-size: 12px; color: #0000ff;"&gt;回到目录&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 14pt; color: #ff0000;"&gt;&lt;strong&gt;相关文章&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2011/01/26/1934162.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;SOA的概念&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2011/03/29/1997889.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;SOA基本架构&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="#"&gt;&lt;span style="color: #0000ff;"&gt;结合领域驱动设计的SOA分布式软件架构&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;div style="float: right; text-align: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;br /&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2011/12/12/2272722.html"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2011/12/12/2272722.html&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;a title="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html" href="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html"&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2272722.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2011/12/12/2272722.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html</id><title type="text">.NET基础篇——利用泛型与反射更新实体（ADO.NET Entity Framework）</title><summary type="text">自从ADO.NET Entity Framework面世以来，受到大家的热捧，它封装了大量代码生成的工具，用户只需要建立好实体之间的关系，系统就是会为用户自动成功了Add、Delete、CreateObject、Attach、ToList......等等方法，这些方法基本上已经包含获取、删除、插入等基本方法，使用起来非常方便。只是在实体的更新上，由于LINQ面向的是泛型对象T，所以每个对象的更新方法都要由用户自动编辑。有见及此，下面在下利用反射方法，创建了一个更新工具，此工具可以更新ObjectContext里面的任意一个实体或者多个关联实体。</summary><published>2011-11-24T07:15:00Z</published><updated>2011-11-24T07:15:00Z</updated><author><name>风尘浪子</name><uri>http://www.cnblogs.com/leslies2/</uri></author><link rel="alternate" href="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html"/><content type="html">&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;自从ADO.NET Entity Framework面世以来，受到大家的热捧，它封装了大量代码生成的工具，用户只需要建立好实体之间的关系，系统就是会为用户自动成功了Add、Delete、CreateObject、Attach、ToList......等等方法，这些方法基本上已经包含获取、删除、插入等基本方法，使用起来非常方便。只是在实体的更新上，由于LINQ面向的是泛型对象T，所以每个对象的更新方法都要由用户自动编辑。有见及此，下面在下利用反射方法，创建了一个更新工具，此工具可以更新ObjectContext里面的任意一个实体或者多个关联实体。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="color: #000000; font-size: 16px;"&gt;&amp;nbsp;&lt;strong&gt;一、简单介绍反射&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;反射是一个程序集发现及运行的过程，通过反射可以得到*.exe或*.dll等程序 集内部的信息。使用反射可以看到一个程序集内部的接口、类、方法、字段、属性、特性等等信息。在System.Reflection命名空间内包含多个反 射常用的类，下面表格列出了常用的几个类。（详细的资料请参考&amp;ldquo;&lt;span style="color: #3366ff;"&gt;&lt;strong&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2011/11/22/2257703.html" target="_blank"&gt;&lt;span style="color: #3366ff;"&gt;反射的奥妙&lt;/span&gt;&lt;/a&gt;&lt;/strong&gt;&lt;/span&gt;&amp;rdquo;）&lt;/p&gt;&lt;table style="width: 721px; height: 238px;" border="1" cellpadding="1"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;&lt;span style="font-size: 14px;"&gt;类型&lt;/span&gt;&lt;/strong&gt;&lt;/td&gt;&lt;td style="text-align: center;"&gt;&lt;strong&gt;&lt;span style="font-size: 14px;"&gt;作用&lt;/span&gt;&lt;/strong&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;Assembly&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;通过此类可以加载操纵一个程序集，并获取程序集内部信息&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;EventInfo&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;该类保存给定的事件信息&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;FieldInfo&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;该类保存给定的字段信息&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;MethodInfo&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;该类保存给定的方法信息&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;MemberInfo&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;该类是一个基类，它定义了EventInfo、FieldInfo、MethodInfo、PropertyInfo的多个公用行为&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;Module&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;该类可以使你能访问多个程序集中的给定模块&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;ParameterInfo&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;该类保存给定的参数信息&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;PropertyInfo&lt;/span&gt;&lt;/td&gt;&lt;td&gt;&lt;span style="font-size: 14px;"&gt;该类保存给定的属性信息&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="font-size: 16px;"&gt;二 、实体与上下文的关系&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;每个实体值都会包含在上下文中， 当您从客户端回收到实体时, 可以比较与上下文中的该实体的版本更新的实体，并应用适当的更改。值得注意的是，上下文会必须KEY找到实体对像，然后对每一个属性逐个赋值。如果想对实体对象直接赋值，那么KEY那将会改变，系统将无法从上下文中找到该对象。&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;三、开发实例&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;在为一个项目建立关系图时，都会为多个实体建立关系，在更新实体时往往需要把导航属性一同更新，这使得更新方法更为繁琐。比如在觉见的订单管理项目中，在更新订单Order的同时，必须把订单对应的OrderItem对象实现同步更新。为了简化代码，在下利用反射原理建立一个了特定类UpdateHelp，利用这个类可以更新ObjectContext里面的多个关系对象。&lt;/p&gt;&lt;p&gt;&lt;img style="display: block; margin-left: auto; margin-right: auto;" src="http://pic002.cnblogs.com/images/2011/64989/2011112413071959.jpg" alt="" /&gt;&lt;/p&gt;&lt;p&gt;其原理在于系统使用GetIntrinsicObj（EntityObject）方法，根据输入实体（obj）的KEY在上下文中获取对应的实体对象（intrinsic），然后使用UpdateIntrinsticObj（Object）方法，利用PropertyInfo遍历实体的每个属性，把输入的实体对象（obj）的每个属性都赋值给上下文的实体对象（intrinsic）。最特别的地方在于当遇到导航属性的时候，使用了递归算法，重复调用UpdateIntrinsticObj（object）方法为导航属性赋值。当遇到一对多或者多对多关系的时候，导航属性将会是是一个List&amp;lt;T&amp;gt;对象,方法中CloneNavigationProperty是为单个对象赋值，而CloneNavigationPropertyEntityCollection方法是为多个对象赋值。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;&lt;span style="color: #0000ff;"&gt;     public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; UpdateHelp:IDisposable&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;记录已经复制过的实体类，避免重复加载&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; IList&amp;lt;Type&amp;gt; listType = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; List&amp;lt;Type&amp;gt;();&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; BusinessContext _context;&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; UpdateHelp(BusinessContext context)&lt;br /&gt;        {&lt;br /&gt;            _context = context;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Dispose()&lt;br /&gt;        {&lt;br /&gt;            _context.Dispose();&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;更新普通属性&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; CloneProperty(PropertyInfo propertyInfo,&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; intrinsicObj,&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; newObj)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; data = propertyInfo.GetValue(newObj, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;            propertyInfo.SetValue(intrinsicObj, data, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;更新普通导航属性&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; CloneNavigationProperty(PropertyInfo propertyInfo,&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; intrinsicObj,&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; newObj)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; data = propertyInfo.GetValue(newObj, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; dataClone = UpdateIntrinsticObj(data);&lt;br /&gt;            propertyInfo.SetValue(intrinsicObj, dataClone, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;更新返回值为集合EntityCollection&amp;lt;TEntity&amp;gt;的导航属性&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; CloneNavigationPropertyEntityCollection(PropertyInfo propertyInfo, &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; intrinsicObj, &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; newObj)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取参数newObj中的对象集合&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            IEnumerable&amp;lt;&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt;&amp;gt; newData = propertyInfo.GetValue(newObj, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;) &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt; IEnumerable&amp;lt;&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt;&amp;gt;;&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取上下文中匹配的原对象集合&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; intrinsicData = propertyInfo.GetValue(intrinsicObj, &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;);&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;利用EntityCollection&amp;lt;TEntity&amp;gt;类的扩展方法Add在原集合中加入新对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; addMethod = intrinsicData.GetType().GetMethod(&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Add&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (&lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; obj &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; newData)&lt;br /&gt;            {&lt;br /&gt;                Object objClone = UpdateIntrinsticObj(obj);&lt;br /&gt;                addMethod.Invoke(intrinsicData, &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt;[] { objClone });&lt;br /&gt;            }&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取上下文中待更新的原对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; GetIntrinsicObj(EntityObject entity)&lt;br /&gt;        {            &lt;br /&gt;            Object intrinsicObj;&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;根据输入对象的EntityKey判断该对象是已有值还是新建值&lt;br /&gt;            &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;若是已有值即从上下文中获取对应值，若是新建值即反射生成一个新对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (entity.EntityKey.EntityKeyValues != &lt;span style="color: #0000ff;"&gt;null&lt;/span&gt;)&lt;br /&gt;                intrinsicObj = _context.GetObjectByKey(entity.EntityKey);&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;br /&gt;                intrinsicObj = Activator.CreateInstance(entity.GetType());&lt;br /&gt;          &lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; intrinsicObj;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;更新上下文中的原对象，返回值为更新后的原对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;object&lt;/span&gt; UpdateIntrinsticObj(Object obj)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;记录已经复制过的实体类，避免重复加载&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            listType.Add(obj.GetType());&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;获取上下文中的原对象&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            Object intrinsicObj=GetIntrinsicObj(obj &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt; EntityObject);&lt;br /&gt;            &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;更新原对象的每个一个属性&lt;br /&gt;            &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;把原对象intrinsicObj的每一个属性设置为与obj对象相等&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;            &lt;span style="color: #0000ff;"&gt;foreach&lt;/span&gt; (PropertyInfo propertyInfo &lt;span style="color: #0000ff;"&gt;in&lt;/span&gt; obj.GetType().GetProperties())&lt;br /&gt;            {&lt;br /&gt;                &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;若listType里面包含些类型，证明此实体类已经更新过&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (!listType.Contains(propertyInfo.PropertyType) &amp;amp;&amp;amp; propertyInfo.CanWrite&lt;br /&gt;                    &amp;amp;&amp;amp; propertyInfo.Name != &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;EntityKey&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&amp;amp;&amp;amp; propertyInfo.PropertyType.Name != &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;EntityReference`1&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;)&lt;br /&gt;                {&lt;br /&gt;                    &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;若为导航属性则需要使用此方法更新&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                    &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (propertyInfo.GetCustomAttributes(&lt;span style="color: #0000ff;"&gt;typeof&lt;/span&gt;(EdmRelationshipNavigationPropertyAttribute), &lt;span style="color: #0000ff;"&gt;false&lt;/span&gt;).Count() != &lt;span style="color: #800080;"&gt;0&lt;/span&gt;)&lt;br /&gt;                    {&lt;br /&gt;                        &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;若导航属性返回值为集合则使用此方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                        &lt;span style="color: #0000ff;"&gt;if&lt;/span&gt; (propertyInfo.PropertyType.Name == &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;EntityCollection`1&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;)&lt;br /&gt;                            CloneNavigationPropertyEntityCollection(propertyInfo, intrinsicObj, obj);&lt;br /&gt;                        &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;若导航属性为普通对象则使用以下方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                            CloneNavigationProperty(propertyInfo, intrinsicObj, obj);&lt;br /&gt;                    }&lt;br /&gt;                    &lt;span style="color: #0000ff;"&gt;else&lt;/span&gt; &lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;若为普通属性则使用以下方法&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;br /&gt;&lt;/span&gt;                        CloneProperty(propertyInfo, intrinsicObj, obj);&lt;br /&gt;                }&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; intrinsicObj;&lt;br /&gt;        }&lt;br /&gt;    }&lt;/div&gt;&lt;p&gt;在完成更新操作后，再加上LingHelp类，就可以利用它完成大部的数据处理问题，大家可以建立main测试一下。&lt;/p&gt;&lt;div style="background-color: #F5F5F5;border: 1px solid #CCCCCC;padding:10px;"&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; LinqHelp:IDisposable&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; BusinessContext _context;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; UpdateHelp _updateHelp;&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; LinqHelp()&lt;br /&gt;        {&lt;br /&gt;            _context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; BusinessContext();&lt;br /&gt;            _updateHelp = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; UpdateHelp(_context);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; LinqHelp(BusinessContext context)&lt;br /&gt;        {&lt;br /&gt;            _context = context;&lt;br /&gt;            _updateHelp = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; UpdateHelp(context);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Dispose()&lt;br /&gt;        {&lt;br /&gt;            _context.Dispose();&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Add&amp;lt;T&amp;gt;(T entity) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt; T : EntityObject&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = -&lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;            Transaction transaction = Transaction.Current;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;            {&lt;br /&gt;                _context.AddObject(entity.GetType().Name, entity);&lt;br /&gt;                n = _context.SaveChanges();&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (Exception ex)&lt;br /&gt;            {&lt;br /&gt;                Business.Common.ExceptionManager.DataException.DealWith(ex);&lt;br /&gt;                transaction.Rollback();&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; n;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; Update&amp;lt;T&amp;gt;(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; T entity) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt; T:EntityObject&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; n = -&lt;span style="color: #800080;"&gt;1&lt;/span&gt;;&lt;br /&gt;            Transaction transaction = Transaction.Current;&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;try&lt;/span&gt;&lt;br /&gt;            {&lt;br /&gt;                EntityObject returnObj = &lt;span style="color: #0000ff;"&gt;this&lt;/span&gt;._updateHelp.UpdateIntrinsticObj(entity) &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt; EntityObject;&lt;br /&gt;                n = _context.SaveChanges();&lt;br /&gt;                entity = _context.GetObjectByKey(entity.EntityKey) &lt;span style="color: #0000ff;"&gt;as&lt;/span&gt; T;&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;catch&lt;/span&gt; (Exception ex)&lt;br /&gt;            {&lt;br /&gt;                Business.Common.ExceptionManager.DataException.DealWith(ex);&lt;br /&gt;                transaction.Rollback();&lt;br /&gt;            }&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; n;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; List&amp;lt;T&amp;gt; GetList&amp;lt;T&amp;gt;(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt; name) &lt;span style="color: #0000ff;"&gt;where&lt;/span&gt; T:EntityObject&lt;br /&gt;        {......}&lt;br /&gt;         ........&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; OrderRepository&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;private&lt;/span&gt; LinqHelp _linqHelp;&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; OrderRepository()&lt;br /&gt;        {&lt;br /&gt;            _linqHelp = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; LinqHelp(); &lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; AddOrder(Order order)&lt;br /&gt;        {..........}&lt;br /&gt;&lt;br /&gt;        ..............&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;int&lt;/span&gt; UpdateOrder(Order order)&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;return&lt;/span&gt; _linqHelp.Update&amp;lt;Order&amp;gt;(&lt;span style="color: #0000ff;"&gt;ref&lt;/span&gt; order);&lt;br /&gt;        }&lt;br /&gt;    } &lt;span style="color: #0000ff;"&gt;   public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; PersonRepository&lt;br /&gt;    {......}&lt;br /&gt;&lt;br /&gt;    &lt;span style="color: #0000ff;"&gt;class&lt;/span&gt; Program&lt;br /&gt;    {&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Main(&lt;span style="color: #0000ff;"&gt;string&lt;/span&gt;[] args)&lt;br /&gt;        {&lt;br /&gt;            Test1();&lt;br /&gt;            Console.ReadKey();&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #0000ff;"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;static&lt;/span&gt; &lt;span style="color: #0000ff;"&gt;void&lt;/span&gt; Test1()&lt;br /&gt;        {&lt;br /&gt;            &lt;span style="color: #0000ff;"&gt;using&lt;/span&gt; (BusinessContext context = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; BusinessContext())&lt;br /&gt;            {&lt;br /&gt;                context.ContextOptions.LazyLoadingEnabled = &lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;;&lt;br /&gt;                &lt;span style="color: #0000ff;"&gt;var&lt;/span&gt; order = context.Order.First();&lt;br /&gt;                order.Person.Address = &lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;北京路1号&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;;&lt;br /&gt;                OrderRepository orderRepository = &lt;span style="color: #0000ff;"&gt;new&lt;/span&gt; OrderRepository();&lt;br /&gt;                orderRepository.UpdateOrder(order);&lt;br /&gt;            }&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: #3300ff;"&gt;public static void&lt;/span&gt; Test2()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; using (BusinessContext context = new BusinessContext())&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Person person = context.Person.First();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Order order = new Order();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; order.OrderNumber = "2A34313344";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; OrderItem orderItem = new OrderItem();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; orderItem.Goods = "555";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; orderItem.Count = 8;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; orderItem.Price = 2.5;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; order.OrderItem.Add(orderItem);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; person.Order.Add(order);&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; PersonRepository personRepository = new PersonRepository();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; personRepository.UpdatePerson(person);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Console.Write(person.Order.First().ID + person.Order.First().OrderItem.First().ID);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;    }&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size: 16px;"&gt;&lt;strong&gt;四、性能问题&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;由于过度使用反射会使系统的性能下降，所以需要注意此更新方法的使用范围。一般此反射更新只会使用在小型的项目当中，如果在大中型项目内使用，将会在性能上负出代价。由于时间有限，而且没有经过大量的测试，有不足之处请点评。&lt;/p&gt;&lt;p&gt;对.NET开发有兴趣的朋友请加入博客园讨论小组&lt;span style="color: #0000ff;"&gt;&lt;a href="http://home.cnblogs.com/group/102576/" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;&amp;ldquo;.NET高级编程&amp;rdquo;&lt;/span&gt;&lt;/a&gt;&lt;/span&gt; 一起探讨！&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/category/347884.html"&gt;&lt;span style="font-size: 14pt; color: #ff0000;"&gt;&lt;strong&gt;.NET基础篇&lt;/strong&gt;&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;address&gt;&lt;span style="color: #0000ff;"&gt;&lt;a id="ctl02_TitleUrl" href="http://www.cnblogs.com/leslies2/archive/2011/01/27/1935860.html"&gt;&lt;span style="color: #0000ff;"&gt;以异步的方式操作TCP/IP套接字&amp;mdash;&amp;mdash;以异步方式实现简单的聊天室&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/address&gt;&lt;address&gt;&lt;span style="color: #0000ff;"&gt;&lt;a id="CategoryEntryList1_EntryStoryList_Entries_TitleUrl_1" href="http://www.cnblogs.com/leslies2/archive/2011/01/28/1939883.html"&gt;&lt;span style="color: #0000ff;"&gt;合理使用&amp;ldquo;.NET扩展方法&amp;rdquo;来简化代码（例子：空值判断，利用扩展方法实现LINQ操作符ForEach）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/address&gt;&lt;address&gt;&lt;span style="color: #0000ff;"&gt;&lt;a id="ctl02_TitleUrl" href="http://www.cnblogs.com/leslies2/archive/2011/09/09/2172267.html"&gt;&lt;span style="color: #0000ff;"&gt;分部类和分部方法&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/address&gt;&lt;address&gt;&lt;span style="color: #0000ff;"&gt;&lt;a id="ctl02_TitleUrl" href="http://www.cnblogs.com/leslies2/archive/2011/11/22/2257703.html"&gt;&lt;span style="color: #0000ff;"&gt;反射的奥妙&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/address&gt;&lt;address&gt;&lt;span style="color: #0000ff;"&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html"&gt;&lt;span style="color: #0000ff;"&gt;利用泛型与反射更新实体（ADO.NET Entity Framework）&lt;/span&gt;&lt;/a&gt;&lt;/span&gt;&lt;/address&gt;&lt;div style="text-algin: right; float: right;"&gt;&lt;p&gt;作者：风尘浪子&lt;/p&gt;&lt;p&gt;&lt;span style="color: #0000ff;"&gt;&lt;a id="Editor_Edit_hlEntryLink" title="view: C#综合揭秘&amp;mdash;&amp;mdash;利用泛型与反射更新实体（ADO.NET Entity Framework）" href="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html" target="_blank"&gt;&lt;span style="color: #0000ff;"&gt;http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html&lt;/span&gt;&lt;/a&gt; &lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;span style="color: #ff0000;"&gt;原创作品，转载时请注明作者及出处&lt;/span&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/leslies2/aggbug/2257572.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/leslies2/archive/2011/11/24/2257572.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry></feed>
