手机浏览 RSS 2.0 订阅 膘叔的简单人生 , 腾讯云RDS购买 | 超便宜的Vultr , 注册 | 登陆
浏览模式: 标准 | 列表2009年04月的文章

jQuery简单开发

jQuery这种轻量级的框架大家使用的都比较多,1.3后效率据说又上升了不少,因此,开发基于jQuery的插件也就显得那么理所当然了。
一般来说,jQuery有两种插件模式,一种是:$.extends({}) ,另一种是:$.fn.extends({})
个人理解:前一种是属于全局性的调用,后一种是针对某个元件的绑定调用。这当然是简单的理解。但事实上,也基本上就是这么做的。

官方的例子也比较简单:

JavaScript代码
  1. $.extend({  
  2.     max: function(a, b) {  
  3.         return a > b ? a : b;  
  4.     },  
  5.     min: function(a, b) {  
  6.         return a > b ? b : a;  
  7.     },  
  8.     avg: function(a, b) {  
  9.         return a / b;  
  10.     }  
  11. });  

看上去是不是容易?然后就可以直接调用了。 $.min(2,3) 返回2
一般情况下,为了在扩展中使用$,却又担心的页面使用了jQuery.noConflict()而取消了$指向jQuery的引用,则需要这样写

JavaScript代码
  1. function($){  
  2.     $.fn.extend({  
  3.         //....code in here  
  4.     });  
  5. })(jQuery);  

这样写不仅能够将$显式指向jQuery,而且将产生的变量封在function的作用范围内,不会污染window全局。
而基于$.fn.extends({})的扩展又如何开发呢?

在这里我引用Roby的译文:http://www.robysky.com/archives/171
英文原文:http://www.learningjquery.com/2007/10/a-plugin-development-pattern

我认为以下插件开发模式是必须应该掌握的:
1.在JQuery命名空间内声明一个特定的命名;
2.接收参数来控制插件的行为;
3.提供公有方法访问插件的配置项值;
4.提供公有方法来访问插件中其他的方法(如果可能的话);
5.保证私有方法是私有的;
6.支持元数据插件;

下面,我将逐一讲述上面的内容,并在同时给出相关的简单插件开发代码。
1.在JQuery命名空间内声明一个特定的命名

这意味着开发的是一个单一命名的插件脚本,如果你的脚本包含多个插件或者有补充性质的插件,比如$.fn.doSomething() 和$.fn.undoSomething(),那你得声明多个命名了。但是总体来说,当开发一个插件时,我们应该努力做到用一个单一的命名来搞定整个插件。

在例子中,我们将声明一个名为“hilight”的插件。

JavaScript代码
  1. $.fn.hilight = function() {  
  2.     // Our plugin implementation code goes here.  
  3. };   

我们可以这样调用:
$(’#myDiv’).hilight();
但是假如我们需要打破这种单一的命名和调用方式呢?有很多理由支持我们这么做:设计上的需要;更加简单和可读的配置;而且那样将更加符合OO的要求。

在没有给命名空间来到麻烦的前提下,将插件的部署打破成为多个函数的形式将是十分繁琐的。我们通过认识并利用JavaScript中 functions是最高层的对象,和其他对象一样,functions可以被赋予属性,前面我们已经将hilight命名声明在了JQuery的原型对象上,那么,其实,其他的我们想扩展的属性或对象都能够在hilight上进行声明。稍后将详细讲述此点。
2.接收参数来控制插件的行为;

来为我们的hilight插件添加指定前景和背景色的功能,我们需要在函数中允许一个object类型的选项设置。如下所展示的那样:

JavaScript代码
  1. $.fn.hilight = function(options) {  
  2.  var defaults = {  
  3.     foreground: 'red',  
  4.     background: 'yellow'  
  5.   };  
  6.   // Extend our default options with those provided.  
  7.   var opts = $.extend(defaults, options);  
  8.   // Our plugin implementation code goes here.  
  9. };  

现在,我们的插件可以这样来调用:

$(’#myDiv’).hilight({
  foreground: ‘blue’
});
3.提供公有方法访问插件的配置项值;

