5/16/2009

The osx update guide for Core2Dual system with EFI

Backup your drivers
Open Terminal
sudo -s
*type password*
In terminal, type:
while sleep 1; do rm -rf /System/Library/Extensions/AppleIntelCPUPowerManagement.kext; done

Open Update Installer
Run update BUT DO NOT RESTART
Go back to your terminal and press Control C to end the script
In terminal type:
nano /System/InstallAtStartup/scripts/1
Replace the line Dont Steal Mac OS X.kext with dsmos.kext
Restore your drivers
Restart and boot with -v
It will start loading and then you will get the message MACH_REBOOT, there you can hard reboot your computer. When you reach the darwin boot screen again, boot with -v again just for safe measure and it will boot fine.

5/13/2009

LINQ expression of Select/Distinct and Count/Sum/Min/Max/Avg

Select/Distinct操作符



适用场景:o(∩_∩)o… 查询呗。


说明:和SQL命令中的select作用相似但位置不同,查询表达式中的select及所接子句是放在表达式最后并把子句中的变量也就是结果返回回来;延迟。


Select/Distinct操作包括9种形式,分别为简单形式、匿名类型形式、带条件形式、指定类型形式、过滤类型形式、shaped类型形式、嵌套类型形式、LocalMethodCall形式、Distinct形式。


1.简单形式:


var q =
  from c in db.Customers
  select c.ContactName;

注意:这个语句只是一个声明或者一个描述,并没有真正把数据取出来,只有当你需要该数据的时候,它才会执行这个语句,这就是延迟加载(deferred loading)。如果,在声明的时候就返回的结果集是对象的集合。你可以使用ToList() 或ToArray()方法把查询结果先进行保存,然后再对这个集合进行查询。当然延迟加载(deferred loading)可以像拼接SQL语句那样拼接查询语法,再执行它。


2.匿名类型形式:


说明:匿名类型是C# 3.0中新特性。其实质是编译器根据我们自定义自动产生一个匿名的类来帮助我们实现临时变量的储存。匿名类型还依赖于另外一个特性:支持根据property来创建对象。比如,var d = new { Name = "s" };编译器自动产生一个有property叫做Name的匿名类,然后按这个类型分配内存,并初始化对象。但是var d = new {"s"};是编译不通过的。因为,编译器不知道匿名类中的property的名字。例如string c = "d";var d = new { c}; 则是可以通过编译的。编译器会创建一个叫做匿名类带有叫c的property。

例如下例:new{c,ContactName,c.Phone};ContactName和Phone都是在映射文件中定义与表中字段相对应的property。编译器读取数据并创建对象时,会创建一个匿名类,这个类有两个属性,为ContactName和Phone,然后根据数据初始化对象。另外编译器还可以重命名property的名字。


var q =
   from c in db.Customers
   select new {c.ContactName, c.Phone};

语句描述:查询顾客的联系人和电话。


var q =
   from e in db.Employees
   select new {Name = e.FirstName + " " + e.LastName, Phone = e.HomePhone};

语句描述:查询职员的姓名和家庭电话


var q =
   from p in db.Products
   select new {p.ProductID, HalfPrice = p.UnitPrice / 2};

3.带条件形式:


说明:生成SQL语句为:case when condition then else。


var q =
   from p in db.Products
   select new {p.ProductName, Availability = p.UnitsInStock - p.UnitsOnOrder < 0 ? "Out Of Stock": "In Stock"};

4.指定类型形式:


说明:该形式返回你自定义类型的对象集。


var q =
   from e in db.Employees
   select new Name {FirstName = e.FirstName, LastName = e.LastName};

5.过滤类型形式:


说明:结合where使用,起到过滤作用。


var q =
   from c in db.Customers
   where c.City == "London"
   select c.ContactName;

6.shaped类型形式:


说明:其select操作使用了匿名对象,而这个匿名对象中,其属性也是个匿名对象。


var q =
   from c in db.Customers
   select new {
     c.CustomerID,
     CompanyInfo = new {c.CompanyName, c.City, c.Country},
     ContactInfo = new {c.ContactName, c.ContactTitle}
   };

语句描述:查询顾客的ID和公司信息(公司名称,城市,国家)以及联系信息(联系人和职位)。


7.嵌套类型形式:


说明:返回的对象集中的每个对象DiscountedProducts属性中,又包含一个集合。也就是每个对象也是一个集合类。


var q =
   from o in db.Orders
   select new {
     o.OrderID,
     DiscountedProducts =
       from od in o.OrderDetails
       where od.Discount > 0.0
       select od,
     FreeShippingDiscount = o.Freight
   };

8.LocalMethodCall形式:


var q = from c in db.Customers
   where c.Country == "UK" || c.Country == "USA"
   select new { c.CustomerID, c.CompanyName, Phone = c.Phone, InternationalPhone =

PhoneNumberConverter(c.Country, c.Phone) };

  


XDocument doc = new XDocument(
   new XElement("Customers", from c in db.Customers
             where c.Country == "UK" || c.Country == "USA"
             select (new XElement("Customer",
               new XAttribute("CustomerID", c.CustomerID),
               new XAttribute("CompanyName", c.CompanyName),
               new XAttribute("InterationalPhone", PhoneNumberConverter(c.Country, c.Phone))
               ))));

