通常摆在我们眼前的如下两种选择来作为我们的容器,数组或对象。我这里选择前者,前者更轻量一点。下面我们就hasClass函数作性能改进。
原来的写法:
1.var hasClass = function(ele,cls) { 
2.  return ele.className.match(new RegExp(‘(\s|^)‘+cls+‘(\s|$)‘)); 
3.}
虽然简短,但做了太多假设了,因为元素有时是未必有className,这时直接返回false就行了。而且match是返回一个数组,和我们期望的布尔值多少有点出入(它在我以前的程序运行良好,完全拜javascript的自动转换所赐)。我们用search代替match:
1.var hasClass = function(ele,cls) { 
2.  return ele.className.search(new RegExp(‘(\s|^)‘+cls+‘(\s|$)‘) > -1); 
3.}
Prototype.js的实现我比较满意,test方法在所有正则方法中是最轻量的(相反,exec是最重量,最慢,最强大):
1.var hasClass = function(el, cls) { 
2.  var classes = el.className;    
3.  return (classes > 0) ? (classes == cls ||  
4.    new RegExp("(^|\s)" + cls + "(\s|$)").test(classes)) : false; 
5.}
到现在为止,基于正则方法的挖掘可谓改无可改,我们祭出缓存大法:
1.(function(){ 
2.  var c={}; 
3.  window.hasClass=function(el, cls){ 
4.    if(!c[cls]){c[cls]=new RegExp("(^|\s)"+cls+"($|\s)");} 
5.    return el.className && c[cls].test(el.className); 
6.  } 
7.})();
如果这个正则以前创建过,就有以前的,没有再创建,因此在大量匹配的算法中非常有优势。放入闭包中是为了防止命名冲突,谁会料到后面会不会杀出一个同名的全局变量c来?!使用和原来的一样,因为我们是通过window来引用它。
01.<script type="text/javascript"> 
02.  (function(){ 
03.    var c=[]; 
04.    window.hasClass=function(el, cls){ 
05.      if(!c[cls]){c[cls]=new RegExp("(^|\s)"+cls+"($|\s)");} 
06.      return !!el.className && c[cls].test(el.className); 
07.    } 
08.  })(); 
09.  window.onload = function(){ 
10.    var div1 = document.getElementById("test1"); 
11.    var div2 = document.getElementById("test2"); 
12.    alert(hasClass(div1,"test1")) 
13.    alert(hasClass(div2,"dd")) 
14.  } 
15.</script> 
16.<div id="test1" class="test1">测试</div> 
17.<img src="http://images.cnblogs.com/t_type1.jpg" alt="mm1" id="1" draggable="true"> 
18.<img src="http://images.cnblogs.com/t_type2.jpg" alt="mm2" id="test2" draggable="true"> 
19.<img src="http://images.cnblogs.com/t_type3.jpg" alt="mm4" id="3" draggable="true"> 
20.<img src="http://images.cnblogs.com/t_type5.jpg" alt="mm5" id="4" draggable="true">