上面的代码我们可以做一下改进,使得插件的默认值可以在插件之外被设置。这无疑是十分重要的,因为它使得插件用户可以使用最少的代码来修改插件配置,这其实是我们利用函数对象的开始。

JavaScript代码
  1. // plugin definition  
  2. $.fn.hilight = function(options) {  
  3.   // Extend our default options with those provided.  
  4.   // Note that the first arg to extend is an empty object -  
  5.   // this is to keep from overriding our "defaults" object.  
  6.   var opts = $.extend({}, $.fn.hilight.defaults, options);  
  7.   // Our plugin implementation code goes here.  
  8. };  
  9.    
  10. // plugin defaults - added as a property on our plugin function  
  11. $.fn.hilight.defaults = {  
  12.   foreground: 'red',  
  13.   background: 'yellow'  
  14. };  

 4.提供公有方法来访问插件中其他的方法(如果可能的话)

这里要讲的方法和前面的讲解一脉相承,用此方法来扩展你的插件(而且能够让其他人进行扩展)是件很有意思的事情。例如,在扩展hilight插件时,我们可以定义一个format方法用来格式化高亮显示的文本,原来的hilight插件和扩展了format方法的插件代码如下:

JavaScript代码
  1. $.fn.hilight = function(options) {  
  2. // iterate and reformat each matched element  
  3. return this.each(function() {  
  4. var $this = $(this);  
  5. ...  
  6. var markup = $this.html();  
  7. // call our format function  
  8. markup = $.fn.hilight.format(markup);  
  9. $this.html(markup);  
  10. });  
  11. };  
  12.    
  13. // define our format function  
  14. $.fn.hilight.format = function(txt) {' 
  15. return '<strong>' + txt + '</strong>';  
  16. };  

如前面所述,我们已经很容易的通过设置options对象的属性来允许一个回调函数来覆写默认的格式设置。在这里有另外一个非常棒的方法来个性化你的插件,上面展示的方法实际上就是通过暴露format方法,使其可以被重新定义。这种做法使得其他人可以采用他们自己的习惯和方式来重写你的插件,这意味着他们可以为你的插件写额外的扩展插件。
仔细考量一下前面我们用到的插件例子程序,你可能会想“我们究竟应该在什么时候使用这种插件方式来实现需求”的问题。一个来自现实应用中的插件便是“ Cycle Plugin”,它是一个支持多种滑动显示特效的插件,特效包括滚动、滑动和渐变等等。但是,实际上,并没有办法来定义每一个可能会用在滑动变幻上的特效。这就是这种扩展方式的有用之处。“ Cycle Plugin”插件暴露了”transitions”对象,这使得用户只需要按照如下方式便可以添加自己的变幻定义:
$.fn.cycle.transitions = {

};
这种技巧使得用户可以定义或者采用自己习惯的方式来扩展“ Cycle Plugin”。
5.保证私有方法是私有的;

上面提到的暴露插件中的公有方法的技巧使得插件能够被覆写,这将使插件变得十分灵活而强大,但至于哪一部分,那些属性和方法应该被暴露出来,你得小心了。一旦使其能够被外界访问到,你就得注意到任何调用参数和语义化的变动都可能使其丧失向前的兼容性。作为一般准则,如果不确定是否应该暴露某个属性或对象的话,那就最好别那样做。
那么我们应该怎样来定义多个方法而不至于使命名空间混乱并且保证不被暴露再外呢?这就是闭包的工作,为了便于演示,我们给插件加入了一个叫做 “debug”的功能,它用来记录firebug控制台所选择的网页元素数目。为了创建一个闭包,我们将整个功能的定义放入在一个function中了(有关这方面的知识,可参见JQuery手册)。