9.Distinct形式:


说明:筛选字段中不相同的值。用于查询不重复的结果集。生成SQL语句为:SELECT DISTINCT [City] FROM [Customers]


var q = (
   from c in db.Customers
   select c.City )
   .Distinct();

语句描述:查询顾客覆盖的国家。


Count/Sum/Min/Max/Avg操作符



适用场景:统计数据吧,比如统计一些数据的个数,求和,最小值,最大值,平均数。


Count


说明:返回集合中的元素个数,返回INT类型;不延迟。生成SQL语句为:SELECT COUNT(*) FROM


1.简单形式:


var q = db.Customers.Count();

2.带条件形式:


var q = db.Products.Count(p => !p.Discontinued);

LongCount


说明:返回集合中的元素个数,返回LONG类型;不延迟。对于元素个数较多的集合可视情况可以选用LongCount来统计元素个数,它返回long类型,比较精确。生成SQL语句为:SELECT COUNT_BIG(*) FROM


var q = db.Customers.LongCount();

Sum


说明:返回集合中数值类型元素之和,集合应为INT类型集合;不延迟。生成SQL语句为:SELECT SUM(…) FROM


1.简单形式:


var q = db.Orders.Select(o => o.Freight).Sum();

2.映射形式:


var q = db.Products.Sum(p => p.UnitsOnOrder);

Min


说明:返回集合中元素的最小值;不延迟。生成SQL语句为:SELECT MIN(…) FROM


1.简单形式:


var q = db.Products.Select(p => p.UnitPrice).Min();

2.映射形式:


var q = db.Orders.Min(o => o.Freight);

3.原理:


var categories =
   from p in db.Products
   group p by p.CategoryID into g
   select new {
   CategoryID = g.Key,
   CheapestProducts =
   from p2 in g
   where p2.UnitPrice == g.Min(p3 => p3.UnitPrice)
   select p2
   };

Max


说明:返回集合中元素的最大值;不延迟。生成SQL语句为:SELECT MAX(…) FROM


1.简单形式:


var q = db.Employees.Select(e => e.HireDate).Max();

2.映射形式:


var q = db.Products.Max(p => p.UnitsInStock);

3.原理:


var categories =
   from p in db.Products
   group p by p.CategoryID into g
   select new {
   g.Key,
   MostExpensiveProducts =
   from p2 in g
   where p2.UnitPrice == g.Max(p3 => p3.UnitPrice)
   select p2
   };

Average


说明:返回集合中的数值类型元素的平均值。集合应为数字类型集合,其返回值类型为double;不延迟。生成SQL语句为:SELECT AVG(…) FROM


1.简单形式:


var q = db.Orders.Select(o => o.Freight).Average();

2.映射形式:


var q = db.Products.Average(p => p.UnitPrice);

3.原理:


var categories =
   from p in db.Products
   group p by p.CategoryID into g
   select new {
   g.Key,
   ExpensiveProducts =
   from p2 in g
   where p2.UnitPrice > g.Average(p3 => p3.UnitPrice)
   select p2
   };

Aggregate


说明:根据输入的表达式获取聚合值;不延迟。即是说:用一个种子值与当前元素通过指定的函数来进行对比来遍历集合中的元素,符合条件的元素保留下来。如果没有指定种子值的话,种子值默认为集合的第一个元素。


下面用一个表格总结一下这篇说的LINQ语句













































Where 过滤;延迟
Select 选择;延迟
Distinct 查询不重复的结果集;延迟
Count 返回集合中的元素个数,返回INT类型;不延迟
LongCount 返回集合中的元素个数,返回LONG类型;不延迟
Sum 返回集合中数值类型元素之和,集合应为INT类型集合;不延迟
Min 返回集合中元素的最小值;不延迟
Max 返回集合中元素的最大值;不延迟
Average 返回集合中的数值类型元素的平均值。集合应为数字类型集合,其返回值类型为double;不延迟
Aggregate 根据输入的表达式获取聚合值;不延迟

4/13/2009

几种比较常见的敏捷编程方法

◆极限编程(XP)
这种方法强调的是适应性,而不是可预测性。它最适合这种场合: 公司并不确切知道自己需要什么样的最终产品。这种方法最先由Kent Beck采用。

◆Scrum
这种方法强调的是重新开始迭代过程,而不是企图补救问题。它最适合这种场合: 公司在使用新工具,以及应用软件在开发过程中几乎肯定会变化。1993年,Jeff Sutherland在Easel Corporation最先使用了Scrum方法。

◆自适应软件开发(ASD)
这种方法强调的是速度和灵活性。它最适合这种场合: 公司需要应用软件能够迅速见效,还能随客户使用需求的增长而灵活变化。这种方法的发明者是Jim Highsmith。

◆动态系统开发方法(DSDM)
这种方法最初来源于强调用户参与的快速应用软件开发(RAD)技术。它最适合于在开发人员不是非常了解环境的情况。1990年,DSDM联合会在英国发明了这种方法,旨在综合编程最佳实践方面的经验。

◆功能驱动开发(FDD)
这种方法强调的是可预测性以及遵守开发最佳实践。它最适合以下场合: 开发团队必须开发具有特定功能及可读性高于正常水平的应用软件。1997年,Jeff De Luca最早发明了这种方法,旨在满足当时一家新加坡大银行的需求。

