从一开始接触Ext就看到有Ext.fly这个函数,当时觉得这个跟Ext.get没什么区别,加之当时对JS性能相关问题认识肤浅,也一直没有在意其区别,今日看learning extjs一书,看到了有专门对Ext.fly特别强调的一处:
Thisisn'texactlyaspeedtip,butismoreaboutconservingmemorybyusing
somethingcalleda"flyweight"toperformsimpletasks,whichresultsinhigherspeed
bynotcloggingupthebrowser'smemory
大概意思也就是Ext.Fly采用flyweight模式使所有fly出来的元素共享内存,可以提高程序执行速度,减少内存占用。
这段话激起了我对这个函数的兴趣,毕竟近段时间一直在搞JS性能优化相关问题,对“内存”这个字眼非常敏感。大概看了下Ext源码对get和fly实现的部分,然后在网上查看了一些资料,终于对他们之间的异同有了个比较深入的认识。
Ext的官方开发人员给出了如下的解释:
Ext.ElementwrapsalotoffunctionalityaroundDOMelement/node,forexamplefunctionslikehide,show,allanimationstuff,dimensionsgettingandsettingfunctionandalotmore.
Ext.ElementkeepsreferencetoDOMelementitiswrappedaroundindomproperty.OnceyouhaveanExt.Element(e.g.youcallExt.get('some-id')itisaninstanceofElementclassandyoucanworkwithitassuch.
Now,imaginethatyouneedtohide1000DOMnodes,youcall1000timesExt.get('some-one-of-1000-id').hide()soyoucreate1000instancesofElementjusttocallonefunction:hide.
Ext.flyisoneinstanceofExt.Elementwith"replaceable"DOMnodeitiswrappedaround.Ifyoucall1000timesExt.fly('some-one-of-1000-id').hide()you1000timesreplacedompropertyofoneinstanceofExt.Element.
Result:higherperformance,lowermemoryusage.
YouonlyneedtokeepinmindthatyoucannotkeepElementreturnedbyExt.flyforlateruseasit'sdomwillsoonerorlatergetsreplacedbyanotherone.
这段话中,大致的意思如下:
Ext.Element是Ext对Dom元素的一个强有力封装,它封装了很多方便对dom操作的接口(并通过Element的dom属性引用对应的
dom元素),因此每创建一个Element元素都将消耗不少的内存(主要是大量的操作接口消耗),因此如果创建过多的Element元素必然导致内存占
用的剧增和系统性能的下降。
Ext.get和Ext.fly返回的都是一个Element对象,但是Ext.get返回的是一个独立的Element,拥有自己独立的操作接口
封装,可以将其返回值保存到变量中,以便以后调用操作等,这样为重用带来了方便。但是它的一个很大缺点就是内存消耗问题,假如调用
Ext.get(id)1000次,则会在内存中创建1000个独立Element,其内存占用可想而知。但是很多时候我们可能仅仅只是对该dom元素执
行一次很简单的操作,如隐藏(hide),这样如果每次都创建一个独立Element放在内存中,实在是对内存的巨大浪费,因此当我们在只需要执行一次操
作或者一个很简单的操作时,采用Ext.get就显得很不合理。Ext.fly正是为了解决这个问题而出现,它通过使每次创建的Element共享内存中
的一套操作接口来达到节省内存的效果。
下面来看Ext.fly的实现代码(我简单加了一些注释):
var
flyFn=function
(){};
flyFn.prototype
=El.prototype
;
var
_cls=new
flyFn();//将Element的所有操作接口放在_cls中
//domisoptional
El.Flyweight=function
(dom){
this
.dom=dom;
};//仅包含一个dom属性的Object
El.Flyweight.prototype
=_cls;//将操作接口复制给Element实例对象
El.Flyweight.prototype
.isFlyweight=true
;//标志该Element是flyweight对象
El._flyweights={};//flyweight对象缓存容器
El.fly=function
(el,named){
named=named||'_global'
;
el=Ext.getDom(el);//取得dom对象
if
(!el){
return
null
;
}
if
(!El._flyweights[named]){
El._flyweights[named]=new
El.Flyweight();//仅在第一次调用Ext.fly时创建一个Flyweight对象并缓存
}
El._flyweights[named].dom=el;//将flyweight对象的dom属性指向该el
return
El._flyweights[named];
};
从上面的代码不难看出,仅在第一次调用Ext.fly时创建一个Flyweight对象(该对象包含了Element的所有操作接口)并将其缓存,
之后的所有fly操作都只是修改该flyweight对象的dom属性,每次fly返回的结果都是共享的同一个flyweight对象。这样每次fly返
回的Element相比Ext.get而言,减少了每次创建Element时对大量的操作接口的创建。所有fly的对象都共享一套Element操作接
口,内存占用自然少了很多,而且执行速度也得到了提升。在大量的创建操作中效果会更加明显。
由于fly的操作原理,我们不能将fly的返回结果保存在变量中以便重用,因为每次fly操作都将可能改变该变量的dom指向。如下面的代码就是不正确的:
var
my_id=Ext.fly('my_id'
);
Ext.fly('another_id'
);//此时my_id的dom引用已经变为another_id
my_id.highlight('FF0000'
,{//此处的操作将是对another_id元素的操作
endColor:'0000FF'
,duration:3
});
在以后使用中,一定要合理的利用Ext.get和Ext.fly,避免滥用Ext.get这个“重量级”的方法。
分享到:
相关推荐
### Ext.get与Ext.fly的区别 在Ext JS框架中,`Ext.get`和`Ext.fly`是两个非常重要的方法,它们主要用于操作DOM元素。理解这两个方法之间的区别以及如何使用它们对于开发高质量、高效率的应用程序至关重要。 #### ...
在EXTJS这个强大的JavaScript框架中,`Ext.get`和`Ext.fly`是两个非常重要的方法,它们都用于操作DOM元素,但它们之间存在着微妙的差异。了解这些差异对于优化代码性能和理解EXTJS的工作机制至关重要。 首先,`Ext....
`Ext.fly`是另一个与`Ext.get`相似但略有不同的方法,它主要用于一次性操作DOM元素,可以减少内存消耗,适用于只需要执行一次操作的情况。 学习Ext.js不仅是学习其API和组件,更重要的是理解其背后的MVC(Model-...
`Ext.fly`函数类似,但它的设计目的是快速执行一次性的DOM操作,而不需要保留对元素的引用,适合一次性操作的场景。 在Ext.js中,DOM操作是非常重要的部分。`Ext.get`和`Ext.getBody`是两个常用的DOM访问方法,前者...
6.5.2 ext.dom.compositeelement与ext.dom.compositeelementlite的区别 / 279 6.5.3 操作元素集合 / 279 6.6 综合实例:可折叠的面板accordion / 280 6.7 本章小结 / 283 第7章 数据交互 / 284 7.1 数据交互...
1.Ext.get var el = Ext.get('myElementId');//获取元素,等同于document.getElementById('myElementId');//会缓存 2. Ext.fly var el = Ext.fly('myElementId')//不需要缓存。 注:享元模式(Flyweight Design ...
例如,`Ext.getDom('elId')`用于通过ID查找DOM节点,而`Ext.getDom(elDom)`则用于通过现有DOM节点查找DOM节点。 接下来,我们讨论EXT中的一些CSS元素操作: 4. **addClass**:使用`Ext.fly('elId').addClass('...
本篇学习笔记将深入探讨`Ext.Element`类,包括`Ext.fly`和`Ext.get`的区别以及如何使用`Ext.Element`进行各种DOM操作。 首先,`Ext.fly` 和 `Ext.get` 都是用来获取`Ext.Element`对象的方法,但它们之间存在一些...
`Ext.get`和`Ext.fly`方法用于获取Element实例,`Ext.query`则类似于jQuery的`$`,用于选取DOM元素。Element对象还支持事件监听和动画效果。 3. **基本数据类型扩展**:EXT JS扩展了JavaScript的基本数据类型,如...
**Ext.Ajax**是ExtJS框架中的一个核心组件,用于实现与服务器的异步通信,即Ajax请求。这一功能对于构建动态、响应式和交互式的Web应用至关重要。Ext.Ajax提供了一套封装良好的API,使得开发者能够更轻松地管理HTTP...
文章最后提到了Ext类的一些常用方法,如addBehaviors、apply、applyIf、decode、destroy、each、encode、escapeRe、extend、fly、get、getBody、getCmp等。这些方法提供了丰富的功能,如事件绑定、对象拷贝、JSON...
例如,`Ext.get()`方法用于获取DOM元素,`Ext.fly()`则允许快速访问并执行一次操作,而无需创建DOM选择器对象。此外,还有用于添加和删除类名、设置样式属性以及处理事件的方法。 **三、事件处理** Ext Core 提供了...
row = Ext.fly(rowNode, '_rowExpander'), nextBd = row.down(me.rowBodyTrSelector, true), isCollapsed = row.hasCls(me.rowCollapsedCls), addOrRemoveCls = isCollapsed ? 'removeCls' : 'addCls', ...
var el = Ext.fly('some-element', 'named'); // 获取带有ID "some-element" 的浮动元素 ``` ##### 11. `get(Mixed el):Element` - **功能**:获取一个Element对象。 - **参数**: - `el`:可以是ID、DOM节点或...
例如,`Ext.getBody()`可以获取当前文档的body对象,`Ext.getDom()`则可以由ID或DOM节点获取对应的DOM元素。 2. **addBehaviors**: 这个方法用于批量添加事件监听器。它允许你使用一种简洁的方式来为多个选择器绑定...
### Ext JS 2.1 核心 API 详解 #### 1. `addBehaviors(Object obj):void` 此方法用于向指定的 DOM 元素添加事件监听器。它接受一个对象作为参数,其中键为事件选择器(selector),值为对应的事件处理函数。 **...