JavaScript代码
  1. // create closure  
  2. (function($) {  
  3.     // plugin definition  
  4.     $.fn.hilight = function(options) {  
  5.         debug(this);  
  6.         ...  
  7.     };  
  8.     // private function for debugging  
  9.     function debug($obj) {  
  10.         if (window.console && window.console.log)  
  11.         window.console.log('hilight selection count: ' + $obj.size());  
  12.     };  
  13.     ...  
  14.     // end of closure  
  15. })(jQuery);  

debug方法在这里是无法被在插件以外访问到的,因此,我们称之为它是插件私有的。
6.支持元数据插件;

根据你所写的插件的类型,为你的插件加入元数据插件的支持将使其变得更强大。就我个人来说,喜欢采用元数据插件的重要原因便是它可以让你使用定义之外的标签来覆写你的插件属性设置(这在创建demo和例子时十分有用),而且支持它十分的简单。
更新:这部分内容可以在本文的评论中展开讨论(既然有争议的话)

JavaScript代码
  1. // plugin definition  
  2. $.fn.hilight = function(options) {  
  3.  ...  
  4.  // build main options before element iteration  
  5.  var opts = $.extend({}, $.fn.hilight.defaults, options);  
  6.  return this.each(function() {  
  7.  var $this = $(this);  
  8.  // build element specific options  
  9.  var o = $.meta ? $.extend({}, opts, $this.data()) : opts;  
  10. ...  

改动部分的代码会做如下的事情:
*测试metadata插件是否可用
*如果可以,将用metadata扩展options对象
这被加入到jQuery.extend,作为其最后一个参数,所以它可以覆写任何其他参数设置。现在我们可以通过下面的方式控制其行为:

XML/HTML代码
  1. <!--  markup  -->  
  2. <div class="hilight { background: 'red', foreground: 'white' }">Have a nice day!</div>  
  3. <div class="hilight { foreground: 'orange' }">Have a nice day!</div>  
  4. <div class="hilight { background: 'green' }">Have a nice day!</div>  

而在调用方面,我们通过一行简单的代码就可以实现预期的效果:
$(’.hilight’).hilight();

将上面所述内容涉及到的代码放在一起,完整的例子程序代码如下:

JavaScript代码
  1. //  
  2. // create closure  
  3. //  
  4. (function($) {  
  5.     //  
  6.     // plugin definition  
  7.     //  
  8.     $.fn.hilight = function(options) {  
  9.         debug(this);  
  10.         // build main options before element iteration  
  11.         var opts = $.extend({}, $.fn.hilight.defaults, options);  
  12.         // iterate and reformat each matched element  
  13.         return this.each(function() {  
  14.             $this = $(this);  
  15.             // build element specific options  
  16.             var o = $.meta ? $.extend({}, opts, $this.data()) : opts;  
  17.             // update element styles  
  18.             $this.css({  
  19.                 backgroundColor: o.background,  
  20.                 color: o.foreground  
  21.             });  
  22.             var markup = $this.html();  
  23.             // call our format function  
  24.             markup = $.fn.hilight.format(markup);  
  25.             $this.html(markup);  
  26.         });  
  27.     };  
  28.     //  
  29.     // private function for debugging  
  30.     //  
  31.     function debug($obj) {  
  32.         if (window.console && window.console.log)  
  33.         window.console.log('hilight selection count: ' + $obj.size());  
  34.     };  
  35.     //  
  36.     // define and expose our format function  
  37.     //  
  38.     $.fn.hilight.format = function(txt) {  
  39.         return '<strong>' + txt + '</strong>';  
  40.     };  
  41.     //  
  42.     // plugin defaults  
  43.     //  
  44.     $.fn.hilight.defaults = {  
  45.         foreground: 'red',  
  46.         background: 'yellow'  
  47.     };  
  48.     //  
  49.     // end of closure  
  50.     //  
  51. })(jQuery);  

看完以上的内容,你是不是对jQuery的插件开发加深了一定的了解了呢?
顺便提一下,yhustc在自己的博客上写了一个基于jQuery的软键盘插件,你是不是又可以根据上面的教程来写一个基于$.fn.extends的扩展呢?让yhustc的插件可以绑定在某个元件上?

Tags: jquery, 开发, 插件, yhustc

切勿过早优化

放在PHP栏目是我仔细想过的,虽然文章内容里并未提及到PHP
开发WEB,很多人在一开始就考虑了优化优化再优化,但是,如果按照你这样的优化下去,当你发现瓶劲的时候你怎么办?你已经无法优化了。。
因此,为自己的代码预留一点优化空间,先赶着把代码上线,然后再边运行边优化。一来也保证了上线的时间,二来也可以在运行时注意到哪些地方是需要重点优化的。

以下内容来自守望轩(博客园)的文章:原文http://www.cnblogs.com/xjb/archive/2009/04/13/no-premature-optimization.html

Donald Knuth说“过早优化是万恶之源”(premature optimization is the root of all evil)。这话也许有些夸张,但“过早优化”的危害我觉得不能忽视。同时,我觉得“过早优化”的概念不专属编写程序,生活中的示例也比比皆是。不信,你看看下面这些情形你是否遇到过:

http://www.watch-life.net/life-thinking/no-premature-optimization.html

1、当你开始学一门程序语言的时候(比如c#),你想如果可以精通开发工具(比如Visual Studio)一定如虎添翼,于是一开始你就花很多时间去研究开发工具,而忘记自己学习的重点是语言本身,而非工具。或者,一开始,你花不少的时间去选择哪门程序语言,比较各种语言的优劣,在五花八门的语言前面犹豫不决,这个想学,那个也不想放弃,结果都是学个半路子。

2、当你学习一门外语比如英语的时候,一开始,你花了很多的时间去下载有关英语资料,花了很多的时间去找英语书籍,以为有了这些资料和书籍就可以学好英文,而不是一开始就踏踏实实的从单词、语法开始,结果后来资料下载了一大堆,书籍买了不少,却没有坚持下去。

3、你想搞体育锻炼,比如打羽毛球,于是一开始你花大量时间去买球衣、球鞋、球拍等装备,可没连几天,你发现自己开始三天打鱼了,最后,那些装备都起了灰,也没锻炼几次。

4、你想做时间管理(Getting Things Done),于是你研究各种时间管理的资料,上各种时间管理技巧的网站,比如lifehack、 digg 、gtdlife,下载对最流行的GTD的管理软件,以节省时间的名义浪费时间,很浮躁,不能做到实实在在把每天的计划都落实,拖拖拉拉。

5、你有没有这样的体验,一本书你总是对开头的部分看的最仔细,后面的章节没坚持看下去,下次又重复这种循环。当你计划做一件事的时候,总是规划的 非常完美,几乎考虑每个细节,但却没有认认真真、一步一步执行,或者过早完美计划,反而让你缩手缩脚,犹豫不前,瞻前顾后,顾此失彼,最后虎头蛇尾。

6、比如,如果我有了钱,我就如何如何享受快乐,比如,如果我将来有了很多的时间,我就会花更多的时间陪家人或锻炼…

这样类似的例子还可以举很多。

过早优化对大的问题在于:过早关注不重要的部分,而忽略行动和目标本身。以静态的思维来优化,殊不知,事务发展总是动态的,“优化”是需要长期的实 践积累才可以获得。出发点是好的,但往往好心办坏事,折腾大量的时间,做了很多不该做的,而该做的、重要的反而没做。强化外部条件、工具等外在,而忽略内 在因素和行动本身,或者,过多期望将来,而忽略当下眼前。

活在当下,实实在在做好手头的事,是避免“过早优化”最好的方法之一

Tags: 优化

以后取名不用担心了

再往 后,取名不用担心了。什么翻康熙字典?不允许
你凭什么翻呀?想反清复明?做梦吧你。
国家有规定,取名有规范,不得取变态名,不得取超长名,象赵C这样的,你敢取?我不给你登记 。
为啥?
看这里:http://news.southcn.com/china/zgkx/content/2009-04/11/content_5057672.htm
我简单摘要一下:

XML/HTML代码
  1. 两千姓氏用字属生造乱编  
  2.   
  3. 姓名用字则有4000个错字别字,以后取名将被规范  
  4.   
  5. 《规范汉字表》对百姓生活有何影响?  
  6.   
  7. 李宇明表示,《规范汉字表》出台后,中小学教材常用字范围等方面可能面临变化,今后会有专门的相应通知下发。  
  8.   
  9. 王宁则特别谈到,新生儿取名更要强调用字规范。她表示,人名用字也是社会用字的一部分,必须要符合汉字使用的规范,这样才是真正的保障姓名权。  
  10.   
  11. 王宁说,中国人的重名现象绝不是因为能够用来取名的字太少,许多给人留下深刻印象的好名字都是从古典诗词、典籍中化用而来,但即使是这些古籍,用字量也非常有限———过去的童蒙识字课本,不重复的字也才2320个;十三经(在南宋形成的十三部儒家经典,包括《诗经》、《周易》、《论语》、《尔雅》、《孟子》等)不重复的字不到6000个;《全宋诗》收录了18401首诗,才用了4520个汉字。而今天的规范汉字达到8000多个,可以有无数种组合,还不够起名吗?  
  12.   
  13. 但据公安部门透露,在此次换领二代身份证的过程中,使用目前通行的收字7.6万个的汉字国际编码,全国人口的姓名用字中竟还有大概8000个字找不到!而据专家研究,这约8000个字中,至少有一半是错字、别字。  
  14.   
  15. 此外,目前我国公民的姓氏用字大概有7600余字,但其中竟有2000个字所代表的姓只有一个人在使用!也就是说,这些姓几乎都是生造或胡乱编出来,而并非历史传承的。这些现象都表明,规范姓名用字是多么迫在眉睫。  
  16.   
  17. 王宁表示,用一个多数人不认识、基本没人用的生僻字起名,既不利于社会又不利于自己,这又何苦?  

Tags: 取名

FriendFeed实现基于MySQL的无模式存储

架构这个东西,不能一味的盲目抄袭,因为每种新架构的出现往往都有其特定的历史背景,要么是数据访问量太大、要么(想写的一些内容因为存储关系丢失了,一下子又没有想起来,下面是重写的,但内容已经和原来想的不太一样了)

高春辉就在他的勃客里认为,主从数据库不行了,未来的数据存储走向应该不会再是主从,他这么说:

还是有关DAL:http://www.paulgao.com.cn/index.php?itemid=141
  1. 这里可以先提前说一下吧,记得之前的迁移网站时的帖子里我说过,让 MYSQL 主从架构去死,很多人不太信。  
  2.   
  3. 而现在这个 DAL 的架子越来越清楚,我相信是可以达到99%的可能性,可以使主从架构从最大的用途是读写分离,变成了数据备份。其实我到现在也不知道 MySQL 当时推主从架构是为了读写分离还是数据备份。:D  
  4.   
  5. 我认为不管是主从还是主主结构都有一个最大的问题,主库和从库的数据的延迟更新问题,主主方式会好一些,但是配置起来太麻烦了。尤其是要求越高,就会越感觉到严重性。  
  6.   
  7. 而从程序员的角度,对于数据库的操作,最大的问题就是要把缓存的逻辑和数据逻辑混写,导致代码很难写也很难读,也很难调试清楚。  
  8.   
  9. 那么 DAL 如果能够帮助程序不用再关心缓存逻辑,只关心业务逻辑的话,不知道您是否认同 DAL 的重大作用呢?而代码量在我认为,起码可以减少个20%-30%吧?因为起码去掉了三个逻辑:读取缓存、判断有效和设置缓存。  
  10.   
  11. 我也觉得其实这个 DAL 的最核心功能就是如何自动缓存和清理缓存了。因为不让程序员缓存和清理,就的是程序自己来管理缓存和清理缓存,总得清理嘛。不过这个还是保密一下吧。起码不是某些人想的只能缓存单条数据,也不是某些人想的清理是按照单条方式的清理。当然另外的一个核心功能就是分库分表的自动和透明化,这个功能有很多软件都实现了,就不多说了。  

文末,他推荐了一篇InfoQ上的文章,在这里我也进行转载一下,是关于FriendFeed实现基于MySQL的无模式存储,不过他这种架构也不是能拿来就要用的,也需要根据目前的实际情况,只能进行参考。这是一篇翻译文章:

作者 Dave West译者 王丽娟 发布于 2009年4月4日 下午8时7分

 

对于迅速增长的网站所遇到的问题——“用灵活的模式存储数据、即时创建新的索引”,FriendFeed的Bret Taylor介绍了一种“无模式的解决方案” 。问题本身源自一些需求:需要不断增加新功能,不断更新底层的数据库结构和数据库中存储的数百万条已有记录,还要同时支持新旧功能。FriendFeed的办法是基于MySQL建立一个无模式的解决方案,而不是迁移到别的技术基础上去。Bret描述了基本问题:

尤其是有一两千万行数据的时候,每次修改模式、往数据库中添加索引都会数小时完全锁定数据库。删除旧索引也需要同样长的时间,但不删除又会影响性能,因为 数据库在每次执行INSERT操作时都会继续读写这些不用的块,而重要的块却没有足够的内存。经过一些复杂的操作过程可以克服以上困难(比如在从机上创建 新索引,然后调换从机和主机),但这些操作过程都很容易出错,也都是重量级的,因此会使我们因为害怕改变模式/索引而不敢增加新功能。由于我们的数据库都 是严重分片的,像JOIN这些MySQL的关系型功能对我们毫无用处,所以我们决定看看RDBMS之外的领域。

研究了几个可行的解决方案后,他们决定基于MySQL的自定义一种“无模式”持久化方案,而不是彻底改换门庭。

他们的解决方案是把主要数据和这些数据的索引分离开来。“我们的数据存储储存了无模式的属性包……我们在单独的MySQL表中存储索引,从而在这些实体中索引数据。”这是以容量来换效率。

结果我们比以前多了很多的表,但添加和删除索引却很容易。我们大力优化了填充新索引的进程(我们称之为“Cleaner”),以便该进程能快速填充新索引,而不会让站点中断。

分离数据和索引引起了一致性和原子性问题。他们没有建立严格的事务规则,而是把数据库表推到最简,索引只用来引用,发生实际的数据库读操作的时候才 施加数据过滤。他们改进了持续更新表的自动化进程,让这个“Cleaner”进程不停地对优先级高的被更新实体进行更新和索引修正。尽管可能出现不一致, 但消除不一致的时间平均不到两秒钟。

Bret用平均页面延迟这一指标描述了以下走向。

  • 整体来说——尽管有增加的趋势,但还是有显著的减少。
  • 过去二十四小时——即使在高峰时段也保持稳定。
  • 前一周——明显减少。

Bret的帖子有很多回复。有一种观点认为“对于模式演变,现代的RDBMS不像MySQL局限那么大”,这种观点忽略了选择背后的成本问题。其它读者则回复了更多种不同的解决办法。

有意思的是,并没有人指出FriendFeed的解决方案与古老的ISAM技术(Indexed Sequential Access Method,索引顺序存取法)之间的相似性。ISAM用的是同样的基本架构——分离数据和索引,同时在数据发生变化时自动更新索引。

查看英文原文:FriendFeed Implements Schema-less Storage Atop MySQL

Tags: 架构

UBUNTU 9.04倒计时

新版本的ubuntu要出来了。每年的4月10月就是出新版本的时候。
这不,网上都开始有倒计时了

装一下时髦,放个代码

Tags: ubuntu