敏捷开发的观点总结与体会

敏捷的三个要素是迭代开发、坦诚合作和自适应性。
迭代开发:把功能进行小粒度的分割,采用迭代和增量式的开发方法,时间段是按周而不是按月进行度量。频每交付使用,而不是等待项目开发完成一次性提交。这样也就能有比较明显的阶段性成果,可以按周交付新功能。这对于Web应用程序尤其适合。持续性的更新,可使用户有新鲜感,提高其访问频度和使用次数。也有助于开发人员根据用户的反馈数据,应对需求的变更,及时做出响应与改进。
  坦诚合作:以我来说,做为开发人员,合作应该主要是有两类:一类是与开发人员的合作,另一类是与业务人员。与业务人员的合作很容易理解,能做到一起紧密工作,可使得产品更能切合实际的需求。而不是作完需求分析后,就将他们一脚踢开,直至产品交付。以往所做项目都不算大,几个人而已,合作也是分模块分别开发再整合。所以与开发人员的合作体会还不是很深,没看出敏捷开发有什么明显的改善。 自适应性:这一点让我有耳目一新的感觉。其实像Web2.0这类互联网应用,现实不断发展与变化,需求也在不断改变,未来状态难以预测,也就很难提前用一个文档来规范所有的开发行为。自适应方法就是不断变化的现实情况,来及时作出改变。这也就需要信任开发人员的能力,给其更多的活动空间。相信对于一个合格的开发人员,这也会有助于调动其主观能动性,以更加积极的态度来参与开发。软件开发更象是拍一场电影,而不是建楼房。项目经理是导演,剧本是已定的。但在拍摄中,是要调动出演员的表演才能,而不是指挥一群木偶。
