<?xml version="1.0" encoding="utf-8"?><feed xmlns="http://www.w3.org/2005/Atom"><title type="text">博客园_老赵点滴 - 追求编程之美</title><subtitle type="text">先做人，再做技术人员，最后做程序员。打造国内最好的.NET技术博客。</subtitle><id>http://feed.cnblogs.com/blog/u/12973/rss</id><updated>2012-05-27T16:52:29Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><generator>feed.cnblogs.com</generator><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/"/><link rel="self" type="application/atom+xml" href="http://feed.cnblogs.com/blog/u/12973/rss"/><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2011/06/22/two-job-descriptions.html</id><title type="text">两则.NET高级技术人员的招聘信息</title><summary type="text">几小时前我在微博上发布了一条消息，表示我即将加入一家外企，而且完全是大家耳熟能详的IT公司之一，而且这个公司会让大家感到“意外”。于是大伙有猜微软的，也有猜Google，Apple，Oracle，HP等等，当然也有猜对的童鞋。在此公布答案，它便是传说中的IBM公司，我将在那里继续我的.NET程序员之旅。同时，我也希望可以找到一位同学可以帮助我目前在盛大创新院的项目继续良好地发展下去。</summary><published>2011-06-21T16:57:00Z</published><updated>2011-06-21T16:57:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/06/22/two-job-descriptions.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/06/22/two-job-descriptions.html"/><content type="html">&lt;p&gt;几小时前我在微博上&lt;a href="http://weibo.com/1560442584/eCyiyZRpjmq"&gt;发布了一条消息&lt;/a&gt;，表示我即将加入一家外企，而且完全是大家耳熟能详的IT公司之一，而且这个公司会让大家感到“意外”。于是大伙有猜微软的，也有猜Google，Apple，Oracle，HP等等，当然也有猜对的童鞋。在此公布答案，它便是传说中的IBM公司，我将在那里继续我的.NET程序员之旅。同时，我也希望可以找到一位同学可以帮助我目前在&lt;a href="http://blog.zhaojie.me/2010/01/1651772.html"&gt;盛大创新院&lt;/a&gt;的&lt;a href="http://note.sdo.com/"&gt;项目&lt;/a&gt;继续良好地发展下去。&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;关于IBM的职位&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;估计大伙会对“在IBM做.NET开发”这点有些疑惑，这里我来解释一下。大约一个月前我收到一封邮件，说IBM目前和&lt;a href="http://www.jpmorgan.com/"&gt;J.P. Morgan&lt;/a&gt;有个合作项目，后者希望建立一个离岸开发中心，由IBM负责招聘员工。这些人员单为J.P Morgan服务（我现场“考察”下来，的确是一个挂着“摩根大通”招牌的独立工作区域），并且会在合同里写明，如果J.P. Morgan满意的话，可以在两年后收编这个团队。那位仁兄说，这个职位主要有三个好处：&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;有机会进入投行，众所周知投行米多。 &lt;/li&gt;    &lt;li&gt;在IBM可以无视那伟大光荣正确的防火墙。 &lt;/li&gt;    &lt;li&gt;两年后有机会在香港工作。 &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;于是我就被打动了，表示可以尝试一下。经过好几轮笔试电话面现场面，我在两天前拿到了IBM的Offer，也是第一个通过的.NET技术人员。可以想象，如果没有J.P. Morgan，IBM也不会招聘.NET技术人员也不会来联系我；如果不是J.P. Morgan和香港，我也不会去尝试加入IBM，更何况要放弃很多东西，从上海千里迢迢前往深圳。我的目的其实也是希望几年后能够在香港工作，然后那时候也恰好可以生个娃什么的……创新院是个好地方，换工作也是个综合考虑的结果。&lt;/p&gt;  &lt;p&gt;那边也在努力招聘员工，虽然努力但也并没有放松要求，尤其是很难找到令人满意的.NET技术人员，因此他们也希望我可以推荐一些。这份.NET工作主要会用到的框架是WPF、WCF和少量ASP.NET，不过您没有接触过这些也没有关系，因为我也丝毫不懂WCF和WPF。笔试和面试时考察的大都是.NET的基础编程能力（CLR，BCL等等）以及计算机基础（例如操作系统与数据结构），还有便是架构、设计、排错以及解决问题的能力等等。这两天我也会单独成文记录一下这方面的情况。&lt;/p&gt;  &lt;p&gt;还有便是英语方面的要求。笔试都是英文，也有英文测试（可以查字典，但每道题都有时间限制）。电话面试和现场面试也都是从J.P. Morgan来的老外，除了您的名字以外听不到半个中文字。不过其实您也不用特别担心，我觉得只要您不是完全的哑巴英语，这方面应该都不会太大问题——要知道笔试面试都会围绕您最熟悉的技术方面展开。就拿我来说，语言方面的最大问题，是在跟老外HR用英语谈薪资时遇到的……&lt;/p&gt;  &lt;p&gt;这个职位在深圳。如果您对这个职位感兴趣，可以给我写封邮件说明一下您的个人情况，我可以考虑推荐给IBM的HR。&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;关于盛大创新院的职位&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blog.zhaojie.me/2010/01/1651772.html"&gt;盛大创新院&lt;/a&gt;是个很不错的地方，有丰厚的薪资，优秀的同事，可以说是个很理想的工作环境。如果您对互联网感兴趣，在那里你永远能发现和玩到各种有趣的东西。例如，下班前&lt;a href="http://weibo.com/dflyingchen"&gt;陈黎夫&lt;/a&gt;同学随手拍了一个同事的工作区：&lt;/p&gt; &lt;img src="http://ww2.sinaimg.cn/large/66573789jw1diesk5pqkzj.jpg" /&gt;   &lt;p&gt;您可以认出其中多少设备？MBP、PC，iMac，iPad 2，Moto Xoom，自然还有iPhone 4和安卓手机——完全没有刻意地收集拍摄，只是突然意识到原来已经有了那么多设备。&lt;/p&gt;  &lt;p&gt;这个工作台的主人和我在一个项目组，“&lt;a href="http://note.sdo.com/"&gt;麦库&lt;/a&gt;”。这个项目是我和其他两位同事从零开始创建的，可以说有着很深的感情。这个项目的发展状况也比较不错，我这次也是花了很长时间才下决心“撤退”。我选择IBM最重要的原因还是“香港”，如果不是这一点，从薪资待遇、工作环境，未来发展来考虑，我几乎不可能离开创新院。更何况去了IBM之后我几乎是转了半个行业，从互联网转向企业应用了。即便离开这个团队，我自然也希望这个项目可以继续良好的发展项目，因此在这里也在临走前为组内找到一个合适的人才。&lt;/p&gt;  &lt;p&gt;我希望您可以有良好的.NET以及ASP.NET编程基础，麦库使用的技术是.NET 4和ASP.NET MVC 3。后台使用CentOS上的MongoDB作为存储，因此也希望您最好有一些Linux和NoSQL方面的经验。在项目的制作过程中，我也总结出了一些开源项目，例如&lt;a href="https://github.com/JeffreyZhao/EasyMongo"&gt;EasyMongo&lt;/a&gt;和&lt;a href="https://github.com/JeffreyZhao/JsonMe"&gt;JsonMe&lt;/a&gt;，我希望您也能够跟我一起完善这些项目，让麦库发展得更好。&lt;/p&gt;  &lt;p&gt;我们在上海工作，如果您对此感兴趣，也请通过邮件联系我。&lt;/p&gt;&lt;p&gt;&lt;span style="color:red;"&gt;原文地址：&lt;/span&gt;《&lt;a href="http://blog.zhaojie.me/2011/06/two-job-descriptions.html"&gt;两则.NET高级技术人员的招聘信息&lt;/a&gt;》&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/2086449.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2011/06/22/two-job-descriptions.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2011/05/16/jscex-write-sexy-javascript-slide.html</id><title type="text">上周末Jscex项目介绍的幻灯片</title><summary type="text">上周末，在风景秀丽的浙江大学校园内，举行了NodeParty杭州站的活动。我在活动上结合Node.js项目对Jscex进行了简单介绍，包括其设计目的，设计原则，使用方式，高级模式，组成部分等等。在场的许多朋友也提出了不少问题，我也一一作了解答或是演示。总体感觉还算不错，毕竟是亲手编写的项目，对其各方面还是了然于胸的。在此发布演讲用的幻灯片，希望能给不在现场的同学带来一些帮助。</summary><published>2011-05-16T06:06:00Z</published><updated>2011-05-16T06:06:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/05/16/jscex-write-sexy-javascript-slide.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/05/16/jscex-write-sexy-javascript-slide.html"/><content type="html">&lt;p&gt;上周末，在风景秀丽的浙江大学校园内，举行了&lt;a href="http://cnodejs.org/blog/?p=956"&gt;NodeParty杭州站的活动&lt;/a&gt;。我在活动上结合&lt;a href="http://nodejs.org/"&gt;Node.js&lt;/a&gt;项目对&lt;a href="https://github.com/JeffreyZhao/jscex"&gt;Jscex&lt;/a&gt;进行了简单介绍，包括其设计目的，设计原则，使用方式，高级模式，组成部分等等。在场的许多朋友也提出了不少问题，我也一一作了解答或是演示。总体感觉还算不错，毕竟是亲手编写的项目，对其各方面还是了然于胸的。在此发布演讲用的幻灯片，希望能给不在现场的同学带来一些帮助。&lt;/p&gt;  &lt;div style="width: 425px" id="__ss_7976001"&gt;&lt;strong style="margin: 12px 0px 4px; display: block"&gt;&lt;a title="Jscex: Write Sexy JavaScript (中文)" href="http://www.slideshare.net/jeffz/jscex-write-sexy-javascript-cn"&gt;Jscex: Write Sexy JavaScript (中文)&lt;/a&gt;&lt;/strong&gt; &lt;iframe height="355" marginheight="0" src="http://www.slideshare.net/slideshow/embed_code/7976001" frameborder="0" width="425" marginwidth="0" scrolling="no"&gt;&lt;/iframe&gt;    &lt;div style="padding-bottom: 12px; padding-left: 0px; padding-right: 0px; padding-top: 5px"&gt;View more &lt;a href="http://www.slideshare.net/"&gt;presentations&lt;/a&gt; from &lt;a href="http://www.slideshare.net/jeffz"&gt;jeffz&lt;/a&gt; &lt;/div&gt; &lt;/div&gt;  &lt;p&gt;为了便于在国外社区推广，我也制作了英文版的幻灯片（事实上这是“原版”，中文版反而是会前临时决定翻译过来的），在此一并献上：&lt;/p&gt;  &lt;div style="width: 425px" id="__ss_7975832"&gt;&lt;strong style="margin: 12px 0px 4px; display: block"&gt;&lt;a title="Jscex: Write Sexy JavaScript" href="http://www.slideshare.net/jeffz/jscex-write-sexy-javascript"&gt;Jscex: Write Sexy JavaScript&lt;/a&gt;&lt;/strong&gt; &lt;iframe height="355" marginheight="0" src="http://www.slideshare.net/slideshow/embed_code/7975832" frameborder="0" width="425" marginwidth="0" scrolling="no"&gt;&lt;/iframe&gt;    &lt;div style="padding-bottom: 12px; padding-left: 0px; padding-right: 0px; padding-top: 5px"&gt;View more &lt;a href="http://www.slideshare.net/"&gt;presentations&lt;/a&gt; from &lt;a href="http://www.slideshare.net/jeffz"&gt;jeffz&lt;/a&gt; &lt;/div&gt; &lt;/div&gt;  &lt;p&gt;欢迎您使用Jscex，遇到什么问题也请及时与我联系。&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;GitHub（英文主站）：&lt;a href="https://github.com/JeffreyZhao/jscex"&gt;https://github.com/JeffreyZhao/jscex&lt;/a&gt; &lt;/li&gt;    &lt;li&gt;SNDACode（中文站）：&lt;a href="http://www.sndacode.com/projects/jscex"&gt;http://www.sndacode.com/projects/jscex&lt;/a&gt; &lt;/li&gt; &lt;/ul&gt;&lt;p&gt;原文地址：&lt;a href="http://blog.zhaojie.me/2011/05/jscex-write-sexy-javascript-slide.html"&gt;http://blog.zhaojie.me/2011/05/jscex-write-sexy-javascript-slide.html&lt;/a&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/2047559.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2011/05/16/jscex-write-sexy-javascript-slide.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2011/04/22/jscex-released-under-bsd-license.html</id><title type="text">Jscex使用BSD授权协议正式发布</title><summary type="text">这次打算把Jscex好好搞一下了，其实很少会有技术方面的障碍能“轮到”我们去突破，但我觉得Jscex的确有机会，HTML 5、Node.js各个都是红火的玩意儿。前几天我花了两个晚上用半生不熟的中式英语写了一篇自认为比较完整的说明文字放到了Github上的项目首页上，没想到几个小时后便收到了StratifiedJS（一个与Jscex目标有些类似的项目）作者的邮件，提到了一些关于StratifiedJS的事情。我向他咨询了StratifiedJS的某些细节问题，也向他简单介绍了Jscex的实现原理。如今Jscex已经使用BSD授权协议正式发布（中文站也会在近期推出），再进行一些细节上的优化便要开始作推广了。</summary><published>2011-04-21T16:18:00Z</published><updated>2011-04-21T16:18:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/04/22/jscex-released-under-bsd-license.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/04/22/jscex-released-under-bsd-license.html"/><content type="html">&lt;p&gt;这次打算把Jscex好好搞一下了，其实很少会有技术方面的障碍能“轮到”我们去突破，但我觉得Jscex的确有机会，HTML 5、Node.js各个都是红火的玩意儿。前几天我花了两个晚上用半生不熟的中式英语写了一篇自认为比较完整的说明文字放到了Github上的项目首页上，没想到几个小时后便收到了&lt;a href="http://onilabs.com/stratifiedjs"&gt;StratifiedJS&lt;/a&gt;（一个与Jscex目标有些类似的项目）作者的邮件，提到了一些关于StratifiedJS的事情。我向他咨询了StratifiedJS的某些细节问题，也向他简单介绍了Jscex的实现原理。如今&lt;a href="https://github.com/JeffreyZhao/jscex"&gt;Jscex已经使用BSD授权协议正式发布&lt;/a&gt;（中文站也会在近期推出），再进行一些细节上的优化便要开始作推广了。&lt;/p&gt;  &lt;p&gt;最近的一次优化便是去除不必要的Delay方法调用。Delay的目的是延迟某段代码的执行时间，确保它只会在合适的时间执行，这对于非“延迟”及有副作用的语言来说十分重要。在F#中Delay方法的签名如下（Jscex与之类似）：&lt;/p&gt;  &lt;span style="color: #006400"&gt;// async.Delay&lt;br/&gt;&lt;/span&gt;((&lt;span style="color: blue"&gt;unit &lt;/span&gt;-&amp;gt; Async&amp;lt;'a&amp;gt;) -&amp;gt; Async&amp;lt;'a&amp;gt;)&lt;p&gt;Delay函数可以不断嵌套，从效果说来讲不会有所区别，例如：&lt;/p&gt;builder.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;    &lt;span style="color: blue"&gt;return &lt;/span&gt;builder.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;        &lt;span style="color: blue"&gt;return &lt;/span&gt;builder.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;            &lt;span style="color: blue"&gt;return &lt;/span&gt;builder.Loop(...);&lt;br/&gt;        });&lt;br/&gt;    });&lt;br/&gt;});&lt;p&gt;上面这段代码和直接一个builder.Loop相比不会对结果产生任何影响，但是显然，从生成代码的整洁、美观程度（这涉及到可调试性）及性能都会有所损耗。之前的Jscex编译器会生成不必要的Delay（当然也不会有上面那么夸张），那是因为以前的代码生成器只是直接遍历从UglifyJS解析器那里获得的AST，以此来生成代码。新的编译器重新调整了结构和策略，会先将UglifyJS的AST转化为一个中间形式——我把它叫做Jscex AST，然后再让代码生成器从Jscex AST生成代码。新的生成器在工作时，会略过某些delay节点，直接从它的自节点中生成代码，以此达到去除不必要的Delay方法调用的目的。&lt;/p&gt;&lt;p&gt;举例来说，一个快速排序的Jscex函数：&lt;/p&gt;&lt;span style="color: blue"&gt;var &lt;/span&gt;bubbleSortAsync = eval(Jscex.compile(&lt;span style="color: maroon"&gt;&amp;quot;async&amp;quot;&lt;/span&gt;, &lt;span style="color: blue"&gt;function &lt;/span&gt;(array) {&lt;br/&gt;    &lt;span style="color: blue"&gt;for &lt;/span&gt;(&lt;span style="color: blue"&gt;var &lt;/span&gt;x = 0; x &amp;lt; array.length; x++) {&lt;br/&gt;        &lt;span style="color: blue"&gt;for &lt;/span&gt;(&lt;span style="color: blue"&gt;var &lt;/span&gt;y = 0; y &amp;lt; array.length - x; y++) {&lt;br/&gt;            &lt;span style="color: blue"&gt;var &lt;/span&gt;r = $await(compareAsync(array[y], array[y + 1]));&lt;br/&gt;            &lt;span style="color: blue"&gt;if &lt;/span&gt;(r &amp;gt; 0) {&lt;br/&gt;                $await(swapAsync(array, y, y + 1));&lt;br/&gt;            }&lt;br/&gt;        }&lt;br/&gt;    }&lt;br/&gt;}));&lt;p&gt;它会生成如下的代码（与&lt;a href="http://blog.zhaojie.me/2011/04/jscex-status-uglifyjs-parser-and-aot-compiler.html"&gt;之前的结果&lt;/a&gt;相比省去了一些Delay方法调用）：&lt;/p&gt;&lt;span style="color: blue"&gt;var &lt;/span&gt;bubbleSortAsync = (&lt;span style="color: blue"&gt;function &lt;/span&gt;(array) {&lt;br/&gt;    &lt;span style="color: blue"&gt;var &lt;/span&gt;$_builder_$ = Jscex.builders[&lt;span style="color: maroon"&gt;&amp;quot;async&amp;quot;&lt;/span&gt;];&lt;br/&gt;    &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Start(&lt;span style="color: blue"&gt;this&lt;/span&gt;, $_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;        &lt;strike&gt;&lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;/strike&gt;&lt;br/&gt;            &lt;span style="color: blue"&gt;var &lt;/span&gt;x = 0;&lt;br/&gt;            &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Loop(&lt;br/&gt;                &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                    &lt;span style="color: blue"&gt;return &lt;/span&gt;x &amp;lt; array.length;&lt;br/&gt;                },&lt;br/&gt;                &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                    x++;&lt;br/&gt;                },&lt;br/&gt;                $_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                    &lt;strike&gt;&lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;/strike&gt;&lt;br/&gt;                        &lt;span style="color: blue"&gt;var &lt;/span&gt;y = 0;&lt;br/&gt;                        &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Loop(&lt;br/&gt;                            &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                                &lt;span style="color: blue"&gt;return &lt;/span&gt;y &amp;lt; (array.length - x);&lt;br/&gt;                            },&lt;br/&gt;                            &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                                y++;&lt;br/&gt;                            },&lt;br/&gt;                            $_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                                &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Bind(compareAsync(...), &lt;span style="color: blue"&gt;function &lt;/span&gt;(r) {&lt;br/&gt;                                    &lt;strike&gt;&lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;/strike&gt;&lt;br/&gt;                                        &lt;span style="color: blue"&gt;if &lt;/span&gt;(r &amp;gt; 0) {&lt;br/&gt;                                            &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Bind(swapAsync(...), &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                                                &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Normal();&lt;br/&gt;                                            });&lt;br/&gt;                                        } &lt;span style="color: blue"&gt;else &lt;/span&gt;{&lt;br/&gt;                                            &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Normal();&lt;br/&gt;                                        }&lt;br/&gt;                                    });&lt;br/&gt;                                });&lt;br/&gt;                            }),&lt;br/&gt;                            &lt;span style="color: blue"&gt;false&lt;br/&gt;                        &lt;/span&gt;);&lt;br/&gt;                    });&lt;br/&gt;                }),&lt;br/&gt;                &lt;span style="color: blue"&gt;false&lt;br/&gt;            &lt;/span&gt;);&lt;br/&gt;        });&lt;br/&gt;    }));&lt;br/&gt;})&lt;p&gt;当然，Jscex还是有进一步优化的空间。例如包括保留“没有bind操作”的代码块，以及“嵌套Jscex函数”等等。最近一段时间应该会不断有一些更新。如果您在用JavaScript开发异步程序，也不妨一起来使用Jscex吧，它毫无疑问能显著改善您的编程生活。&lt;/p&gt;&lt;p&gt;&lt;font color="#ff0000"&gt;&lt;strong&gt;广告时间：&lt;/strong&gt;&lt;/font&gt;第四届nBazaar技术交流会将于4月23日（本周六）于畅星大厦（上海市浦东新区碧波路888号，地铁二号线张江高科站下，步行10分钟可达）副楼3楼会议厅举行，在此欢迎您的到来，请于下午1点前准时入场。没有报名的朋友也可以现场报名。由于领导支持，我们将在现场送出&lt;a href="http://bambook.sdo.com/"&gt;市场价999元的盛大Bambook&lt;/a&gt;一台作为幸运观众的礼品，此外图灵出版社也赞助了十几本图书将会送给积极发言的观众。更多详细信息请参考&lt;a href="http://nbazaar.org/"&gt;活动首页&lt;/a&gt;。&lt;/p&gt;&lt;p&gt;原文：&lt;a href="http://blog.zhaojie.me/2011/04/jscex-released-under-bsd-license.html"&gt;Jscex使用BSD授权协议正式发布&lt;/a&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/2024408.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2011/04/22/jscex-released-under-bsd-license.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2011/04/15/jscex-status-uglifyjs-parser-and-aot-compiler.html</id><title type="text">Jscex项目现状：UglifyJS解析器及AOT编译器</title><summary type="text">Jscex项目是我为了简化JavaScript异步的一个类库，支持任意JavaScript（ECMASCript 3）引擎。Jscex小巧而强大，可以极大地改善前端的AJAX及动画等场景的编程体验，同样也可以用在node.js进行服务器开发。从产生Jscex的想法到现在也有几个月的时间了，也一直想设法进行推广。在思考过程也发现了它在实际生产中可能会遇到的问题，于是前两个星期的主要工作，便是针对这些问题进行优化。首先我将Jscex的JavaScript分析器从Narcissus换成了UglifyJS，并基于node.js开发了一个简单的AOT编译器。接下来我也打算写个稍微详细一点的介绍，然后在国外社区看看反响如何。</summary><published>2011-04-14T18:09:00Z</published><updated>2011-04-14T18:09:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/04/15/jscex-status-uglifyjs-parser-and-aot-compiler.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/04/15/jscex-status-uglifyjs-parser-and-aot-compiler.html"/><content type="html">&lt;p&gt;&lt;span style="color: red"&gt;先来一段广告：&lt;/span&gt;&lt;a href="http://nbazaar.org/"&gt;第四届nBazaar技术交流会&lt;/a&gt;将于2011年4月23日举行。第四届交流会的形式将略作改变：除了三场演讲（Windows Phone 7、IDE插件开发、单点登陆解决方案设计与实现）之外，本次活动设有嘉宾互动环节，您将有机会和嘉宾就某些话题进行探讨。我们正在收集话题，也希望大家踊跃提问，具体信息详见&lt;a href="http://nbazaar.org/"&gt;http://nbazaar.org/&lt;/a&gt;。此外，nBazaar技术沙龙的邮件列表已经正式启用，所有用户也已添加完成（之前报名或参加过技术会议）。如果有任何疑问，请邮件至&lt;img class="embed" src="http://services.nexodyne.com/email/customicon/9xaGAYDnFdYrRqAdl1tTvrs%3D/Y4fIT8s%3D/000000/ffffff/000000/0/image.png" /&gt;。&lt;/p&gt;&lt;p&gt;&lt;a href="https://github.com/JeffreyZhao/jscex"&gt;Jscex&lt;/a&gt;项目是我为了简化JavaScript异步的一个类库，支持任意JavaScript（ECMASCript 3）引擎。Jscex小巧而强大，可以极大地改善前端的AJAX及动画等场景的编程体验，同样也可以用在&lt;a href="http://nodejs.org/"&gt;node.js&lt;/a&gt;进行服务器开发。从产生Jscex的想法到现在也有几个月的时间了，也一直想设法进行推广。在思考过程也发现了它在实际生产中可能会遇到的问题，于是前两个星期的主要工作，便是针对这些问题进行优化。首先我将Jscex的JavaScript分析器从&lt;a href="https://github.com/mozilla/narcissus"&gt;Narcissus&lt;/a&gt;换成了&lt;a href="https://github.com/mishoo/UglifyJS"&gt;UglifyJS&lt;/a&gt;，并基于node.js开发了一个简单的AOT编译器。接下来我也打算写个稍微详细一点的介绍，然后在国外社区看看反响如何。&lt;/p&gt;  &lt;p&gt;Jscex的本质是一个用JavaScript编写的JavaScript编译器，因此我需要一个JavaScript实现的JavaScript解析器。我起初&lt;a href="http://blog.zhaojie.me/2010/11/narcissus-javascript-parser.html"&gt;选择了著名的Narcissus项目&lt;/a&gt;，但由于它用到了&lt;a href="http://en.wikipedia.org/wiki/SpiderMonkey_(JavaScript_engine)"&gt;SpiderMonkey&lt;/a&gt;的一些扩展，最终我使用的其实是&lt;a href="http://www.neilmix.com/narrativejs/doc/"&gt;NarrativeJS&lt;/a&gt;中旧版的Narcissus代码。我一直在设法减小Jscex核心的体积及执行速度（毕竟一个重要的场景是浏览器端），再加上不是很喜欢旧版Narcissus代码的解析结果，于是我也在不断寻找它的替代品。前段时间我发现了UglifyJS这个JavaScript压缩器，它的解析器移植于&lt;a href="http://marijn.haverbeke.nl/parse-js/"&gt;parse-js&lt;/a&gt;项目，后者是一个用Common Lisp实现的类库，因此输出结构也十分简单，一个“表”而已，&lt;a href="http://blog.zhaojie.me/2011/04/uglifyjs-has-a-good-javascript-parser.html"&gt;执行速度也大大领先于Narcissus&lt;/a&gt;，体积也更小。于是我花了一个周末的时间将Jscex编译器改写为基于UglifyJS的实现。&lt;/p&gt;  &lt;p&gt;在改写过程中，我也同样考虑了目标代码在压缩后的体积。我使用&lt;a href="http://code.google.com/closure/compiler/"&gt;Closure Compiler&lt;/a&gt;的“高级”模式压缩代码，一般来说Closure Compiler的高级模式很破坏代码，我&lt;a href="http://blog.zhaojie.me/2011/04/compress-javascript-with-google-closure-compiler-in-advance-mode.html"&gt;使用了各种方式&lt;/a&gt;来保证压缩后的代码能够正确执行。目前，如果您要在项目中使用Jscex编写异步程序，需要依次加载以下三个文件（它们都在项目源码的bin目录中）：&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;uglifyjs-parser.min.js：UglifyJS解析器，大小20K，gzip后8K。 &lt;/li&gt;    &lt;li&gt;jscex.min.js：Jscex核心编译器，大小5.5K，gzip后1.8K。 &lt;/li&gt;    &lt;li&gt;jscex.async.min.js：Jscex异步核心类库，大小2K，gzip后0.9K。 &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;如果您觉得gzip后10K左右的体积还是有些大，那么也可以使用目前已经提供的AOT编译器——虽然AOT编译器的原始目的并不是为了减小体积。&lt;/p&gt;  &lt;p&gt;Jscex改善异步编程的原理，在于让程序员直接编写代码，使用普通的编程思路来实现算法，包括是用try...catch来捕获异常等等，而不会因为异步所需要的回调将代码拆得支离破碎。例如我们要实现冒泡排序算法的动画演示，也只需要使用传统编码方式实现算法即可：&lt;/p&gt;  &lt;span style="color: green"&gt;// 标准算法&lt;/span&gt;&lt;br/&gt;&lt;span style="color: blue"&gt;var &lt;/span&gt;bubbleSort = &lt;span style="color: blue"&gt;function &lt;/span&gt;(array) {&lt;br/&gt;    &lt;span style="color: blue"&gt;for &lt;/span&gt;(&lt;span style="color: blue"&gt;var &lt;/span&gt;x = 0; x &amp;lt; array.length; x++) {&lt;br/&gt;        &lt;span style="color: blue"&gt;for &lt;/span&gt;(&lt;span style="color: blue"&gt;var &lt;/span&gt;y = 0; y &amp;lt; array.length - x; y++) {&lt;br/&gt;            &lt;span style="color: blue"&gt;if &lt;/span&gt;(array[y] &amp;gt; array[y + 1]) {&lt;br/&gt;                swap(array, y, y + 1);&lt;br/&gt;            }&lt;br/&gt;        }&lt;br/&gt;    }&lt;br/&gt;}&lt;br/&gt;&lt;br/&gt;&lt;span style="color: green"&gt;// 演示动画&lt;/span&gt;&lt;br/&gt;&lt;span style="color: blue"&gt;var &lt;/span&gt;bubbleSortAsync = eval(Jscex.compile(&lt;span style="color: maroon"&gt;&amp;quot;async&amp;quot;&lt;/span&gt;, &lt;span style="color: blue"&gt;function &lt;/span&gt;(array) {&lt;br/&gt;    &lt;span style="color: blue"&gt;for &lt;/span&gt;(&lt;span style="color: blue"&gt;var &lt;/span&gt;x = 0; x &amp;lt; array.length; x++) {&lt;br/&gt;        &lt;span style="color: blue"&gt;for &lt;/span&gt;(&lt;span style="color: blue"&gt;var &lt;/span&gt;y = 0; y &amp;lt; array.length - x; y++) {&lt;br/&gt;            &lt;span style="color: blue"&gt;var &lt;/span&gt;r = $await(compareAsync(array[y], array[y + 1]));&lt;br/&gt;            &lt;span style="color: blue"&gt;if &lt;/span&gt;(r &amp;gt; 0) {&lt;br/&gt;                $await(swapAsync(array, y, y + 1));&lt;br/&gt;            }&lt;br/&gt;        }&lt;br/&gt;    }&lt;br/&gt;}));&lt;p&gt;Jscex.compile会解析代码，并生成异步代码，并交给eval来解释执行。bubbleSortAsync和其中调用的compareAsync（比较两个元素大小，并暂停10毫秒）和swapAsync（交换两个元素，绘图，并暂停20毫秒）都是异步方法。但是无论在编写和使用上，异步方法和同步算法几乎没有区别——唯一的区别便是$await语句必须单起一行。这个限制一是为了保证开发人员可以明确分清普通的JavaScript代码及异步方法调用，二便是为了简化编译器的实现。例如，“理想情况”下类似以下的代码也需要支持：&lt;/p&gt;f(g(1), $await(...))&lt;br/&gt;&lt;br/&gt;&lt;span style="color: blue"&gt;if &lt;/span&gt;(x &amp;gt; y &amp;amp;&amp;amp; $await(...)) { ... }&lt;p&gt;尤其是第二行代码，$await可能由于短路而根本不会执行。为此，Jscex要求开发人员明确编写这样的代码：&lt;/p&gt;&lt;span style="color: blue"&gt;var &lt;/span&gt;a1 = g(1);&lt;br/&gt;&lt;span style="color: blue"&gt;var &lt;/span&gt;a2 = $await(...);&lt;br/&gt;f(a1, a2);&lt;br/&gt;&lt;br/&gt;&lt;span style="color: blue"&gt;if &lt;/span&gt;(x &amp;gt; y) {&lt;br/&gt;    &lt;span style="color: blue"&gt;var &lt;/span&gt;flag = $await(...);&lt;br/&gt;    &lt;span style="color: blue"&gt;if &lt;/span&gt;(flag) { ... }&lt;br/&gt;}&lt;p&gt;我并不担心这会让开发人员编写代码时有所不便，事实上F#的&lt;a href="http://msdn.microsoft.com/en-us/library/dd233250.aspx"&gt;Async Workflow&lt;/a&gt;是有这般要求，我甚至敢保证&lt;a href="http://blog.zhaojie.me/2010/10/pdc2010-the-future-of-csharp-and-vb-by-anders-hejlsberg-1.html"&gt;未来C#的异步特性&lt;/a&gt;也是类似的设计。但是，JavaScript有个重要的特点：它在实际使用时往往会被压缩。如果仅仅是去除空白字符，那么Jscex自然还可以正常工作。但事实上现代的JavaScript压缩工具都会分析代码的语义，并重新生成体积更小的代码。例如之前的bubbleSortAsync经过压缩便会成为：&lt;/p&gt;&lt;span style="color: blue"&gt;var &lt;/span&gt;bubbleSortAsync=eval(Jscex.compile(&lt;span style="color: maroon"&gt;&amp;quot;async&amp;quot;&lt;/span&gt;,&lt;span style="color: blue"&gt;function&lt;/span&gt;(a){&lt;span style="color: blue"&gt;for&lt;/span&gt;(&lt;span style="color: blue"&gt;var &lt;/span&gt;b=0;b&amp;lt;a.length;b++)&lt;span style="color: blue"&gt;for&lt;/span&gt;(&lt;span style="color: blue"&gt;var &lt;/span&gt;c=0;c&amp;lt;a.length-b;c++){&lt;span style="color: blue"&gt;var &lt;/span&gt;d=$await(compareAsync(a[c],a[c+1]));d&amp;gt;0&amp;amp;&amp;amp;$await(swapAsync(a,c,c+1))}}))&lt;p&gt;试看d&amp;gt;0&amp;amp;&amp;amp;$wait(...)这段代码，完全就让Jscex无法工作了。为此，我为Jscex开发了AOT编译器（scripts目录下的jscexc.js及JscexExtractor.js文件），即在部署前便对代码进行编译并生成目标代码（之前是在运行时生成代码，即JIT编译）。AOT编译器同样使用JavaScript编写，使用node.js运行，这样便可以直接使用Jscex的编译器实现。与编译器核心不同，AOT编译器使用了最新版的Narcissus来解析代码，这是因为Narcissus能够提供更丰富的解析结果，我可以直接获得整个目标方法的起始和结束地址（不过有bug，我使用时绕开了），自然还包括原始代码，用起来十分方便。至于之前提到的依赖于SpiderMonkey扩展，体积较大，执行速度慢等缺点，对于AOT编译器来说便完全不是问题了。&lt;/p&gt;&lt;p&gt;Jscex的AOT编译器使用起来十分简单：&lt;/p&gt;node jscexc.js --input input_file --output output_file&lt;p&gt;例如，如果一个文件包含之前的bubbleSortAsync方法，那么经过AOT编译器之后，它的代码便会被替换成为：&lt;/p&gt;&lt;span style="color: blue"&gt;var &lt;/span&gt;bubbleSortAsync = (&lt;span style="color: blue"&gt;function &lt;/span&gt;(array) {&lt;br/&gt;    &lt;span style="color: blue"&gt;var &lt;/span&gt;$_builder_$ = Jscex.builders[&lt;span style="color: maroon"&gt;&amp;quot;async&amp;quot;&lt;/span&gt;];&lt;br/&gt;    &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Start(&lt;span style="color: blue"&gt;this&lt;/span&gt;, &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;        &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;            &lt;span style="color: blue"&gt;var &lt;/span&gt;x = 0;&lt;br/&gt;            &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Loop(&lt;br/&gt;                &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                    &lt;span style="color: blue"&gt;return &lt;/span&gt;x &amp;lt; array.length;&lt;br/&gt;                },&lt;br/&gt;                &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                    x++;&lt;br/&gt;                },&lt;br/&gt;                $_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                    &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                        &lt;span style="color: blue"&gt;var &lt;/span&gt;y = 0;&lt;br/&gt;                        &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Loop(&lt;br/&gt;                            &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                                &lt;span style="color: blue"&gt;return &lt;/span&gt;y &amp;lt; (array.length - x);&lt;br/&gt;                            },&lt;br/&gt;                            &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                                y++;&lt;br/&gt;                            },&lt;br/&gt;                            $_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                                &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Bind(compareAsync(...), &lt;span style="color: blue"&gt;function &lt;/span&gt;(r) {&lt;br/&gt;                                    &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Delay(&lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                                        &lt;span style="color: blue"&gt;if &lt;/span&gt;(r &amp;gt; 0) {&lt;br/&gt;                                            &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Bind(swapAsync(...), &lt;span style="color: blue"&gt;function &lt;/span&gt;() {&lt;br/&gt;                                                &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Normal();&lt;br/&gt;                                            });&lt;br/&gt;                                        } &lt;span style="color: blue"&gt;else &lt;/span&gt;{&lt;br/&gt;                                            &lt;span style="color: blue"&gt;return &lt;/span&gt;$_builder_$.Normal();&lt;br/&gt;                                        }&lt;br/&gt;                                    });&lt;br/&gt;                                });&lt;br/&gt;                            }),&lt;br/&gt;                            &lt;span style="color: blue"&gt;false&lt;br/&gt;                        &lt;/span&gt;);&lt;br/&gt;                    });&lt;br/&gt;                }),&lt;br/&gt;                &lt;span style="color: blue"&gt;false&lt;br/&gt;            &lt;/span&gt;);&lt;br/&gt;        });&lt;br/&gt;    });&lt;br/&gt;})&lt;p&gt;再进行压缩，便不会产生任何问题了。从表面看起来，编译后的Jscex代码体积大了不少，但是其中大部分为重复架子代码，压缩比例一般也会比较大。使用AOT编译后的代码有以下几个好处：&lt;/p&gt;&lt;ul&gt;  &lt;li&gt;经过JavaScript压缩器处理后也能正确执行。 &lt;/li&gt;  &lt;li&gt;运行时只需要加载一个极小的jscex.async.min.js文件（异步核心类库），gzip后大小不到1K。 &lt;/li&gt;  &lt;li&gt;由于代码在发布前生成，节省了JIT编译的开销。 &lt;/li&gt;&lt;/ul&gt;&lt;p&gt;在我个人看来，目前的Jscex已经可以在一些比较正式的场合中使用了。Jscex功能强大，实现小巧，能够与其它类库同时使用（它只会在全局对象上产生一个Jscex对象），接下来我也会为jQuery或MooTools等著名JavaScript框架/类库提供Jscex的绑定。在此也希望您可以实际使用一下Jscex项目，如果遇到问题请及时与我联系，我会给予您必要的支持。&lt;/p&gt;&lt;p&gt;原文：《&lt;a href="http://blog.zhaojie.me/2011/04/jscex-status-uglifyjs-parser-and-aot-compiler.html"&gt;Jscex项目现状：UglifyJS解析器及AOT编译器&lt;/a&gt;》&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/2016645.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2011/04/15/jscex-status-uglifyjs-parser-and-aot-compiler.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2011/02/10/piano-life-and-interests-driven-practice.html</id><title type="text">我们不是牛人，所以还是老老实实跟着兴趣走吧</title><summary type="text">前几天周筠老师写了篇博客，她认为兴趣十分重要，没有兴趣做不成事情。我对此十分同意，有亲身经历为证。更值得一提的是，这个亲身经历和技术或是职业方面的关系真不大，我对许多技术都感兴趣，一时还真难找出对比反差明显的东西。这次来说说我近几个月找到——或者说“找回”的兴趣，弹钢琴。在看来，这对我来说实在是“兴趣”的最佳例证了。</summary><published>2011-02-09T18:02:00Z</published><updated>2011-02-09T18:02:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/02/10/piano-life-and-interests-driven-practice.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/02/10/piano-life-and-interests-driven-practice.html"/><content type="html">&lt;p&gt;前几天周筠老师&lt;a href="http://blog.sina.com.cn/s/blog_6242cc7f0100oonu.html"&gt;写了篇博客&lt;/a&gt;，她认为兴趣十分重要，没有兴趣做不成事情。我对此十分同意，有亲身经历为证。更值得一提的是，这个亲身经历和技术或是职业方面的关系真不大，我对许多技术都感兴趣，一时还真难找出对比反差明显的东西。这次来说说我近几个月找到——或者说“找回”的兴趣，弹钢琴。在看来，这对我来说实在是“兴趣”的最佳例证了。&lt;/p&gt; &lt;a href="http://img.zhaojie.me/blog/piano-mbp-score.jpg" target="_blank"&gt;&lt;img src="http://img.zhaojie.me/blog/piano-mbp-score.jpg" width="450" /&gt;&lt;/a&gt;   &lt;p&gt;以上是我的装备，CASIO PX-130，相当著名的低端电钢琴。必要时前方放一纸箱，侧卧一个笔记本用于看谱，效果还算不错。对于在线的乐谱，我会把它截屏至PowerPoint中播放，再接个鼠标放地上，作为脚踏板用于翻页。电钢琴的声音和触键与真钢琴相比自然差一大截，但它的好处在于不会扰民，可以允许我半夜两三点尽情抒发情怀。等老子有钱了，一定搞间隔音好的屋子，放台斯坦威大三角，就像白天做梦时梦到的那种样子。&lt;/p&gt;  &lt;p&gt;就像大部分琴童那样，我从三四岁的时候开始学琴。当时家里花了大笔积蓄，也就是二十多年前的5000块钱，买了台现在也差不多值5000块钱的聂耳牌立式钢琴——话说这台钢琴已经破败不堪，许多键已经松弛疲软，延音踏板踩下去也没有延音效果了。过段时间打算找人来调试修理一下，然后给我妈用，她报名的老年班月底就要开始上课了。现在，再给这部老爷琴留个影吧。&lt;/p&gt; &lt;a href="http://img.zhaojie.me/blog/home-old-piano.jpg" target="_blank"&gt;&lt;img src="http://img.zhaojie.me/blog/home-old-piano.jpg" width="450" /&gt;&lt;/a&gt;   &lt;p&gt;还是和大部分琴童那样，我没能在七八岁时达到演奏肖练的水平，在那个时候钢琴给我带来的似乎只有痛苦。这么想吧，一个小破孩儿，每天在同学朋友都在疯跑玩耍的时候，被父母逼着坐在钢琴前进行枯燥的练习。此外身边同时常常伴随着耳光皮带拖鞋板，所以我如今皮糙肉厚反应灵敏也非一朝一夕之功。您可能会说弹钢琴件多么美妙的事情哪，但是对于对于当年的我，乃至绝大部分琴童来说，要“享受”钢琴几乎是件不可能的事情。&lt;/p&gt;  &lt;p&gt;首先，除了某些天才型选手，很难有琴童能在一开始的几年里有能力驾驭钢琴，因此只能不断地弹奏特定的简单作品或是练习曲等等。其次，即便有了一定程度的技术水平，也不一定能够真正体会到音乐的美妙。其中第二点原因尤其关键。对琴童来说，弹琴必然意味着考级，而即便是业余十级水平关注的还是技术——我并没有觉得这点有太大问题，因为钢琴演奏首先的确是个技术活。只可惜，在应试教育的一贯优秀传统下，可怜的琴童们被强迫不断地练习，只为“跑完”整首曲目，“体会”也好“精雕细琢”也罢就先放一边吧。&lt;/p&gt;  &lt;p&gt;这真的很讽刺。我前段时间翻出90年代初的考级用书，发现其中的确也包含了丰富的著名曲目，但是我当时完全没有意识到这一点。我只是个苦恼地一边弹琴一边哭哭啼啼的小破孩，时刻准备着偷懒。终于，在上初中以后，我以学业为由终止了钢琴演奏，直到几个月前，期间十几年没有摸过钢琴。&lt;/p&gt;  &lt;p&gt;一切是从我上大学开始改变的。不知道是什么原因，我第一次迷上古典音乐，后来总结了一下，至少听了千余盘CD，其中大部分是钢琴演奏。名家作品名家演绎几乎一个不拉，包括&lt;a href="http://www.naxosdirect.co.uk/Liszt-The-Complete-Piano-Music/title/CDS44501/98/"&gt;Leslie Howard在Naxos录制的李斯特大全集&lt;/a&gt;在内的许多整套录音都听了不止一遍，如肖邦舒伯特莫扎特贝多芬钢琴作品全集这样的“流行音乐”更是反复欣赏比较了好几个甚至十几个不同的版本。逐渐，我自然无法满足与单纯地“聆听”，而想亲手体会一下这些乐章的美妙。但是，几次重新接触琴键，唯一的感觉还是只有痛苦。这样的痛苦尤甚小时候初学钢琴时，因为我发现自己完全无法控制自己的双手，技术也已经远不如童年的巅峰时期，一些基本的音阶琶音和弦已经完全无法跑下，只想剁手。&lt;/p&gt;  &lt;p&gt;但是，我现在还是在坚持，因为王力宏有首歌唱得好：“欺骗世界、欺骗自己”。和小时候相比，我除了身高体重之外，最大的长进可能就是自欺欺人的功夫了。我时刻告诉自己，我还能够练好；只要坚持，终有一天我的手下也会出现名家的演绎水准。我时常也会翻出些著名的曲目，演奏其中一些不是太难的片段，自我安慰/享受一番，以免自己重新迷失在枯燥的基础练习中。如今，在我编程疲惫之余以弹琴作为放松，反之亦然；为了能够在午休的时候也能摸上琴键，我还自费购买了一台电钢琴放在公司。使用这种方式，我居然也硬扛下来贝多芬“悲怆”钢琴奏鸣曲的第一乐章——这也是促使我重新开始弹琴的曲目。当然，只能算是半熟不熟地跑下而已，毫无质量可谈。总而言之，如今我痛并快乐着。&lt;/p&gt;  &lt;p&gt;在钢琴演奏方面，可谓“兴趣”是我的唯一动力。小时候的技术比现在好得多，但却体会不到如今的快乐。其中唯一的区别就是兴趣了。我想，如果重来一次，我有机会可以引导小时候的我领悟一些简单的音乐之美，甚至只需要播放一些录音，可能一切就都会不一样了。说起来，我也打算引导（但不强迫）我的小孩学习钢琴，因为这的确是个美妙的事物。我们都不是&lt;a href="http://www.douban.com/group/topic/17278934/"&gt;郎朗般的牛人&lt;/a&gt;，还是跟着兴趣走下去吧。&lt;/p&gt;&lt;p&gt;没有兴趣？培养兴趣也要产生兴趣。“欺骗世界，欺骗自己”。&lt;/p&gt;&lt;embed src="http://www.tudou.com/v/vFMiG7X9K3A/&amp;amp;rpid=55026969/v.swf" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" wmode="opaque" width="480" height="400"&gt;&lt;/embed&gt;   &lt;p&gt;以上是我目前的水平（各位暂时先不要苛求电钢琴那单薄的录音效果了），一年后我们再来看。&lt;/p&gt;  &lt;p&gt;&lt;font color="#ff0000"&gt;广告时间：&lt;/font&gt;第三届nBazzar技术交流会所有演讲资料已经发布，&lt;a href="http://nbazaar.org/"&gt;欢迎关注&lt;/a&gt;。&lt;/p&gt;&lt;p&gt;原文：&lt;a href="http://blog.zhaojie.me/2011/02/piano-life-and-interests-driven-practice.html"&gt;我们不是牛人，所以还是老老实实跟着兴趣走吧&lt;/a&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/1950483.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2011/02/10/piano-life-and-interests-driven-practice.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2011/01/14/be-clear-with-language-spec-and-platform-implementation-dotnet-cross-platform.html</id><title type="text">分清“语言/规范”以及“平台/实现”，以及跨平台.NET开发</title><summary type="text">在许多年前，“语言”就等同于“平台”，例如C，C++以及最早的Ruby和Python等等。但是随着技术发展，出现了一些通用的平台，例如.NET和Java，逐渐这些平台上的语言也越来越多。再后来，某些语言在不同平台上的实现也越来越多，事情也变得有些复杂。技术在发展，但是从目前社区的讨论中，我发现许多朋友的观念还没有跟上。简单地说，如今的观念，一定要从“语言即平台”切换成“语言及平台”，当分清“语言”和“平台”这两个不同事物之后，许多问题才能讨论地清楚。而且，这点对于.NET程序员来说尤为重要，因为C#语言可以说是目前“平台”、“实现”最为广泛的“语言”之一了。</summary><published>2011-01-13T17:52:00Z</published><updated>2011-01-13T17:52:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/01/14/be-clear-with-language-spec-and-platform-implementation-dotnet-cross-platform.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/01/14/be-clear-with-language-spec-and-platform-implementation-dotnet-cross-platform.html"/><content type="html">&lt;p&gt;在许多年前，“语言”就等同于“平台”，例如C，C++以及最早的Ruby和Python等等。但是随着技术发展，出现了一些通用的平台，例如.NET和Java，逐渐这些平台上的语言也越来越多。再后来，某些语言在不同平台上的实现也越来越多，事情也变得有些复杂。技术在发展，但是从目前社区的讨论中，我发现许多朋友的观念还没有跟上。简单地说，如今的观念，一定要从“语言即平台”切换成“语言及平台”，当分清“语言”和“平台”这两个不同事物之后，许多问题才能讨论地清楚。&lt;/p&gt;  &lt;p&gt;例如我写过一个太监系列《&lt;a href="http://blog.zhaojie.me/2010/04/why-java-sucks-and-csharp-rocks-1-thoughts-and-goals.html"&gt;Why Java Sucks and C# Rocks&lt;/a&gt;》，其中谈的是C#和Java两个“语言”而不是两者的“平台”。编程“语言”其实是一种“规范”，它涉及了程序员在使用这门语言时的文本表现形式（这里暂不考虑其他形式的语言），而“平台”则包括对这个规范的“实现”（广义的“平台”还包括整个生态环境等等）。C#和Java分别处在各自的平台上，但许多语言其实是跨多种平台的。例如Python，Ruby，Scala，Clojure，JavaScript等等，数不胜数。同样，一个平台上也会出现多种语言。而且事实上，由于.NET和Java这样的平台越来越成熟，语言的设计及实现者也都越来越倾向于让语言运行在“某个平台”上。这么做可以尽可能地利用前人的成果，而不是什么都要自己从头做起。&lt;/p&gt;  &lt;p&gt;其实基本的原则就是这么简单，但是真正在考虑问题的时候，可能就不是那么容易了，我们必须时刻保持清晰地头脑。&lt;/p&gt;  &lt;p&gt;例如有个人说“C#比Java执行效率高（或低）”，这个说法是否正确？其实这种说法有很大问题。因为我们知道，在这里C#和Java都是“语言”，它们的执行环境CLI及JVM一样都是“规范”，但“执行效率”是一种表现，这和“实现”得如何有很大关系。例如，C#是运行在.NET平台还是Mono上（它们都是CLI规范的具体实现），Java是运行在JRockit还是Hotspot（前者是Oracle的JVM商业实现，后者是Sun的开源实现——当然现在也是Oracle的），亦或是Android的Dalvik上？很显然，不同实现之间的表现会有区别，不可一概而论，否则也不会出现JavaScript引擎的效率之争了。同理，有些人使用Hotspot上的Java性能来说明Java在Android上运行时的表现，这也是不对的——要知道Google在和Oracle的Java专利官司中不断强调Dalvik不是“Oracle那种Java”。作为结论，Java在Android上的表现的确不错，但论证方式也必须正确才行。&lt;/p&gt;  &lt;p&gt;当然，有时候“规范”也会影响到“实现”，例如一个动态分发的语言，其性能基本百分百不如在编译期绑定的静态语言。所以事情原本就是这么复杂，做一个思路清晰的程序员并不是件容易的事情。顺便一提，女人在这方面的头脑一般都比较清楚，她们一般都知道骑白马的不一定是王子，也有可能是唐僧。&lt;/p&gt;  &lt;p&gt;对于俗称“.NET程序员”的那一批人来说，分清“语言”和“平台”更是一件十分重要的事情，因为C#语言可以说是目前“平台”、“实现”最为广泛的“语言”之一了。之前我为InfoQ写过一篇文章，其中提到Mono的创始人&lt;a href="http://tirania.org/blog/"&gt;Miguel de Icaza&lt;/a&gt;给出的&lt;a href="http://www.infoq.com/cn/news/2010/11/mono-cross-platform"&gt;目前C#语言可执行平台的“不完全”列表&lt;/a&gt;，几乎覆盖了各种流行的操作系统及设备等等，例如：&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;Windows &lt;/li&gt;    &lt;li&gt;Mac OS &lt;/li&gt;    &lt;li&gt;Linux / BSD / Solaris &lt;/li&gt;    &lt;li&gt;Windows Phone，Android，iOS &lt;/li&gt;    &lt;li&gt;XBox 360，Wii，PS3 &lt;/li&gt;    &lt;li&gt;…… &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;因此就拿C#这一种语言来说，“实现”也会各自略有不同，这便是所谓的“配置（Profile）”。目前至少已经有这么多配置了：&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;.NET 4.0配置 &lt;/li&gt;    &lt;li&gt;Silverlight配置 &lt;/li&gt;    &lt;li&gt;Windows Phone 7配置 &lt;/li&gt;    &lt;li&gt;XBox360配置 &lt;/li&gt;    &lt;li&gt;Mono核心配置：与.NET配置相同，可以在Linux，MacOS X，Solaris，Windows和BSD里使用。 &lt;/li&gt;    &lt;li&gt;.NET Micro Framework &lt;/li&gt;    &lt;li&gt;Mono的iOS配置 &lt;/li&gt;    &lt;li&gt;Mono的Android配置 &lt;/li&gt;    &lt;li&gt;Mono的PS3配置 &lt;/li&gt;    &lt;li&gt;Mono的Wii配置 &lt;/li&gt;    &lt;li&gt;Moonlight配置（与Silverlight兼容） &lt;/li&gt;    &lt;li&gt;Moonlight扩展配置（Silverlight和完整的.NET 4 API） &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;“配置”之间的区别主要体现在执行环境的能力（例如iOS不支持运行时代码生成，因此支持AOT但不能JIT）以及类库的覆盖面上（例如XNA类库只存在于Windows Phone及XBox 360等游戏平台），不过它们终究实现了一个核心规范，因此我们可以说在不同平台上都可以“使用.NET进行开发”。&lt;/p&gt;  &lt;p&gt;Mono实在是一个了不得的作品，它让我知道了“跨平台原来可以这么做”。之前我也写过有关&lt;a href="http://blog.zhaojie.me/2010/06/is-cross-platform-a-lie-or-not.html"&gt;跨平台的问题&lt;/a&gt;，其中谈到在“客户端的跨平台一般都很难得到最佳的体验”，这个论点的最佳证明便是Java。但Mono走的却是另一条跨平台的道路，它在各平台上实现了核心的执行引擎和类库之外，解决“体验”的方式便是在各个平台上提供原生平台的绑定。这样无论是在Mac OS，iOS，Android上都可以得到原生应用的体验。&lt;/p&gt;  &lt;p&gt;我很奇怪为什么有些搞.NET的人一边说.NET的适用面太小，一边却忽视Mono的成果，在我看来这完全是“自作孽不可活”，我愈发觉得是否接受Mono是判断一个.NET程序员是否优秀的重要准则。其实Mono实在很火，因为他为广大.NET程序员扩展了工作领域，使用现有的知识来开发iOS等平台的应用程序，还可以共享代码，何乐而不为？前不久苹果发布了Mac上的App Store，于是MonoMac也立即推出了&lt;a href="http://tirania.org/monomac/archive/2011/Jan-10-1.html"&gt;面向AppStore的打包器&lt;/a&gt;，&lt;a href="http://twitter.com/#!/praeclarum"&gt;Frank Krueger&lt;/a&gt;也开始着手移植它的作品&lt;a href="http://icircuitapp.com/"&gt;iCircuit&lt;/a&gt;，&lt;a href="http://vimeo.com/18651634"&gt;成果显著&lt;/a&gt;。因此在我看来，这才是一个现代.NET程序员该有的工作台：&lt;/p&gt; &lt;a href="http://img.zhaojie.me/blog/morden-dotnet-prog-workbench.jpg" target="_blank"&gt;&lt;img src="http://img.zhaojie.me/blog/morden-dotnet-prog-workbench.jpg" width="450" /&gt;&lt;/a&gt;   &lt;p&gt;对于MonoTouch这样的新思路，带有疑惑是正常的。我也知道还有许多聪明人可以找到各种反对的理由。不管怎样，我现在这里随意列上几条吧：&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;有人说，用MonoTouch等.NET实现来做iOS开发“不正式”；我说，这个说法颇有“血统论”的意味，不过既然在Windows上用C++和Delphi都很正式，那么为什么在iOS上使用Objective-C才是正途？&lt;/li&gt;    &lt;li&gt;有人说，MonoTouch性能一定不如Objective-C好；我说，这是猜测，即使性能不如Objective-C，看看各种案例也知道这在实践中并不是问题（事实上MonoTouch的前身便是Unity3D对Mono的使用，而iOS上实在有太多游戏在使用Unity3D了）。&lt;/li&gt;    &lt;li&gt;有人说，MonoTouch或MonoDroid没有大公司支持，不靠谱；我说，您之前不是经常鄙视类似“开源没有微软靠谱”或是“微软开发人员只知道微软技术”这种说法的吗？&lt;/li&gt;    &lt;li&gt;有人说，用MonoTouch等于抛弃了CocoaTouch社区，出了问题都没人问；我说，MonoTouch的问题基本就是CocoaTouch的问题，MonoTouch的UI层就是CocoaTouch，有问题直接去CocoaTouch社区或CocoaTouch程序员，代码直接映射，类库直接使用。&lt;/li&gt;    &lt;li&gt;有人说，用MonoTouch的人不好招；我说，用C#、.NET的人比用Objective-C、Cocoa多太多了。给我一个熟练使用.NET和C#的人，三天上手，一周成为能够开发出成品的iOS开发者。&lt;/li&gt;    &lt;li&gt;有人说，难道就是为了用.NET所以用MonoTouch？我说，用MonoTouch/MonoDroid的好处很多，例如我可以在iOS、Android、Windows Phone甚至更多平台上共享UI以外的代码，并可以直接使用大量.NET上的类库——这点实在太方便了。不要问我为什么Android上不能使用Java类库，我只知道开发Andorid的同事发现SOAP访问类库没有，REST找不到好的，JSON支持也只有最原始的支持，于是痛苦万分。&lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;我还知道，这些说法依旧挡不住出现基于MonoDroid的&lt;a href="http://deltaengine.net/"&gt;DeltaEngine&lt;/a&gt;，这是个跨平台的游戏引擎，在Mono的支持下可以运行在Linux，MacOS X，iOS和Android上，在微软.NET支持下可以运行在XBox 360，Windows Phone 7自然还有普通的Windows系统上。在CES 2011上&lt;a href="http://blogs.nvidia.com/2011/01/nvidia-press-conference-ces-2011/"&gt;NVidia演示了一个游戏&lt;/a&gt;，&lt;a href="http://mobilebits.de/Blog/post/2011/01/05/Delayed-blogging-of-building-the-first-SoulCraft-Tech-Demo-version.aspx"&gt;Soul Craft&lt;/a&gt;，它运行在&lt;a href="http://blogs.nvidia.com/2011/01/lg-launches-optmus-2x-dual-core-superphone-powered-by-tegra-2/"&gt;LG Optimus 2X&lt;/a&gt;，这个游戏正是使用了DeltaEngine。&lt;/p&gt;  &lt;p&gt;对于我们来说，最大的限制其实还是眼界和思维，突破这一屏障也是我组织&lt;a href="http://nbazaar.org/"&gt;nBazaar技术沙龙&lt;/a&gt;的目的之一。本周六将会举办第三届nBazaar技术交流会，具体信息请访问&lt;a href="http://nbazaar.org/"&gt;http://nbazaar.org/&lt;/a&gt;。如果您还没有报名，也可以直接前来，也欢迎带上感兴趣的朋友或同事。根据以往的经验，场地就像乳沟，挤挤总是有的……&lt;/p&gt;  &lt;p&gt;原文：《&lt;a href="http://blog.zhaojie.me/2011/01/be-clear-with-language-spec-and-platform-implementation-dotnet-cross-platform.html"&gt;分清“语言/规范”以及“平台/实现”，以及跨平台.NET开发&lt;/a&gt;》&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/1935012.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2011/01/14/be-clear-with-language-spec-and-platform-implementation-dotnet-cross-platform.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2011/01/11/paid-for-app-hub-membership.html</id><title type="text">“花钱”购买App Hub Membership终于成功了</title><summary type="text">作为一个身在天朝的开发人员，要及早使用国外的服务总是一件杯具的事情，注册Windows Phone 7的App Hub Membership也不例外。不幸中的万幸，我工作于盛大创新院，这也是个奇妙的地方，身边的同事就有美国人，在他的帮助下，从提及注册信息到审核成功也只用了6、7个小时。说起来美国人在这方面的确占有十分重大的优势，不光是审核速度快（其他国家用户还需要等待GeoTrust主动联系，并提交更多信息，多花上2、3个工作日十分正常），连价格也便宜（年费只需99美金，前两天让荷兰的朋友帮忙注册需要99欧元），不得不长叹一声。</summary><published>2011-01-10T17:52:00Z</published><updated>2011-01-10T17:52:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/01/11/paid-for-app-hub-membership.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2011/01/11/paid-for-app-hub-membership.html"/><content type="html">&lt;p&gt;作为一个身在天朝的开发人员，要及早使用国外的服务总是一件杯具的事情，注册Windows Phone 7的App Hub Membership也不例外。不幸中的万幸，我工作于&lt;a href="http://blog.zhaojie.me/2010/01/1651772.html"&gt;盛大创新院&lt;/a&gt;，这也是个奇妙的地方，身边的同事就有美国人，在他的帮助下，从提及注册信息到审核成功也只用了6、7个小时。说起来美国人在这方面的确占有十分重大的优势，不光是审核速度快（其他国家用户还需要等待GeoTrust主动联系，并提交更多信息，多花上2、3个工作日十分正常），连价格也便宜（年费只需99美金，前两天让荷兰的朋友帮忙注册需要99欧元），不得不长叹一声。&lt;/p&gt;  &lt;p&gt;由于注册无法重现，我在这里只能简单描述一番。第一个环节是选择国家/地区，以及帐号类型等等，这与接下来的信用卡以及费用有关。接着则是各种信息，姓名电话地址邮编等等，也要和最后那张信用卡相符。之后则是提交信用卡的信息了，自不必说。值得一提的是，在提交信用卡的时候，网站总是说我的信息无法通过认证，几经尝试，最后使用我的美国VPS作代理才注册通过，看来是IP问题。通过之后，邮箱里会收到微软和GeoTrust发来的确认邮件，其中包含一个用于身份认证的链接，点开后则要求输入美国公民的各种信息，例如社会保障号等等。填写必需的字段，提交后便说“请等待处理”了。下午注册，晚上8点就收到邮件说成功了。总体而言，对于国内用户来说，App Hub Membership的“注册代理”比Android Market要宽松一些，后者似乎还要验证邮箱等等。&lt;/p&gt;  &lt;p&gt;App Hub包含了Windows Phone和XBox的开发和发布权限，我虽然也&lt;a href="http://blog.zhaojie.me/2011/01/htc-7-mozart-t8698-windows-phone-7-review-and-xbox-kinect.html"&gt;刚入手了XBox和Kinect&lt;/a&gt;，但我注册个App Hub完全就是为了Windows Phone上面的开发。诚然，如果不需要发布到Marketplace，使用微软提供的免费工具，&lt;a href="http://blog.zhaojie.me/2011/01/htc-7-mozart-t8698-windows-phone-7-review-and-xbox-kinect.html"&gt;再加上ChevronWP7的破解&lt;/a&gt;，早已足够了，但我还是选择了购买App Hub。这不到700块钱用于体验时代潮流，仔细想来也并不太多——当然这也涉及到个人的价值观。有些人认为4、500块钱的手机用来打电话发短信也已够用，而另一部分人（包括我）的看法是，几千块钱本身说起来也不能做太多事情，不如用于体会互联网时代的价值，这也是一种进修。所以我会较快购进Windows Phone、Kinect以及MonoTouch等等，即使从某些角度来看Windows Phone并非是一个适合国内用户的产品。&lt;/p&gt;  &lt;p&gt;以前我总是舍不得花钱，和许多朋友一样觉得这也很贵，那也很贵，于是也会用盗版等等。后来我和别人一起创业，虽然并非直接掌管资金，但也对于各种花销建立了一些概念。例如我知道了开一天公司需要多少钱，给员工交工资和福利、网站托管、流量购买需要多少钱，于是我就不会认为一套不到3000的MonoTouch，或是其他某个组件的商业授权有多么昂贵，因为它们的确可以为我省下更多的钱。从那时起，我会适当地选择开发效率更高的.NET平台加上价格便宜（3000左右）工作足够对硬件也十分宽松的Windows Web Server 2008，配合价格便宜选择丰富的*nix作后端存储。&lt;/p&gt;  &lt;p&gt;学会合理花钱的好处其实很多，首先我可以自豪地宣布，我已经不用盗版软件许多年，其次我学会通过花费现在的钱来提高自己或是节省精力，以便赚到更多的钱。我现在越来越喜欢适当使用一些收费的组件，因为我相信他们为了卖更多的授权，会不断提高自己的产品以及服务质量，这让我可以轻松不少。反之如果一切都由自己从头做起，可能大量的时间都耗费在一些无谓的细节上面才能得到与商业产品差不多的质量。时间往往比金钱更有价值。如果纠缠于那些细节无法让人提高，我情愿将时间用在自我学习、娱乐甚至是简单的休息上面。&lt;/p&gt;  &lt;p&gt;说起来购买App Hub Membership也是类似的道理，我不想把大量精力耗费在刷机、破解等方面（虽然我知道许多朋友乐在其中）。非官方的解锁方式总是无法让人安心，可能一次系统升级就让手机重新锁定了，于是又要折腾半天。现在则不然，即便微软接下来会升级Windows Phone，我也可以放心继续使用。因为我已经成为了正式的开发人员，XBox Live的Avatar都可以使用新装备了，哈哈。&lt;/p&gt;  &lt;p&gt;如今是程序员的黄金年代，移动平台和应用市场的兴起让我们可以比以往任何时候都轻松地赚取零花钱，甚至开创一番事业——当然前提是要有创意，这也是我最缺乏的。因此，如果您有什么需求或是点子，也不妨给我一些指点，我也有点实际内容可做。&lt;/p&gt;  &lt;p&gt;最后，依然来推广一下本周六即将举办的“&lt;a href="http://nbazaar.org/"&gt;第三届nBazaar技术交流会&lt;/a&gt;”，欢迎继续报名（近日将发出邀请函）。在今后的交流会上，我也会引入更多有趣的话题，例如移动平台的开发，甚至是与Kinect相关的话题。Kinect的确是神器，在我家已经成为父母每天必修的娱乐活动，可能我还会再买一套送给他们。&lt;/p&gt;&lt;p&gt;原文：《&lt;a href="http://blog.zhaojie.me/2011/01/paid-for-app-hub-membership.html"&gt;“花钱”购买App Hub Membership终于成功了&lt;/a&gt;》&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/1932475.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2011/01/11/paid-for-app-hub-membership.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2010/12/21/3rd-nbazaar-meeting-sign-up.html</id><title type="text">第三届nBazaar技术交流会开始报名</title><summary type="text">为了错开年底密集的技术会议，第三届nBazaar技术交流会（即前“盛大创新院赞助的.NET技术交流会”）将于2011年1月15日举行。第三届的交流会将继续以往四场高质量的演讲，这也是确定nBazaar名称之后的第一次活动，希望nBazaar能够真正成为“集市”般热闹的社区活动。从现在开始，nBazaar技术沙龙的相关信息将逐渐集中至独立域名中，欢迎关注。</summary><published>2010-12-20T16:49:00Z</published><updated>2010-12-20T16:49:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2010/12/21/3rd-nbazaar-meeting-sign-up.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2010/12/21/3rd-nbazaar-meeting-sign-up.html"/><content type="html">&lt;p&gt;为了错开年底密集的技术会议，第三届&lt;a href="http://nbazaar.org/"&gt;nBazaar技术交流会&lt;/a&gt;（即前“盛大创新院赞助的.NET技术交流会”）将于2011年1月15日举行。第三届的交流会将继续以往四场高质量的演讲，这也是确定nBazaar名称之后的第一次活动，希望nBazaar能够真正&lt;a href="http://blog.zhaojie.me/2010/10/status-of-iron-languages-and-nbazaar.html"&gt;成为“集市”般热闹的社区活动&lt;/a&gt;。从现在开始，nBazaar技术沙龙的相关信息将逐渐集中至独立域名中，欢迎关注。&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;志愿者招募&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;为了留下每次的活动资料，我们希望为每场演讲进行拍摄。如果您有这方面的志愿请发邮件至&lt;a href="mailto:jeffz@nbazaar.org"&gt;jeffz@nbazaar.org&lt;/a&gt;与我联系。&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;时间及议程安排&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;本次交流会首次向社区征集议题，我们在回复中挑选了三场：面向iPad平台的网站架构、面向企业应用语言ABAP、基于.NET的轻量级分布式框架，以及在创新院内部分享会上倍受好评的“分布式版本管理”话题。四位演讲者都是业界一线技术高手，四场话题都是他们的实战心得，希望能够让您满意。&lt;/p&gt;  &lt;table style="text-align: center" border="1" cellspacing="0" cellpadding="5"&gt;&lt;thead&gt;     &lt;tr&gt;       &lt;th&gt;时间&lt;/th&gt;        &lt;th&gt;议程&lt;/th&gt;     &lt;/tr&gt;   &lt;/thead&gt;&lt;tbody&gt;     &lt;tr&gt;       &lt;td&gt;12:30 ~ 13:00&lt;/td&gt;        &lt;td&gt;签到&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td&gt;13:00 ~ 14:00&lt;/td&gt;        &lt;td&gt;针对iPad平台的高性能网站架构&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td&gt;14:00 ~ 14:10&lt;/td&gt;        &lt;td&gt;短休&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td&gt;14:10 ~ 15:10&lt;/td&gt;        &lt;td&gt;分布式版本管理&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td&gt;15:10 ~ 15:40&lt;/td&gt;        &lt;td&gt;茶歇&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td&gt;15:40 ~ 16:40&lt;/td&gt;        &lt;td&gt;企业开发领域的语言特性&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td&gt;16:40 ~ 16:50&lt;/td&gt;        &lt;td&gt;短休&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td&gt;16:50 ~ 17: 50&lt;/td&gt;        &lt;td&gt;使用.NET构建轻量级分布式框架&lt;/td&gt;     &lt;/tr&gt;   &lt;/tbody&gt;&lt;/table&gt;  &lt;p&gt;&lt;strong&gt;演讲内容&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;以下为是四场演讲的信息：&lt;/p&gt; &lt;a href="http://nbazaar.org/_media/%E8%AE%B2%E5%B8%88/mashijie-450x600.jpg" target="_blank"&gt;&lt;img class="floatRight" src="http://nbazaar.org/_media/%E8%AE%B2%E5%B8%88/mashijie-450x600.jpg" height="150" /&gt;&lt;/a&gt;   &lt;p&gt;&lt;strong&gt;针对iPad平台的高性能网站架构&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;讲师：&lt;/strong&gt;马士杰，EF英孚教育，Tech Leader。关注高性能网站架构和前沿技术在线教育领域的应用创新。曾经重点关注的技术领域包括ORM，AOP和SOA。近期的关注重点是针对移动平台的高性能网站架构。&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;简介：&lt;/strong&gt;iPad的横空出世，几乎使得2010年成为全球IT领域的平板电脑之年。摩根士丹利发布的《移动互联网报告》认为移动互联网周期是50年来的第5个新技术周期，以Apple的iPad平板电脑和手机上网为代表的移动互联网的增长势头将超过电脑上网。本演讲的目的是和听众分享本人近一年在针对iPad平台的高性能网站架构方面的一些经验，包括兼容不同平台桌面和移动浏览器的表现层设计模式，针对iPad Mobile Safari浏览器的Web页面性能优化和iPad本地程序和在线网站的无缝整合等。&lt;/p&gt; &lt;a href="http://nbazaar.org/_media/%E8%AE%B2%E5%B8%88/lijun-400x600.jpg" target="_blank"&gt;&lt;img class="floatRight" src="http://nbazaar.org/_media/%E8%AE%B2%E5%B8%88/lijun-400x600.jpg" height="150" /&gt;&lt;/a&gt;   &lt;p&gt;&lt;strong&gt;分布式版本管理&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;讲师：&lt;/strong&gt;李骏，中国第一批J2EE开发者，大中华区第一个中间件和SOA领域的Oracle ACE Director。有着10年以上企业级应用系统咨询/设计/实施以及软件公司管理经验的行业老兵，因为喜欢创造能影响人们日常生活的东西，所以来到盛大创新院，梦想能找到“正确的把软件作成业务”的方法。&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;演讲：&lt;/strong&gt;源代码和其它软件工程产物的版本管理，是每个开发者每天都会碰到的问题，经过数十年的发展，CVS、SVN等上一代版本管理系统中的一些问题，催生着新的技术及其应用模式。在过去几年中以Git和Mercurial为代表的分布式版本管理工具有了较大的发展，已经基本具备了普及应用的基础。这里将介绍分布式版本管理欲解决的问题及其关键价值，并以Mercurial为例介绍具体使用的方法和流程。&lt;/p&gt; &lt;a href="http://nbazaar.org/_media/%E8%AE%B2%E5%B8%88/shijianzhuo-576x432.jpg" target="_blank"&gt;&lt;img class="floatRight" src="http://nbazaar.org/_media/%E8%AE%B2%E5%B8%88/shijianzhuo-576x432.jpg" height="150" /&gt;&lt;/a&gt;   &lt;p&gt;&lt;strong&gt;企业开发领域的语言特性&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;讲师：&lt;/strong&gt;师建茁（Amos Shi），GRC软件工程师，SAP Labs China。中学时代在 286、486 系统上学会了 12个DOS内部命令，若干外部命令；使用QBasic开始程序生涯，半夜起来在图画本上设计流程图。后来跟着谭浩强的C语言课本和Borland的TC 2.0进入 Windows CMD 时代，后来有了 C++、Delphi、Python、.NET、Java，排名不分先后，意识到语言并非那么重要； 直到有一天，遇到了 ABAP，以及 Web Dynpro，意识到，对于优秀的软件，高级语言特性还是有所帮助的。2007年加入SAP Labs China，从事GRC软件产品的研发。日常工作涉及GRC 的多个部分。&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;演讲：&lt;/strong&gt;作为一个程序员，在加入SAP之前用过一些各种各样流行的技术来写软件产品，到了Labs之后开始使用一种不广为所知的ABAP语言开发GRC软件产品。在学习和使用ABAP语言的过程中，经常会有类似“啊！对了，以前我就想过应该是这样的”、“是的！就是应该这样集成！”、“本来嘛，已经有足够的信息在那里了，她就是应该自动生成，一行代码都不应该写！”这样的感叹，对很多特性总是有相见恨晚的感觉。回想到以前的产品开发中遇到的种种问题，觉得如果这些特性已经有了的话，可以大大提高效率，降低错误。后来逐渐接触到其后面的NetWeaver平台，和Web Dynpro之后，更觉得这一整套东西为企业应用进行了精心设计。又回想起了“程序员如何在非洲捕捉大象？”这个经典笑话，哈哈哈哈。如果你要开发企业应用的话，确实有很多东西可以从这里借鉴，希望对你能有所裨益。&lt;/p&gt; &lt;a href="http://nbazaar.org/_media/%E8%AE%B2%E5%B8%88/qiaojie-400x622.jpg" target="_blank"&gt;&lt;img class="floatRight" src="http://nbazaar.org/_media/%E8%AE%B2%E5%B8%88/qiaojie-400x622.jpg" height="150" /&gt;&lt;/a&gt;   &lt;p&gt;&lt;strong&gt;使用.NET构建轻量级分布式框架&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;讲师：&lt;/strong&gt;乔捷，瓦格纳比罗舞台系统公司，技术主管。热爱技术，对多种技术领域都有涉猎，目前主要从事剧院舞台控制系统和虚拟舞台系统的设计和研发工作，主要涉及到分布式系统、实时控制系统、虚拟现实系统、3D实时/离线渲染等技术领域。主要的编程语言为C++/C#/JavaScript，喜爱.NET技术，最近比较关注分布式计算和并行计算技术，并已在实际的项目应用中取得了初步的成功。&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;演讲：&lt;/strong&gt;分布式系统的设计和构建是一项复杂多变而很具有挑战性的任务，设计的目标包括服务的伸缩性、可靠性、安全性、实时性、性能、容错等多个方面，同时还可能需要面对各种异构平台的集成和整合。目前市面上已有的分布式框架包括.NET提供的Remoting和WCF，都不能很好的满足上述所有的这些需求。因此，打造一套轻量级的、高度可定制的、符合自身项目需求的分布式框架变得很有现实意义。本演讲就来讨论如何应用.NET技术构建这样一套轻量级的分布式框架。&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;地点&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;本次交流会举办地为&lt;strong style="color: red"&gt;上海市浦东新区碧波路888号畅星大厦&lt;/strong&gt;（地铁二号线张江高科站下，步行10分钟可达）3楼会议厅，地图如下：&lt;/p&gt; &lt;a href="http://img.zhaojie.me/blog/snda-dotnet-conf/changxing-map.png"&gt;&lt;img src="http://img.zhaojie.me/blog/snda-dotnet-conf/changxing-map.png" width="400" /&gt;&lt;/a&gt;   &lt;p&gt;鸟瞰图：&lt;/p&gt; &lt;a href="http://img.zhaojie.me/blog/snda-dotnet-conf/changxing-hybrid.jpg"&gt;&lt;img src="http://img.zhaojie.me/blog/snda-dotnet-conf/changxing-hybrid.jpg" width="400" /&gt;&lt;/a&gt;   &lt;p&gt;畅星大厦外观：&lt;/p&gt; &lt;a href="http://img.zhaojie.me/blog/snda-dotnet-conf/changxing-building.jpg"&gt;&lt;img src="http://img.zhaojie.me/blog/snda-dotnet-conf/changxing-building.jpg" width="400" /&gt;&lt;/a&gt;   &lt;p&gt;会场实景照片：&lt;/p&gt; &lt;a href="http://img.zhaojie.me/blog/snda-dotnet-conf/changxing-room.jpg"&gt;&lt;img src="http://img.zhaojie.me/blog/snda-dotnet-conf/changxing-room.jpg" width="400" /&gt;&lt;/a&gt;   &lt;p&gt;会场容量可以容纳超过200人，希望到时候不会显得太过空旷。:)&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;报名信息&lt;/strong&gt;&lt;/p&gt; &lt;img src="http://img.zhaojie.me/blog/snda-dotnet-conf/sign-up-now.jpg" /&gt;   &lt;p&gt;本次交流会&lt;a href="http://diaochapai.com/survey518744"&gt;现已开始报名，请填写报名表&lt;/a&gt;。&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/1911929.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2010/12/21/3rd-nbazaar-meeting-sign-up.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2010/11/05/silverlight-and-microsoft-technology-2-microsoft-technology-and-how-to-learn.html</id><title type="text">Silverlight与微软技术（下）：微软技术与技术学习</title><summary type="text">经常听到有人说微软的技术变化太快，持续性不好，让程序员追得很累。这种观点在微软技术社区内部和外部都有出现，似乎是一个不争的事实。但从我追随.NET平台这近十年的时间里，我并没有明显的感觉。微软的技术的确很多，但至少在.NET领域过渡性做的非常好，我没有任何疲惫之感。微软技术开拓了我的眼界，让我在微软内外许多技术方面越来越少有“新奇”的感觉，一切都是那么自然和稳妥。我现在就来仔细谈谈我在学习微软技术方面的经验与感受。</summary><published>2010-11-04T16:17:00Z</published><updated>2010-11-04T16:17:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2010/11/05/silverlight-and-microsoft-technology-2-microsoft-technology-and-how-to-learn.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2010/11/05/silverlight-and-microsoft-technology-2-microsoft-technology-and-how-to-learn.html"/><content type="html">&lt;p&gt;经常听到有人说微软的技术变化太快，持续性不好，让程序员追得很累。这种观点在微软技术社区内部和外部都有出现，似乎是一个不争的事实。但从我追随.NET平台这近十年的时间里，我并没有明显的感觉。微软的技术的确很多，但至少在.NET领域过渡性做的非常好，我没有任何疲惫之感。微软技术开拓了我的眼界，让我在微软内外许多技术方面越来越少有“新奇”的感觉，一切都是那么自然和稳妥。我现在就来仔细谈谈我在学习微软技术方面的经验与感受。&lt;/p&gt;&lt;p&gt;我一直对编程有浓厚的兴趣，上大学前在编程方面的经验主要来自于信息学竞赛，此外就是用一些VB或是Delphi写一些小程序，拿去参加高中的一些名不见经传的小比赛，那点小名次，小打小闹，仅此而已。到了大学里，学习（或自学）了Java，少许LISP，数据结构与算法，操作系统，计算机体系结构，计算机网络，编译原理等最传统的科班课程，但似乎学的不太好，现在想来颇是后悔。此外学过几次C++，但智商有限，几次下来都没有坚持到底，现在也忘得差不多了。可以这么说，我的专业程序员生涯的成长离不开微软与.NET。当然，我热爱各种技术，各方面也学习了很多。我接下来也会说到，技术本就不应该分为“微软”与“非微软”两个部分。&lt;/p&gt;&lt;p&gt;我在大学的时候学习和使用的是Java，也用Java参与了一些奇怪的“企业项目”——如上海海关进出口检疫局的什么什么系统（不过那时候我也已经开始接触C# 1.0和.NET了）。后来由于去了微软，自然全面转向.NET。我在微软只待了一年半，但这一年半给我最大的帮助就是让我开阔了眼界，知道技术领域有多么广阔，知道学校里了解的一些东西是多么的不靠谱。可以说在微软的这段时间对我来说是个突破，从那时起我就对各种技术都抱有强烈的兴趣。&lt;/p&gt;&lt;p&gt;有人说微软技术发展太快，且时常淘汰很多东西，对此我并不赞同太多。我接触到的说微软技术变化太快的同学，大都是老程序员，他们因为微软将重心放在了.NET上，导致了COM等技术运用场景减少，于是颇为不满。他们时不时“预言”微软以后会抛下.NET，虽然.NET已经发展了近10年，且力度越来越大，所以我称这种“预言”是一种FUD。我是从.NET 1.x/C# 1.0学起的，一直到现在，无论是语言还是基础类库，一切都良好过渡。您在C# 1.0里学到的东西，有哪些在C# 4.0里消失了么？您写的ASP.NET 2.0程序，直接无痛升级到ASP.NET 3.5——这是&lt;a href="http://www.dianping.com/"&gt;大众点评网&lt;/a&gt;的架构师&lt;a href="http://blog.zhaojie.me/2010/06/first-snda-dotnet-conference-videos.html"&gt;在分享会上提到的&lt;/a&gt;，它的应用规模及复杂度不低于您的项目吧？微软是个对企业应用有许多投入的公司，在过渡和兼容性方面必须做到几乎百分百的保证，这些经验也总结成册，例如获得Jolt大奖的《&lt;a href="http://www.amazon.com/Framework-Design-Guidelines-Conventions-Libraries/dp/0321246756"&gt;Framework Design Guildline&lt;/a&gt;》，其中不断强调的一点，就是在设计时对兼容性方面的考虑。&lt;/p&gt;&lt;p&gt;在兼容性方面，某些技术领域的程序员就有更高的“觉悟”。例如Python 3.0成为了一门不兼容Python 2.x的语言，Rails 3.0也不兼容Rails 2.x。我咨询过几个Rails程序员对此的看法，他们观点十分一致，那就是对Rails 3.0很有好感，至于以前的项目，“没有必要从2.x升级到3.0啊！”。我也支持他们的看法，如果您不喜欢C#里的新特性，那就不用那些特性。如果您不喜欢新框架的功能，那就继续用原来的方式做事情，新的框架也不会对您有影响。我支持Python和Rails项目发展的决定，他们为了前进抛下一些历史包袱，我可以理解。这并不会影响我对Python和Rails的喜爱，它们依然是十分优秀的语言和框架。&lt;/p&gt;&lt;p&gt;有人说，微软会淘汰技术，那么对这些技术的投资不就失效了吗？这方面我认为自己有很好的发言权。我&lt;a href="http://blog.zhaojie.me/2009/10/talk-about-blogging.html"&gt;之前也提到过&lt;/a&gt;，我在社区里的“声望”是靠ASP.NET AJAX积累起来的。但是现在ASP.NET AJAX似乎慢慢地淡出了人们的视线，那么我的投资失败了吗？完全没有，确切地说简直太成功了。ASP.NET AJAX覆盖了浏览器端的JavaScript开发，以及后台对ASP.NET WebForms页面模型的扩展，当然，还包括两者的交互。我一直认为UpdatePanel是前后端交互的经典之作，它通过在前端页面的hook，以及对后端WebForm模型输出的捕获，做到了非常透明的AJAX效果，只可惜由于项目分工，前端开发人员大都喜欢手写的纯客户端模型，因此UpdatePanel不太受人待见。我读过了ASP.NET AJAX的前台代码，由此全方面了解了JavaScript语言和许多前端开发的技术和技巧。我读过了ASP.NET AJAX的后端代码，由此我了解了一个JSON序列化框架可以如何实现出来，体会到了ASP.NET及其WebForms模型丰富灵活的内涵。从ASP.NET AJAX开始，我可以自豪地认为自己“精通”了ASP.NET，对它各方面的扩展可谓如鱼得水。例如，我可以轻易写出一个&lt;a href="http://blog.zhaojie.me/2008/05/build-component-to-upload-file-in-updatepanel.html"&gt;UpdatePanel上传文件&lt;/a&gt;，或是&lt;a href="http://blog.zhaojie.me/2008/04/try-to-build-an-updatepanel-for-asp-dot-net-mvc.html"&gt;ASP.NET MVC中UpdatePanel&lt;/a&gt;的原型，虽不至于成为一个通用的组件及解决方案，但是对于自己项目本身已完全够用（我几乎没有纯“玩闹”而写的扩展，都是源自于项目本身）。后来微软出了ASP.NET MVC，我花两天时间扫视一遍它的源代码，也已经基本掌握了它的原理，使用方式，扩展也罢，一切都那么顺其自然。例如Rails是个优秀的Web框架，包含许多对实际生产非常有效率的特性，但是我在看了这些特性的使用方式之后，几乎都可以立即想象出它在ASP.NET里的实现方式，就例如&lt;a href="http://blog.zhaojie.me/2009/09/aspnet-mvc-fragment-cache-1.html"&gt;表现层的片段缓存&lt;/a&gt;那样。&lt;/p&gt;&lt;p&gt;我一直强调，我并不了解所有的.NET相关的框架，但就我所了解的.NET技术而言，它们都有这样的特征：过渡性很好，自然地，有底蕴的发展。就拿C#来说，C# 1.0中创造了“委托”这个函数的一等公民类型，而在C# 2.0里引入了匿名方法，C# 3.0里强化了函数式编程的理念，成就了这一到目前为止最为经典的C#语言。C# 3.0中引入了Monadic的LINQ语法，几年下来基于LINQ发展了太多太多，如PDC 09中的&lt;a href="http://blog.zhaojie.me/2010/09/async-programming-and-reactive-framework.html"&gt;LINQ to Observable&lt;/a&gt;，PDC 10上的&lt;a href="http://player.microsoftpdc.com/Session/bfa72307-6534-41ad-bcf7-0f4fb9280515"&gt;LINQ to Azure&lt;/a&gt;。社区里如围绕NHiberante的贡献更是数不胜数。微软技术在我看来是十分领先的，这个领先并不一定指它在计算机科学上的创新和突破，而是指它对于这些经典理念与工业生产相结合方面的超前。可能它不如某些朋友心目中LISP那般博大精深，但可以说更直接地在让我在实际生产中体会到了经典的魅力。&lt;/p&gt;&lt;p&gt;这样的“领先”给我带来了许多乐趣，也让我慢慢难以从其他技术上感到“惊喜”。例如，一个Java程序员转到Python以后，会感觉生产力有了显著的提高，但就我来说，&lt;a href="http://blog.zhaojie.me/2009/02/1381867.html"&gt;相当部分的生产力在C#中都有体现&lt;/a&gt;，我不会以为生产力低下是“静态语言”的关系。同样，我最近在关注iOS及Mac OS方面的应用程序开发，接触了一些Objective-C，发现它的block就相当于.NET中的委托，而在09年随Snow Leopard引入的block的支持语法早在C# 2.0中就由“匿名方法”特性实现了，更不说C# 3.0在这方面有更进一步的发展。同样，我阅读了&lt;a href="http://developer.apple.com/library/mac/#documentation/Performance/Reference/GCD_libdispatch_Ref/Reference/reference.html"&gt;GCD（Grand Central Dispatch）的文档&lt;/a&gt;之后，发现它和.NET 4.0中的TPL（Task Parallel Library，任务并行库）解决的是相同的问题，其实现思路也有许多相同之处，例如都是主要通过描述“任务”（如任务内容及依赖关系）来避免程序员直接使用线程，避免复杂的同步问题，并由系统来负责对任务的调度。有时在推特上，我时常可以看到一些Cocoa的开发者津津乐道于block及GCD对于并行开发所带来的诸多便利——于是我想，这个早已不该是新闻了嘛。我现在还知道&lt;a href="http://blog.zhaojie.me/2010/10/pdc2010-the-future-of-csharp-and-vb-by-anders-hejlsberg-1.html"&gt;未来C#还会在这方面有更多便利&lt;/a&gt;，它在Anders Hejlsberg的带领下再一次走到了领先的位置。&lt;/p&gt;&lt;p&gt;微软的技术大都容易入门，但这并不影响这些技术深厚的底蕴，您在学习时应该了解这种底蕴。例如，您在学习C#时，不应该只关注它的表面特性，而要知道“为什么Anders会设计这样的特性”。我认为，一个优秀的C#程序员应该对函数式编程有一定程度的理解。当您学习&lt;a href="http://msdn.microsoft.com/en-us/devlabs/ee794896.aspx"&gt;Reacive Framework&lt;/a&gt;时，应该顺便去了解一下响应式编程。同样，我看到社区里有一些关于TPL的文章，但认为它们还是没有把握到精髓。事实上这些精髓都不是秘密，微软对各种原理几乎都不做保留。例如微软免费提供了《&lt;a href="http://parallelpatterns.codeplex.com/"&gt;Patterns for Parallel Programming&lt;/a&gt;》等资料，详细解释了并行编程中的诸多模式，以及它们在TPL（C#与VB）或是F#中的实现方式，这些都体现了微软在设计这些语言或类库时的思路。微软在构建这些技术的时候并非无中生有，都是事先设计好使用场景的。例如用Task应对任务并行，用PLINQ应对数据并行，毫不草率，堪称经典。此外，TPL的设计者&lt;a href="http://www.bluebytesoftware.com/blog/Default.aspx"&gt;Joe Duffy&lt;/a&gt;是业界大牛，他写过一本《&lt;a href="http://www.amazon.com/Concurrent-Programming-Windows-Joe-Duffy/dp/032143482X"&gt;Concurrent Programming on Windows&lt;/a&gt;》，描述了大量关于TPL的实现细节，例如无锁数据结构的编写方式，Work Stealing，如何改善&lt;a href="http://blog.zhaojie.me/2009/01/system-architecture-and-program-performance.html"&gt;局部性&lt;/a&gt;等等。您了解了这些内容以后，我想GCD对您来说可能也只是换套API而已，应该也不算是件难事儿。我一直认为，就算微软明天给外星人一锅端了，我也能很快进入其他技术领域，并很快达到较高级的程度。但是，如果您每次都只了解一些表面，自然很容易觉得天崩地裂。盲目追赶，那也只是恶性循环而已。&lt;/p&gt;&lt;p&gt;我一直强调“眼界”，微软技术不断为我打开新视野，这些技术的设计者都在各种场合提到其他技术对他们的影响。因此，学习了C#和F#，我对于Python，Ruby，Scala，Haskell都产生了浓厚的兴趣，我不会像许多Java程序员认为Java语言已经足够了，或是像许多Ruby程序员那样认为&lt;a href="http://blog.zhaojie.me/2010/08/programmer-hierarchy-disgusting-csdn-news.html"&gt;自己领先于其他程序员&lt;/a&gt;，我能时刻保持Keep Stupid，Keep Hungry。我时常不解一些技术人员在我看来&lt;a href="http://blog.zhaojie.me/2010/03/microsoft-technology-and-the-attitude.html"&gt;莫名其妙的轻视（不是“敌视”）微软技术&lt;/a&gt;，我认为技术的大千世界何其美好。因此，即便我再是厌恶Java语言，也对JVM和其生态环境敬爱有加。于是，我通过《&lt;a href="http://www.amazon.com/CLR-via-Dev-Pro-Jeffrey-Richter/dp/0735627045/"&gt;CLR via C#&lt;/a&gt;》对.NET运行时浅尝辄止之后，又通过《&lt;a href="http://www.amazon.com/Oracle-JRockit-Definitive-Marcus-Hirt/dp/1847198066/"&gt;Oracle JRockit: The Definitive Guide&lt;/a&gt;》深入了解JVM的虚拟机世界。我看过了《Concurrent Programming on Windows》之后，又去阅读了作者推荐的《&lt;a href="http://www.amazon.com/Java-Concurrency-Practice-Brian-Goetz/dp/0321349601/"&gt;Java Concurrency in Practice&lt;/a&gt;》。&lt;/p&gt;&lt;p&gt;如果眼界没有打开，即便您学习的是业界“最先进”的技术，也可能产生偏差。例如时常看到Rails开发人员自豪地说，他们可以从Rails里学习RESTful。由于前段时间我刚巧看了《&lt;a href="http://www.amazon.com/REST-Practice-Hypermedia-Systems-Architecture/dp/0596805829"&gt;RESTful in Practice&lt;/a&gt;》一书，再结合我对Rails的了解，我实在没有感到这个Web框架在RESTful方法的独到之处。于是他们让我去看Rails 3.0里&lt;a href="http://guides.rubyonrails.org/routing.html"&gt;强大的Routing功能&lt;/a&gt;。我看后，才意识到其实他们似乎对于REST的理解有所偏差——REST的精髓在于&lt;a href="http://roy.gbiv.com/untangled/2008/rest-apis-must-be-hypertext-driven"&gt;由Hypermedia驱动的State Transfer&lt;/a&gt;，而形如“/article/20”这样的URL，以及映射一些HTTP方法等等，其实远非RESTful架构设计里的关键。RESTful只是要求“每个资源对于一个URI”，但并没有规定URI的形式，而且如果客户端直接了解服务器端的URL规格并直接访问，就与REST的“解耦”目标渐行渐远了。事实上，《RESTful in Pratice》一书甚至有建议对URL做些混淆。总体而言，Rails只是对REST架构中的一小部分提供了较好的支持而已，还远不能“从Rails学习REST”。昨天晚上我和REST专家李琨老师谈了我在这方面的理解，他基本赞同我的看法。我庆幸不已，要知道在此之前我还看过《RESTful .NET》一书，但我走向《RESTful in Practice》之后，才意识到前者给我带来了不少错误的观念。幸好，我并没有良好的自我感觉，也没有满足于现状。&lt;/p&gt;&lt;p&gt;如果您学习的是.NET，那么打开眼界的一个有效工具便是Mono。Mono及Miguel de Icaza已经不再拘泥于跨平台的.NET这个目标，而是努力在其之上实现大量的开源或商业产品。其中的典型便是&lt;a href="http://www.infoq.com/cn/news/2010/10/Cross-Dev-WP7-iPhone-Android"&gt;MonoTouch和MonoDriod让.NET及C#进入iOS和Android平台&lt;/a&gt;，&lt;a href="http://tmssoftware.com/site/blog.asp?post=183"&gt;广受喜爱&lt;/a&gt;，也已经&lt;a href="http://matt-greer.com/blog/2010/10/optix-trailer/"&gt;有越来越多的成功案例&lt;/a&gt;。此外，Mono对于&lt;a href="http://www.infoq.com/cn/news/2010/10/MonoMac-Update"&gt;开发原生Mac OS应用程序的支持&lt;/a&gt;也步入了正轨。我作为一个.NET开发人员，从没有过如此兴奋的感觉。&lt;/p&gt;&lt;p&gt;如果您正确地学习了.NET技术，您会发现自己走上了一条良性发展的道路。从另一方面来讲，微软的技术固然多，但作为开发人员我们并不需要了解每项技术。微软在创建一门新的技术的时候，都会讲清楚这门技术所解决的问题是什么，如果与您无关，完全可以不去学习。例如.NET 2.0与3.5之间还有一个3.0，其中提供了WPF，WF和WCF三个框架。我可以坦率地讲，我对它们没有任何了解，但这丝毫不影响我自称是一个优秀.NET技术人员的自信。很多时候，如“疲于追赶”这种事情，我觉得太多程度上都是自寻烦恼了。这样“无中生有”的烦恼还有很多，例如微软给出F#以后，就有人说微软要抛弃C#了。您为什么就不能认为这是一种互补，或者说，给您多了一种选择呢？微软同时发展VB.NET和C#语言好多年了，您一直没有学习VB.NET的烦恼，为什么现在多了一个F#，您又动摇了呢？还有例如近日的Silverlight问题，&lt;a href="http://blog.zhaojie.me/2010/11/silverlight-and-microsoft-technology-1-is-silverlight-dead.html"&gt;前篇文章已有详述&lt;/a&gt;，不提。&lt;/p&gt;&lt;p&gt;许多人会持有这样的观念：整个技术领域分割为“微软”和“非微软”两部分，然后指责“微软”技术不如“非微软”来的丰富。在我看来这种分割方式是十分可笑的，怎么没有人将技术分为“Ruby”和“非Ruby”，然后指责“Ruby”技术不够丰富呢？此外，还有一些观点，认为ASP.NET应用程序靠memcached提高伸缩性是种失败，这也是同样的割裂逻辑。为什么PHP和Rails使用memcached就被视为正当手段呢？说起来，memcached是C语言写的，还真不关PHP和Rails什么事情呢。&lt;/p&gt;&lt;p&gt;而且，正如我之前说的，微软技术对我的重要价值之一，便是促进了我对各方面技术的浓厚兴趣。无论您是专攻哪种技术的开发人员，如果只是停留在自己这一亩三分地上，这都是不甚可取的。没有人限制微软系的技术人员从其他领域吸取经验，正如一个优秀Ruby程序员肯定也从Ruby外的技术领域吸收了大量精华。说实话，除了政治需要，我实在找不到将微软和开源社区（或是其他社区）对立起来的理由。事实上，我时常感觉，您即便工作于.NET的竞争性平台，学习.NET对于个人提高来说也是大有帮助的。&lt;/p&gt;&lt;p&gt;就写到这里吧。希望对您了解微软技术，以及如何学习微软技术能够有所帮助。&lt;/p&gt;&lt;p&gt;原文首发：&lt;a href="http://blog.zhaojie.me/2010/11/silverlight-and-microsoft-technology-2-microsoft-technology-and-how-to-learn.html"&gt;Silverlight与微软技术（下）：微软技术与技术学习&lt;/a&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/1869194.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2010/11/05/silverlight-and-microsoft-technology-2-microsoft-technology-and-how-to-learn.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry><entry><id>http://www.cnblogs.com/JeffreyZhao/archive/2010/11/02/silverlight-and-microsoft-technology-1-is-silverlight-dead.html</id><title type="text">Silverlight与微软技术（上）：微软抛弃Silverlight了么？</title><summary type="text">话说，在最近的PDC上，微软的副总裁Bob Muglia说了类似的话“我们对Silverlight的策略改变了，我们要用HTML5来实现跨平台的应用程序”，于是乎，社区铺天盖地响起了“微软要抛弃Silverlight”的调调。出现这个说法并不奇怪，媒体转述一遍，再给社区理解一下，很正常。但是我觉得奇怪甚至有些恶心的是，当事实愈发明朗化的时候，冒出的一些莫名其妙，兴灾乐祸，事后诸葛还在愈演愈烈。这两天我在社区里看的很多说法，某些“评论家”连一些基本概念，如“Silverlight是Windows Phone 7的开发平台”都不清楚，就来捕风捉影，实在让我难以继续旁观。</summary><published>2010-11-02T05:30:00Z</published><updated>2010-11-02T05:30:00Z</updated><author><name>Jeffrey Zhao</name><uri>http://www.cnblogs.com/JeffreyZhao/</uri></author><link rel="alternate" href="http://www.cnblogs.com/JeffreyZhao/archive/2010/11/02/silverlight-and-microsoft-technology-1-is-silverlight-dead.html"/><link rel="alternate" type="text/html" href="http://www.cnblogs.com/JeffreyZhao/archive/2010/11/02/silverlight-and-microsoft-technology-1-is-silverlight-dead.html"/><content type="html">&lt;p&gt;话说，在最近的PDC上，微软的副总裁Bob Muglia说了类似的话“我们对Silverlight的策略改变了，我们要用HTML5来实现跨平台的应用程序”，于是乎，社区铺天盖地响起了“微软要抛弃Silverlight”的调调。出现这个说法并不奇怪，媒体转述一遍，再给社区理解一下，很正常。但是我觉得奇怪甚至有些恶心的是，当事实愈发明朗化的时候，冒出的一些莫名其妙，兴灾乐祸，事后诸葛还在愈演愈烈。这两天我在社区里看的很多说法，某些“评论家”连一些基本概念，如“Silverlight是Windows Phone 7的开发平台”都不清楚，就来捕风捉影，实在让我难以继续旁观。&lt;/p&gt;&lt;p&gt;其实&lt;a href="http://www.zdnet.com/blog/microsoft/microsoft-our-strategy-with-silverlight-has-shifted/7834"&gt;Bob Muglia的原话&lt;/a&gt;是这样的：&lt;/p&gt;&lt;blockquote style='border:2px solid #EFEFEF;color:#333333;padding:5px 10px;'&gt;  &lt;p&gt;&amp;quot;Silverlight will continue to be a cross-platform solution, working on a variety of operating system/browser platforms, but HTML is the only true cross platform solution for everything, including (Apple's) iOS platform.&lt;/p&gt;  &lt;p&gt;Silverlight将继续是一个跨平台的解决方案，未来Silverlight将持续工作在各种操作系统/浏览器平台上，但是HTML才是目前一切运用真正跨平台解决方案，包括苹果的iOS平台。&lt;/p&gt;&lt;/blockquote&gt;&lt;p&gt;这句话的问题在哪里？我看不出任何要放弃Silverlight的意思。微软从一开始就说Silverlight将会跨操作系统及浏览器运行，目前是，将来也是，包括Windows，Mac OS及这些平台上的各种浏览器。但是，对于移动设备又能怎么办呢？苹果的iOS上已经拒绝Flash进入，因此拒绝Silverlight也是可以预料的，因此Silverlight方面就算尽再大努力也无法实现这点。而苹果是支持HTML 5的，因此微软为了发展，将HTML作为“跨所有平台”的手段，在我看来十分顺理成章。可能Silverlight以后不会进入iOS，但并不表示它不会进入Android等其他手机平台，而就目前来说，Silverlight本身已经是Windows Phone 7的开发平台了。&lt;/p&gt;&lt;p&gt;Silverlight之于Windows Phone 7，WPF之于Windows，就好比CocoaTouch之于iOS及Cocoa之于Mac OS，它们都是十分正常的产品及开发平台策略。就拿苹果来做例子吧，CocoaTouch只能工作在iOS系统上，您担心CocoaTouch被苹果抛弃吗？诚然，微软的手机才刚刚起步，平板电脑更是没有踪影，从商业上来说远不如iOS设备成功，但是人人都能看到微软对Windows Phone 7的重视，WP7是微软不断强调的“三屏一云”战略的重要组成部分，而Silverlight就是WP7上的开发环境，那么您为什么会担心它会被微软抛弃？我看到有些文章的标题类似于：“Silverlight失败，未来属于移动互联网”，于是我就转不过脑子了，Silverlight对于微软来说，就几乎等同于“移动互联网”，您一边看好移动互联网，一边觉得Silverlight挂了，你让微软情何以堪？&lt;/p&gt;&lt;p&gt;有人说，这次的&lt;a href="http://player.microsoftpdc.com/session"&gt;PDC 2010&lt;/a&gt;都没有Silverlight的内容了，可以看出微软不要Silverlight了，否则怎么没有Silverlight 5的消息？我也觉得很奇怪，PDC是有主题的，这次的主题是Azure，IE 9和WP 7，因此强调的是云计算，HTML 5和移动互联网开发，最后一个其实就是Silverlight。事实上Silverlight的内容本就没少，只是换了个名字叫做WP 7。我不知道嚷嚷着PDC没有了Silverlight的同学有没有真正看过PDC，不过我在看，看了很多，感觉很爽。我看到了&lt;a href="http://player.microsoftpdc.com/Session/6f853fa2-06f6-45e5-ac25-18c31cc4ba32"&gt;PDC的Keynote演讲&lt;/a&gt;上ScottGu就在现场操练Silverlight开发，分会场里也在大谈“&lt;a href="http://player.microsoftpdc.com/Session/58d670be-bd26-4ee3-9db1-5f2767eba4f8"&gt;基于Silverlight开发面向Azure平台的WP7应用程序&lt;/a&gt;”、“&lt;a href="http://player.microsoftpdc.com/Session/14b74bfd-d2e5-42de-accf-3ff2418783a8"&gt;优化WP7中Silverlight程序性能&lt;/a&gt;”，“&lt;a href="http://player.microsoftpdc.com/Session/73abab73-15e2-4911-a125-ab9487ebea22"&gt;早该知道的WP7开发注意事项&lt;/a&gt;”，还有与WP7几乎无关的“&lt;a href="http://player.microsoftpdc.com/Session/76864d75-b4da-4858-aac7-786c5f28e344/2.69"&gt;使用Silverlight 4开发商业应用&lt;/a&gt;”，“&lt;a href="http://player.microsoftpdc.com/Session/638f610a-ea51-4aef-9657-e3fe425ae745/469.163"&gt;如何在WPF和Silverlight中共享代码&lt;/a&gt;”等等太多内容。半年前的Mix 10大会上微软还在大谈Silverlight和WP7，只不过打得是Silverlight的旗号，而仅过了半年，微软打着自己正在全力推广的WP7的旗号来谈几乎相同的话题，您怎么就突然崩溃了呢？&lt;/p&gt;&lt;p&gt;PDC是微软专业会议，议程及其有限，而微软的技术实在太多，没有登上PDC讲台的话题实在太多太多了。去年的PDC还有关于CLR、虚拟化、Windows Server的话题呢，这次都看不到了，莫非微软要抛弃这些了？如果像某些同学希望的这样，微软发布了Silverlight 5的消息，我估计对于微软铺天盖地的谴责之声就要变成“技术发展太快”了。&lt;/p&gt;&lt;p&gt;如果说CocoaTouch只是在iOS设备上运行，而Silverlight除了Windows Phone 7以外，之前Windows和Mac OS上该有的还有，已经在的还在。Silverlight对于微软的重要性，不会比CocoaTouch对于苹果的重要性来的差。作为一个Silverlight开发人员原本该干什么，现在还是干什么，除此之外，退可开发WPF，进可出手WP7。&lt;a href="http://player.microsoftpdc.com/Session/b3efbe56-08c0-4ea9-85ec-eb481c189abd"&gt;ScottGu在PDC上接受Scott Hanselman采访时&lt;/a&gt;说，微软将开发语言、框架、工具进行统一，让开发人员可以很自如地进入WP7的开发领域。我对WPF和Silverlight一窍不通，但我从没像现在这么羡慕您已经掌握了这部分技术（当然其实也没那么羡慕啦，我相信自己会学得很快），因为在移动互联网的大潮下，我可能以后还真要去学习WP7上的Silverlight开发，而您已经可以顺利过渡了。&lt;/p&gt;&lt;p&gt;如果您还是对Bob的那段话表示纠结的话，其实也可以继续看看他的说法了。他和微软Silverlight团队估计也没想到，当然现在也意识到事态的严重性，于是连续发表了两篇声明，一是&lt;a href="http://team.silverlight.net/announcement/the-future-of-silverlight/"&gt;微软对Silverlight未来的担保&lt;/a&gt;，二是关于&lt;a href="http://team.silverlight.net/announcement/pdc-and-silverlight/"&gt;PDC上关于Silverlight那些表态的后续解释&lt;/a&gt;，其中写到：&lt;/p&gt;&lt;blockquote style='border:2px solid #EFEFEF;color:#333333;padding:5px 10px;'&gt;  &lt;p&gt;I said, &amp;quot;Our Silverlight strategy and focus going forward has shifted.&amp;quot; This isn't a negative statement, but rather, it's a comment on how the industry has changed and how we're adapting our Silverlight strategy to take advantage of that. &lt;/p&gt;  &lt;p&gt;我之前说到：“我们的Silverlight策略和前进的重心转移了”，这不是一个负面的说法，它只表示业界的现状改变了，我们调整Silverlight的策略希望可以利用这种改变。&lt;/p&gt;&lt;/blockquote&gt;&lt;p&gt;在我看来，业界现状的表现之一，就是之前我所说的苹果不会接受Silverlight和Flash，但它对HTML 5友好。微软不强求Silverlight进入iOS——这是Bob之前所特地强调的设备——而是让Silverlight去迎合HTML 5大潮。例如，Adobe在刚刚结束的&lt;a href="http://max.adobe.com/blog/"&gt;MAX 2010&lt;/a&gt;大会上&lt;a href="http://news.csdn.net/a/20101101/281147.html"&gt;展示了一款Flash至HTML 5的转化工具&lt;/a&gt;，那么我猜想，微软今后也会这么做吗？利用Flash和Silverlight所配备的高度生产力与HTML 5相抗衡也不失为一种竞争手段。当然，谁知道呢。此外，文章里还谈到过几个月就有下一代Silverlight的消息了，不知道这能否让某些朋友松一口气。&lt;/p&gt;&lt;p&gt;讨论和争议是好事，但是在这个过程中出现了一些声音让我很不满。例如某些同学连Silverlight与WP7的关系都不知道就来指点江山。Ivony写到过类似的意思：社区里有一些人，看着某个事物不断发展却无力接触，一遇任何风吹草动却跳出来幸灾乐祸，正如这次Silverlight事件，还有上次微软于LINQ to SQL等等。我不知道上次的那些认为微软放弃LINQ的同学，看到.NET 4.0中LINQ to SQL的更新，LINQ to Entity在&lt;a href="http://player.microsoftpdc.com/Session/68cfa011-c399-4151-ad9f-748d8723a19d"&gt;最近两届PDC中的表现&lt;/a&gt;，以及本次PDC上随Azure出现的“&lt;a href="http://player.microsoftpdc.com/Session/bfa72307-6534-41ad-bcf7-0f4fb9280515"&gt;LINQ to Azure，LINQ to Everything&lt;/a&gt;”的演讲是什么感觉。&lt;/p&gt;&lt;p&gt;微软的技术一定是有问题的，但是我们完全可以用合适的方式来对待，受用无穷。当然，这方面内容就下次再展开了。&lt;/p&gt;&lt;p&gt;原文首发：&lt;a href="http://blog.zhaojie.me/2010/11/silverlight-and-microsoft-technology-1-is-silverlight-dead.html"&gt;Silverlight与微软技术（上）：微软抛弃Silverlight了么？&lt;/a&gt;&lt;/p&gt;&lt;img src="http://www.cnblogs.com/JeffreyZhao/aggbug/1867052.html?type=1" width="1" height="1" alt=""/&gt;&lt;p&gt;&lt;a href="http://www.cnblogs.com/JeffreyZhao/archive/2010/11/02/silverlight-and-microsoft-technology-1-is-silverlight-dead.html" target="_blank"&gt;本文链接&lt;/a&gt;&lt;/p&gt;</content></entry></feed>