认识的几个误区:1. 敏捷是“一个”过程
敏捷不是一个过程,是一类过程的统称,它们有一个共性,就是符合敏捷价值观,遵循敏捷的原则。敏捷的价值观如下:* 个体和交互 胜过 过程和工具* 可以工作的软件 胜过 面面俱到的文* 客户合作 胜过 合同谈判* 响应变化 胜过 遵循计划
由价值观引出的12条敏捷原则:1 我们最优先要做的是通过尽早的、持续的交付有价值的软件来使客户满意。2 即使到了开发的后期,也欢迎改变需求。敏捷过程利用变化来为客户创造竞争优势。3 经常性地交付可以工作的软件,交付的间隔可以从几个星期到几个月,交付的时间间隔越短越好。4 在整个项目开发期间,业务人员和开发人员必须天天都在一起工作。5 围绕被激励起来的个体来构建项目。给他们提供所需的环境和支持,并且信任他们能够完成工作。6 在团队内部,最具有效果并且富有效率的传递信息的方法,就是面对面的交谈。7 工作的软件是首要的进度度量标准。8 敏捷过程提倡可持续的开发速度。责任人、开发者和用户应该能够保持一个长期的、恒定的开发速度。9 不断地关注优秀的技能和好的设计会增强敏捷能力。10 简单——使未完成的工作最大化的艺术——是根本的。11 最好的构架、需求和设计出自于自组织的团队。12 每隔一定时间,团队会在如何才能更有效地工作方面进行反省,然后相应地对自己的行为进行调整。 建立敏捷联盟的17位大师所创立的敏捷方法包括:极限编程,Scrum,特征驱动开发,动态系统开发方法,自适应软件开发,水晶方法,实用编程方法。这些方法统称为敏捷方法。
其实每个人都可以从敏捷宣言和原则出发,明确问题,找出一些解决方法,形成自己的过程。我觉得国内的软件环境这么复杂,程序员的自主精神又这么强,敏捷方法应该是在中国首先提出才对,只是国人都有唯标准唯规范至上的心理定式,即使找出好办法,也觉得不规范,没有深入形成理论,无法提升高度,始终是跟着鬼子屁股后面走,我想这也是国外软件行业不成熟的表现之一吧。 2. 敏捷仅仅是一个软件过程如果仅仅从软件过程的角度去认识敏捷实施敏捷,效果不会太好。敏捷相对以前的软件工程最大的革新之处在于把人的作用提高到了过程至上,正如敏捷宣言的第一条“个体和交互胜过过程和工具”所说的。涉及到人的问题,就已经不再是过程所能覆盖的了,就到了企业管理的层面上了,包括企业的价值观和文化。这也是敏捷在国内实施的最大障碍:把客户当作合作伙伴而不是对手,从客户角度出发去想问题,充分的跟客户沟通,而不是出了问题推诿责任。目标是让软件实现客户的价值,而不是收钱就完事儿。把人的能动性调动起来,给动力而不是给压力。要实用而不是要规范。让开发人员理解并实施,体验到敏捷的好处,而不是盲目机械地实施规范。没有绝对的权威,每个人都有可取之处。3. 迭代就是敏捷,UP属于敏捷。看到这么多人都把UP归入敏捷,我都开始怀疑是不是自己搞错了。但是在我的印象中:UP是重型的过程,虽然引入了迭代,但是其原则和价值观与敏捷是不同的。敏捷注重的是反馈,迭代周期尽量的短,重在客户的参与,通过客户的参与,获取持续的反馈,不断调整使整个项目走在正确的方向上。同时也给客户一个感受和思考的机会,因为对于大多数客户而言,目标是明确的(不排除有些客户目标也不明确),但是具体怎么做,开始时是没有想法的,只有看到具体的东西的时候,才知道“噢,原来可以这样,那我想把这里调整一下”。4. 敏捷是彻底革命的。敏捷,特别是XP,让人有耳目一新的感觉,觉得以前的所有软件工程理论,设计方法都可以抛弃掉了,推翻一切,从头再来。抱着这种想法实施敏捷,那就错了,敏捷不是“石头里蹦出个孙大圣”,以前的软件过程中也有敏捷的影子,只是没有像敏捷一样上升到价值观和原则的高度,比如快速原型法。敏捷是在对已有的软件过程方法的改进,抛弃的是传统软件工程低效的外表,以往的软件过程中很多技巧都是很实用的。实施敏捷应该以现有的软件过程为基础,从敏捷宣言和原则出发,利用敏捷的方法来改善过程。5. 敏捷是反文档的。文档只是为了达成目标的一种手段,如果这种手段是低效的,那就换一种手段。可是完全抛弃了文档,怎样解决沟通的问题?难道你想每次沟通都完全用手比划,用嘴说,跟不同的人重复表述同样的想法,那样更是低效的。应该清楚文档的本质是把知识显性化。在一个项目中存在很多需要沟通的知识,知识具备两种形态,显性的和隐性的,传统的观念是尽量把隐性知识显性化,即文档化,而忽略了这其中的代价(特别是更新同步文档的代价)。因此,在实施敏捷的时候,需要在团队内明确哪些知识是必须显性的,这些知识可以通过文档交流。哪些知识是可以隐性的,这些知识则完全可以通过口头的方式进行交流,以达到沟通的最佳效率。文档不是目的,有效沟通才是目的。6. 为了敏捷而敏捷“嗯,敏捷这么好,我们也敏捷吧”,可能很多人会有这种想法。忘了以前是在哪儿看的大师采访录:Q:“我们现有的过程很好,不知道怎么用敏捷改进?”A:“既然很好,那就不要用敏捷”。做什么事情都要有明确目标的,敏捷虽好,得看你需不需要,能不能解决你现在头疼的问题,如果不是,那就不
要给自己找麻烦了。7. 敏捷是CMM的反义词在桂林会议的讨论中,很多人把CMM作为敏捷的反义词,我觉得这不是很合适。CMM只是一种衡量软件成熟度的标准,并非过程,和敏捷不是一类概念。如果要给敏捷找一个反义词,我觉得传统的瀑布式开发应该更合适一些。并且,我认为,如果CMM还能继续流行下去的话,应该会有公司可以用敏捷改善的过程通过CMM认证。8. 敏捷是自由的,无约束的。
敏捷强调的是自组织团队,发挥人的能动性,以动力代替压力,让人有绝对自由的错觉。但是应该清楚,凡是都是要讲究一个平衡,人也是两面的,消极的一面和积极的一面同时并存,绝对的自由会放纵人消极的一面。敏捷并非是绝对自由,无约束的。作为管理者,有一个职责,就是引导团队成员用自己积极的一面去压制消极的一面,不能放任团队中出现搭便车的现象,否则将打击整个团队的士气。如果实在无效,那就只能将其排除出团队了,这个惩罚够有约束力吧?9. 重做就是重构
重做不等于重构,很多场合这两个概念是混淆的。但是在敏捷中,重构的一个特征是必须可控的。当对系统结构进行大的调整时,如果没有测试驱动辅助的话,那么可控性就会很差,这不能叫做重构。

敏捷开发过程中容易出现的问题有时在敏捷开发中,反而不觉得有多敏捷,进度一拖再拖,问题一个接着一个,让我觉得我们是在进行慌乱开发为什么会这样?
  杀手一: 管理者的执行力不够
  据我观察,目前项目中,开发者或者说参与人的状态是混乱的,或者说是慌乱的。那问题在哪里呢?是我们的工作流程出了问题?不应该啊。我们在项目启动前已经定了一个看似美好的流程啊,而且是经过参与人讨论一致通过的。那么问题在哪里呢?昨天,一位产品专员在跟进项目时没有按照流程走,当我跟他讲起那个美好的流程的时候,他竟然说我不知道有这个流程啊! 问题出现了,原来是沟通、传达出了问题。同样的问题也出现在了另一位产品经理上,我们聊起进度时,他讲到似乎觉得目前的进度不可控,和他探讨不可控的原因(我很开心他愿意和我交流,也很感谢他能给我这个机会发表我对项目管理方面的看法,因为我曾被其他的产品er伤害多次),我说他的执行力不够,然后给了他一些如果是我我会怎样怎样之类的建议,希望能对他以及我们的项目有所帮助。
  解决办法:加大执行力,今日事今日毕,这是必须的。
杀手二:无法预测的风险
  这个问题还是原于我和那位产品经理的谈话,我们在分析进度不可控的原因时,他提到了这样一个问题:当他跟踪开发人员的进度,并询问为什么没有按照进度进行时,得到的回答是我开始没有想到有这么多 。OK,问题出来了,为什么没有想到有这么多?项目开始前的进度计划是开发人员自己定的,那么在项目开始前,他应该是给自己预留了一些机动的、预备性的风险时间吧,难道他没有么?我们不知道。那如果我现在问抛开你没想到的那些,你开始想到的东西是按进度进行的么?恐怕得到的回答也未必是令人满意的吧,那么难道这句没有想到难道是个托辞么?希望不是。
  解决办法:充分意识到项目中可能会存在的风险因素,在制定计划时预留一定的时间,如果在项目进行中出现了没有想到的问题,根据其重要性,考虑压后解决,要在计划的时间内把计划的事情完成好,并为后续解决问题争取更多的时间。
杀手三:团队的做事风格
  这个问题应该是因团而异的,so,我只讲我不喜欢的风格。
  1、我们抛开以前的……现在开始……
  这可以说是作为个人来讲在目前的开发过程中最讨厌的一句话, 这句话意味着凡事不求原因,只求结果,也许这是敏捷开发带来的恶果(可怜的敏捷开发-_-),但更多的原因应该是做事的风格问题,我极厌恶这种不问原因的做法。请放心,如果你的团队在开发过程中出现了这句话,他一定会出现第二次、第三次。。。。请耐心等待
  解决办法:发现问题,及时找到产生问题的原因,制定相应的解决办法,并在后续的开发过程中尽量避免发生同样的问题。
  个人觉得好的开发过程应该是这样的:
  1、有一个优化的工作流程
  2、有一个良好的项目计划(包括风险的预测)
  3、有一个良好的做事风格
  4、有一个执行力强的头头
  5、有一个平稳的心态,不要慌
常见程序开发人员的一些常见通病:
[*]消极:不愿意修改bug,不愿意改代码以满足用户新提出的需求[*]焦虑:担心刚刚修改的代码会破坏已有功能,对下一个版本能否正常工作毫无信心,梦到测试人员报告其大量bug[*]易怒:经常对测试mm发火,私下里诅咒客户,抱怨别人弄坏了自己的程序[*]神经质:系统偶尔出现奇怪行为就胡乱猜测,改了不该改的地方导致更多奇怪现象出现[*]那段日子简直不堪回首,是对程序员身心的双重折磨![*]需求变化频繁:敏捷的口号就是"拥抱变化",有单元测试作保障,让变化来的更多些吧
建议:
勇气:单元测试是自动化的回归测试,她让我对自己的代码充满自信,每一个测试就像攀岩者钉在峭壁上的一个楔子,没有了程序衰退的担心,于是我可以大胆的重构、积极的拥抱变化;快速反馈:每写一段代码,我都可以在几秒钟之内看到他的运行效果,免去了打包、部署、重起server以及在一堆日志里找结果的工作,开发的效率极大提高;
测试驱动设计:通过编写测试可以准确的理解需求、发现问题、发现接口,在不知不觉间做出最合理的设计;文档:测试是最好的详细设计文档,不会过时、可运行。
从瀑布模型向增量开发模型转变,那么如何才能在转变的

Test-Driven Development,测试驱动开发,它是敏捷开发的最重要的部分。在ThoughtWorks,我们实现任何一个功能都是从测试开始,首先对业务需求 进行分析,分解为一个一个的Story,记录在Story Card上。然后两个人同时坐在电脑前面,一个人依照Story,从业务需求的角度来编写测试代码,另一个人看着他并且进行思考,如果有不同的意见就会提 出来进行讨论,直到达成共识,这样写出来的测试代码就真实反映了业务功能需求。接着由另一个人控制键盘,编写该测试代码的实现。如果没有测试代码,就不能 编写功能的实现代码。先写测试代码,能够让开发人员明确目标,就是让测试通过。

Continuous Integration,持续集成。在以往的软件开发过程中,集成是一件很痛苦的事情,通常很长时间才会做一次集成,这样的话,会引发很多问题,比如 build未通过或者单元测试失败。敏捷开发中提倡持续集成,一天之内集成十几次甚至几十次,如此频繁的集成能尽量减少冲突,由于集成很频繁,每一次集成 的改变也很少,即使集成失败也容易定位错误。一次集成要做哪些事情呢?它至少包括:获得所有源代码;编译源代码;运行所有测试,包括单元测试、功能测试 等;确认编译和测试是否通过,最后发送报告。当然也会做一些其它的任务,比如说代码分析、测试覆盖率分析等等。 在我们公司里,开发人员的桌上有一个火山灯用来标志集成的状态,如果是黄灯,表示正在集成;如果是绿灯,表示上一次集成通过,开发人员在这时候获得的代码 是可用而可靠的;如果显示为红灯,就要小心了,上一次集成未通过,需要尽快定位失败原因从而让灯变绿。

Refactoring,重构。相信大家对它都很熟悉了,有很多很多的书用来介绍重构,最著名的是 Martin的《重构》,Joshua的《从重构到模式》等。重构是在不改变系统外部行为下,对内部结构进行整理优化,使得代码尽量简单、优美、可扩展。 在以往开发中,通常是在有需求过来,现在的系统架构不容易实现,从而对原有系统进行重构;或者在开发过程中有剩余时间了,对现在代码进行重构整理。但是在 敏捷开发中,重构贯穿于整个开发流程,每一次开发者check in代码之前,都要对所写代码进行重构,让代码达到clean code that works。值得注意的是,在重构时,每一次改变要尽可能小,用单元测试来保证重构是否引起冲突,并且不只是对实现代码进行重构,如果测试代码中有重复, 也要对它进行重构。

Pair-Programming,结对编程。在敏捷开发中,做任何事情都是Pair的,包括分析、写测试、写实 现代码或者重构。Pair做事有很多好处,两个人在一起探讨很容易产生思想的火花,也不容易走上偏路。在我们公司,还有很多事都是Pair来做,比如 Pair学习,Pair翻译,Pair做PPT,关于这个话题,钱钱同学有一篇很有名的文章对它进行介绍,名为Pair Programming (结对编程)。Stand up,站立会议。每天早上,项目组的所有成员都会站立进行一次会议,由于是站立的,所以时间不会很长,一般来说是15-20分钟。会议的内容并不是需求分 析、任务分配等,而是每个人都回答三个问题:1. 你昨天做了什么?2. 你今天要做什么? 3. 你遇到了哪些困难?站立会议让团队进行交流,彼此相互熟悉工作内容,如果有人曾经遇到过和你类似的问题,那么在站立会议后,他就会和你进行讨论。

Frequent Releases,小版本发布。在敏捷开发中,不会出现这种情况,拿到需求以后就闭门造车,直到最后才将产品交付给客户,而是尽量多的产品发布,一般以 周、月为单位。这样,客户每隔一段时间就会拿到发布的产品进行试用,而我们可以从客户那得到更多的反馈来改进产品。正因为发布频繁,每一个版本新增的功能 简单,不需要复杂的设计,这样文档和设计就在很大程度上简化了。又因为简单设计,没有复杂的架构,所以客户有新的需求或者需求进行变动,也能很快的适应。

Minimal Documentation,较少的文档。其实敏捷开发中并不是没有文档,而是有大量的文档,即测试。这些测试代码真实的反应了客户的需求以及系统API 的用法,如果有新人加入团队,最快的熟悉项目的方法就是给他看测试代码,而比一边看着文档一边进行debug要高效。如果用书面文档或者注释,某天代码变 化了,需要对这些文档进行更新。一旦忘记更新文档,就会出现代码和文档不匹配的情况,这更加会让人迷惑。而在敏捷中并不会出现,因为只有测试变化了,代码 才会变化,测试是真实反应代码的。 这时有人会问:代码不写注释行吗?一般来说好的代码不是需要大量的注释吗?其实简单可读的代码才是好的代码,既然简单可读了,别人一看就能够看懂,这时候 根本不需要对代码进行任何注释。若你觉得这段代码不加注释的话别人可能看不懂,就表示设计还不够简单,需要对它进行重构。

Collaborative Focus,以合作为中心,表现为代码共享。在敏捷开发中,代码是归团队所有而不是哪些模块的代码属于哪些人,每个人都有权利获得系统任何一部分的代码然 后修改它,如果有人看到某些代码不爽的话,那他能够对这部分代码重构而不需要征求代码作者的同意,很可能也不知道是谁写的这部分代码。这样每个人都能熟悉 系统的代码,即使团队的人员变动,也没有风险。

Customer Engagement ,现场客户。敏捷开发中,客户是与开发团队一起工作的,团队到客户现场进行开发或者邀请客户到团队公司里来开发。如果开发过程中有什么问题或者产品经过一个迭代后,能够以最快速度得到客户的反馈。

Automated Testing ,自动化测试。为了减小人力或者重复劳动,所有的测试包括单元测试、功能测试或集成测试等都是自动化的,这对QA人员提出了更高的要求。他们要熟悉开发语 言、自动化测试工具,能够编写自动化测试脚本或者用工具录制。我们公司在自动化测试上做了大量的工作,包括Selenium开源项目。

Adaptive Planning,可调整计划。敏捷开发中计划是可调整的,并不是像以往的开发过程中,需求分析->概要设计->详细设计->开发- >测试->交付,每一个阶段都是有计划的进行,一个阶段结束便开始下一个阶段。而敏捷开发中只有一次一次的迭代,小版本的发布,根据客户反馈 随时作出相应的调整和变化。

敏捷开发过程与传统的开发过程有很大不同,在这过程中,团队是有激情有活力的,能够适应更大的变化,做出更高质量的软件。

2/20/2009

2008年最龌龊语录100句(暴笑+发人深思的笑)

002◎和一MM争论鲸鱼是不是鱼,最后我说“曰本人也带个人字”,她这才同意鲸鱼不是鱼。

003◎男人膝下有黄金,我把整个腿都切下来了,连块铜也没找着!

004◎春天我把玉米埋在土里,到了秋天我就会收获很多玉米。春天我把老婆埋在土里,到了秋天我就会…被枪毙!

005◎如果你看到面前的阴影,别怕,那是因为你的背后有阳光!

006◎踏遍青楼人未老,请用汇仁肾宝。

007◎听君一席话,省我十本书!

008◎0岁出场亮相,10岁天天向上。20岁远大理想,30岁发奋图强。40岁基本定向,50岁处处吃香。60岁打打麻将,70岁处处闲逛。80岁拉拉家常,90岁挂在墙上!

009◎脱了衣服我是禽兽,穿上衣服我是衣冠禽兽!

010◎师太,你就从了老衲吧!…很久很久以后…师太,你就饶了老衲吧!

011◎“亲爱的,我…我怀孕了…三个月了,不过你放心,不是你的,不用你负责……”

012◎我们产生一点小分歧:她希望我把粪土变黄金,我希望她视黄金如粪土。

013◎读10年语文,不如聊半年QQ。

014◎早晨懒床,遂从口袋里掏出6枚硬币:如果抛出去六个都是正面,我就去上课!思躇良久,还是算了,别冒这个险了……

015◎我花8万买了个西周陶罐,昨儿到《鉴宝》栏目进行鉴定,专家严肃地说:“这哪是西周的?这是上周的!”

016◎我能容忍身材是假的,脸是假的,胸是假的,臀是假的!!!但就是不容忍钱是假的!!!!

017◎士为知己者装死,女为悦己者整容。

018◎长大了要嫁给唐僧,能玩就玩,不能玩就把他吃掉。

019◎一山不能容二虎,除非一公和一母。

020◎千万别等到人人都说你丑时才发现自己真的丑。

021◎如果朋友可以出卖,每个值五块的话,我也能发笔小财了。

022◎征婚启事:要求如下,A活的,B女的。

023◎给点阳光我就腐烂。

024◎要适当吃一点,才有劲减肥啊。

025◎摇啊摇,摇到奈何桥。

026◎命运负责洗牌,但是玩牌的是我们自己!

027◎问:你喜欢我哪一点?答:我喜欢你离我远一点!

028◎你快回来,我一人忽悠不来!

029◎生活就像宋祖德的嘴,你永远都不知道下一个倒霉的会是谁~~~

030◎跌倒了,爬起来再哭~~~

031◎世界上难以自拔的,除了牙齿,还有爱情。

032◎一恐龙路过西X交大时上了趟厕所,出来后她呜咽道:“555,这辈子终于不愁嫁不出去了……”

033◎生,容易。活,容易。生活,不容易。

034◎吾表兄,年四十余。始从文,连考三年而不中。遂习武,练武场上发一矢,中鼓吏,逐之出。改学医,自撰一良方,服之,卒。

035◎问君能有几多愁,恰似一群太监上青楼……

036◎吾生也有涯,而吃也无涯~~~

037◎想污染一个地方有两种方法:垃圾,或是钞票!

038◎年轻的时候,我们常常冲着镜子做鬼脸;年老的时候,镜子算是扯平了。

039◎你瞎了眼啊?这么大的盾牌你看不见,偏偏要把石头朝我脑袋上扔!

040◎出问题先从自己身上找原因,别一便秘就怪地球没引力。

041◎拍脑袋决策,拍胸脯保证,拍屁股走人。

042◎我们走得太快,灵魂都跟不上了……

043◎不要和地球人一般见识~~~

044◎女孩从处女到女人只要一次并成功,男孩从处男变男人需要反复的磨练!

045◎出来混,老婆迟早是要换的!

046◎小时候我以为自己长大后可以拯救整个世界,等长大后才发现整个世界都拯救不了我……

047◎有钱的都是大爷!但是欠钱不还的更是!

048◎我就算是一只癞蛤蟆,我也决不娶母癞蛤蟆。

049◎生前何必久睡,死后自会长眠……

050◎不想当厨子的裁缝,不是好司机。

051◎时间是最好的老师,但遗憾的是——最后他把所有的学生都弄死了。

052◎去西安出差的路上,一位大连老兄一阵狂吹大连多好多好,然后说大连建市一百周年的时候举行了很隆重的庆祝活动云云,然后问了旁边一人:“西安建市一百周年有什么庆祝活动没有?”旁边几位西安的哥们一愣,过了一会儿,逼出一句话来:“我记得西安建市600年的时候搞了一个‘烽火戏诸侯’吧……”

053◎钻石恒久远,一颗就破产!

054◎和谐校园里,骑自行车的也许是位博导,而开奔驰的则可能是个后勤……

055◎是金子,总会花光的;是镜子,总会反光的……

056◎我女友不当尼姑的原因是她四级没过,庵里不收。

057◎明星脱一点就能更出名,我脱的光光的却被抓起来了!

058◎看一漂亮MM,苦无搭讪办法,路旁一砖头,拣起,上前,“同学,这是你掉的吧?”

059◎小时候的梦想并不是要当什么科学家,幻想自己是地主家的少爷,家有良田千顷,终日不学无术,没事领着一群狗奴才上街去调戏一下良家少女……

060◎别和我谈理想,戒了!

061◎玫瑰你的,巧克力你的,钻石你的。你,我的!

062◎所谓惊喜就是你苦苦等候的兔子来了,后面跟着狼!

063◎什么是幸褔?幸福就是猫吃鱼狗吃肉,奥特曼打小怪兽!

064◎俩农夫吹牛:“俺们农场的鸡,吃的都是茶叶,下的全是茶叶蛋”“有嘛啊,咱农场给鸡吃钱包,让它下荷包蛋。”

065◎蟑螂都不怕蟑螂药了,我们却连维生素都搞不定!

066◎长个包子样就别怨狗跟着!

067◎男人偷腥时的智商仅次于爱因斯坦!

068◎为中华而努力读书!一包中华好多钱啊……

069◎如果你不能给你的女人穿上嫁衣,那么千万别停下你解开她衣扣的手!

070◎别以为穿着脏衣服就可以做污点证人;别以为穿着木制拖鞋就可以做木屐证人……

071◎事业是国家的,荣誉是单位的,成绩是领导的,工资是老婆的,财产是孩子的,错误是自己的。

072◎凤凰重生就是涅盘,野鸡重生就是尸变。

073◎如果有一天我变成流氓,请告诉别人,我纯真过……

074◎老子不但有车,还是自行的……

075◎女人拥有无数个QQ号只为了调戏一个男人,男人常用一个QQ号上面加满各种各样的女人……

076◎偶然看见书上所谓的当代女子择偶标准:“有车有房,父母双亡。”郁闷。遂写下幻想中的选妻标准:“家中财产过亿,美貌天下第一,贤惠温柔性感,岳父癌症晚期……”

077◎大部分人一辈子只做三件事:自欺、欺人、被人欺。

078◎睡眠是一门艺术——谁也无法阻挡我追求艺术的脚步!

079◎为了避免家庭暴力,于是我决定不结婚!

080◎你可以像猪一样的生活,但你永远都不能像猪那样快乐!

081◎迅雷不及掩耳盗铃,以不变应万变不离其宗,成事不足挂齿,此物最相思风雨中,一屋不扫何以扫天下无敌,东边日出西边雨一直下,举头望明月几时有,呆若木鸡毛当令箭,杀鸡焉用牛刀小试,锋芒毕露春光,围魏救赵宝奎,Very good bye,八格牙鲁冰花,一泻千里共婵娟……

082◎某女的一篇博客日记:某月某日,大醉而归,伸手一摸——手机和贞操都在,睡觉!

083◎又美丽、又纯洁、又温柔、又性感、又可爱的处女,就像鬼魂一样,男人们都在谈论它,但从来没有人亲眼见过……

084◎记得小学老师骂我:“我一巴掌把你踢出去!”当时我想笑却不敢笑。现在,是敢笑却不会笑了……

085◎如果幸福是浮云,如果痛苦似星辰。那我的生活真是万里无云,漫天繁星……

086◎避孕的效果:不成功,便成“人”。

087◎孤单是一个人的狂欢,狂欢是一群人的孤单。

088◎这世上最累的事情,莫过于眼睁睁看着自己的心碎了,还得自己动手把它粘起来。

089◎人生的悲惨在于:辛辛苦苦的作了一晚上内容香艳的美梦,第二天早上醒来居然全都记不起来了!

090◎父亲问我人生有什么追求?我回答金钱和美女,父亲凶狠的打了我的脸;我回答事业与爱情,父亲赞赏的摸了我的头。

091◎男人都好色,色心稍强一点叫色狼,再强一点叫色鬼,更加强就叫色魔,尤其强那就成了变态色魔,好色到了极致,被称作人体美学艺术家。

092◎记得刚毕业不久的一天,女友给我发了一条短信:“我们还是分手吧!”我还没来得及伤心呢,女友又发来一条:“对不起,发错了。”这下可以彻底伤心了……

093◎此地禁止大小便,违者没收工具。

094◎在街上看美女,目光高一点就是欣赏,目光低一点就是流氓。

095◎孩儿他娘,咱这辈子还有很多事要做呢,别耽误功夫和我玩捉迷藏了,赶紧蹦出来吧~~~

096◎女人一生喜欢两朵花:一是有钱花,二是尽量花!

097◎一炮走红——是形容女艺人的……

098◎这个世界不公平就在于:上帝说:“我要光!”于是有了白天。美女说:“我要钻戒!”于是她有了钻戒。富豪说:“我要女人!”于是他有了女人。我说:“我要洗澡!”居然停水了!

099◎真不明白,女孩买很多很多漂亮衣服穿,就是为了吸引男孩的目光,但男孩想看的,却是不穿衣服的女孩。

100◎偶尔幽生活一默你会觉得很爽,但生活幽你一默就惨了……

2/02/2009

WCF服务的程序字符串过长时服务器端报HTTP 400错误

编写基于WCF服务的程序时,向WCF服务端发送一长串的HTML源码,结果客户端收到提示如下:
格式化程序尝试对消息反序列化时引发异常: 对操作“AddArticle”的请求消息正文进行反序列化时出现错误。读取 XML 数据时,超出最大字符串内容长度配额 (8192)。通过更改在创建 XML 读取器时所使用的 XmlDictionaryReaderQuotas 对象的 MaxStringContentLength 属性,可增加此配额。 第 64 行,位置为 79。
主要是maxStringContentLength和maxReceivedMessageSize的设置会影响到消息的发送和接收,于是全部改为2MB大小,即2097152。客户端app.config修改:


openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00"
allowCookies="false" bypassProxyOnLocal="false" hostNameComparisonMode="StrongWildcard"
maxBufferSize="65536" maxBufferPoolSize="524288" maxReceivedMessageSize="2097152"
messageEncoding="Text" textEncoding="utf-8" transferMode="Buffered"
useDefaultWebProxy="true">

maxBytesPerRead="4096" maxNameTableCharCount="16384" />

realm="" />





服务端web.config修改: