




已阅读5页,还剩261页未读, 继续免费阅读
版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
使用Ext.extend进行继承的一个有趣的问题 在Ext的使用过程中,偶然发现了一个有趣的问题, 和大家共享一下。 先看如下代码:/ 定义一个基类, 一个数组成员arr,和一个空函数initvar BaseClass = Ext.extend(Ext.util.Observable, arr: ,init: Ext.emptyFn);/ 定义一个子类,继承自BaseClass,并重写init方法, 向数组arr中添加一个1var SubClass1 = Ext.extend(BaseClass, init: function() this.arr.push(1););/ 再定义一个子类, 也继承自BaseClass,并重写init方法, 向数组arr中添加一个2var SubClass2 = Ext.extend(BaseClass, init: function() this.arr.push(2););function extTest() var c1 = new SubClass1();c1.init();alert(c1.arr); / 这里得到的应该是1, 结果也确实是1, 没错var c2 = new SubClass2();c2.init();alert(c2.arr); / 这里得到的应该是一个2, 但是实际结果却是1,2 ,有趣的问题出现了在执行extTest函数时,收到的两个alert分别是1和1,2 ,而且,如果不断的执行extTest函数,得到的值会不断的增加, 这是什么原因呢?问题肯定是处在Ext.extend方法上,加载debug版本的脚本, 对这个方法进行单步跟踪,发现最终问题出现在Ext.override函数上, 看图:看来在那个for循环之中,只是将overrides中的各个属性进行简单赋值操作, 但是,对于本例中出现的数组, 赋值只能传递对数组的引用, 也就是说SubClass1和SubClass2将共享一个数组,因为他们引用的是同一个数组,怪不得得到的结果会与期望的不一致呢。当然, 对于上面的代码适当进行修改, 既可以得到预期的值var BaseClass = Ext.extend(Ext.util.Observable, arr: null,init: function() this.arr = ; / init arr here.);var SubClass1 = Ext.extend(BaseClass, init: function() SubClass1.superclass.init.call(this); / call base class s init function this.arr.push(1););var SubClass2 = Ext.extend(BaseClass, init: function() SubClass2.superclass.init.call(this); / call base class s init functionthis.arr.push(2););function extTest() var c1 = new SubClass1();c1.init();alert(c1.arr); var c2 = new SubClass2();c2.init();alert(c2.arr);虽然这只是一个很小的问题,但是却不容忽视,我就犯了一个这样的“错误”,郁闷了好长时间才发现原因, 因此给大家提个醒。Ext.extend用法以及代码解读概述Ext.extend是Ext的继承机制,这个函数的代码相当难懂。要明白这个函数的代码,首先要知道这个函数如何使用。使用方式使用示例假设有个function名为SuperClass,要实现一个子类,名为MyClass。下面的两种方式都可以实现这个功能。 MyClass = Ext.extend(SuperClass, /* */ );Ext.extend(MyClass, SuperClass, /* */);下面来个具体示例:var a = function(id) this.id = id;totype = tostring : function() return this.id; ; b = function(id) b.superclass.constructor.call(this, id);Ext.extend(b, a, tostring : function() return String.format(b:0, this.id); );/测试一下var obj1 = new a(obj1);alert(obj1.tostring();var obj2 = new b(obj2);alert(obj2.tostring();或者下面的代码,可以得到同样的效果:var a = function(id) this.id = id;totype = tostring : function() return this.id; ;b = Ext.extend(a, tostring : function() return String.format(b:0, this.id); );/测试一下var obj1 = new a(obj1);alert(obj1.tostring();var obj2 = new b(obj2);alert(obj2.tostring();一个错误例子下面看个示例:BaseClass = function() this.f1 = function() alert(f1 in base); this.f2 = function() alert(f2 in base); ChildClass = function() ChildClass.superclass.constructor.call(this); Ext.extend(ChildClass, BaseClass, f1: function() alert(f1 in child); , f3: function() alert(f3 in child); );var b = new ChildClass();b.f1();b.f2();b.f3();可以去执行一下,可以发现f1的执行结果仍然是f1 in base。并没有真正的达到override的效果。Ext.extend puts the properties specified in the 3rd argument into the subclasss prototype也就是说:第三个参数里面的函数被放置在了子类的prototype中。而在ChildClass.superclass.constructor.call(this);这句上,BaseClass的f1成了ChildClass的变量,而不是ChildCtotype。通过对JavaScript的原型继承的了解,可以知道,实例变量的优先级是高于prototype的,所以上面的这个代码是达不到override的功能的。修改的方式如下:BaseClass = function() ;BaseCtotype = f1: function() alert(f1 in base); ;代码解读JavaScript中的继承实现先了解一下最简单的继承是如何实现的:function Extend(subFn, superFn) subFtotype = new superFn() subFtotype.constructor = subFnfunction Animal() this.say1 = function() alert(Animal); function Tiger() this.say2 = function() alert(Tiger); Extend(Tiger,Animal);var tiger = new Tiger();tiger.say1();/Animaltiger.say2();/Tiger可以看到最简单的继承只做了两件事情,一是把subFn的prototype设置为superFn的一个实例,然后设置subFtotype.constructor为subFn。Ext.extend的代码Ext.extend函数中用到了Ext.override,这个函数把第二个参数中的所有对象复制到第一个对象的prototype中。首先贴上Ext.override函数的代码:Ext.override = function(origclass, overrides) if(overrides) var p = totype; for(var method in overrides) pmethod = overridesmethod; 然后贴上Ext.extend的代码:/* 继承,并由传递的值决定是否覆盖原对象的属性* 返回的对象中也增加了override()函数,用于覆盖实例的成员* param Object subclass 子类,用于继承(该类继承了父类所有属性,并最终返回该对象)* param Object superclass 父类,被继承* param Object overrides (该参数可选) 一个对象,将它本身携带的属性对子类进行覆盖* method extend*/function extend () / inline overrides var io = function(o) for(var m in o) thism = om; ; return function(sb, sp, overrides) if(typeof sp = object) overrides = sp; sp = sb; sb = function()sp.apply(this, arguments); var F = function(), sbp, spp = totype; F.prototype = spp; sbp = totype = new F(); sbp.constructor=sb; sb.superclass=spp; if(spp.constructor = Ototype.constructor) spp.constructor=sp; sb.override = function(o) Ext.override(sb, o); ; sbp.override = io; Ext.override(sb, overrides); return sb; ;();代码中进行了太多的简写,看起来不是特别方便,把代码中的简写补全,代码如下:function extend() / inline overrides var inlineOverride = function(o) for (var m in o) thism = om; ; return function(subFn, superFn, overrides) if (typeof superFn = object) /如果subFn也是对象的话(一般来说subFn这里放的是父类的构造函数),那么第三个参数overrides参数相当于被忽略掉 overrides = superFn; superFn = subFn; /subFn重新定义了函数 subFn = function() superFn.apply(this, arguments); ; var F = function() , subFnPrototype, superFnPrototype = superFtotype; F.prototype = superFnPrototype; subFnPrototype = subFtotype = new F(); subFnPrototype.constructor = subFn; subFn.superclass = superFnPrototype; if (superFnPrototype.constructor = Ototype.constructor) superFnPrototype.constructor = superFn; subFn.override = function(obj) Ext.override(subFn, obj); ; subFnPrototype.override = inlineOverride; Ext.override(subFn, overrides); return subFn; ;补全以后也不是特别容易明白,那么我们就把这个代码分开,分为2个参数和3个参数。两个参数的Ext.extend代码首先把代码改写成两个参数的。/两个参数的时候的代码,注意第二个参数必须为objectfunction extend() / inline overrides var inlineOverride = function(o) for (var m in o) thism = om; ; return function(superFn, overrides) var subFn = function() superFn.apply(this, arguments); ; var F = function() , subFnPrototype, superFnPrototype = superFtotype; F.prototype = superFnPrototype; /注意下面两句就是上面最简单的继承实现。 subFnPrototype = subFtotype = new F(); subFnPrototype.constructor = subFn; /添加了superclass属性指向superFn的Prototype subFn.superclass = superFnPrototype; /为subFn和subFnPrototype添加override函数 subFn.override = function(obj) Ext.override(subFn, obj); ; subFnPrototype.override = inlineOverride; /覆盖掉子类prototype中的属性 Ext.override(subFn, overrides); return subFn; ;从注释中可以看到,做的工作很简单,只是定义一个subFn函数,这个函数中会调用superFn函数。定义了subFn以后,就使用上面的最简单的继承方式实现继承。然后为subFn和subFn的prototype添加了一个override函数。最后的Ext.override(subFn, overrides);把overrides中的函数写入subFn的prototype中。三个参数的Ext.extend代码下面我们把函数改写为只处理3个参数的,改写后的代码如下:/三个参数时的代码function extend() / inline overrides var inlineOverride = function(o) for (var m in o) thism = om; ; return function(subFn, superFn, overrides) var F = function() , subFnPrototype, superFnPrototype = superFtotype; F.prototype = superFnPrototype; /注意下面两句就是上面最简单的继承实现。 subFnPrototype = subFtotype = new F(); subFnPrototype.constructor = subFn; /添加了superclass属性指向superFn的Prototype subFn.superclass = superFnPrototype; /为subFn和subFnPrototype添加override函数 subFn.override = function(obj) Ext.override(subFn, obj); ; subFnPrototype.override = inlineOverride; /覆盖掉子类prototype中的属性 Ext.override(subFn, overrides); return subFn; ;过程与两个参数的时候相差无几,只是两个参数的时候,subFn时重新定义的一个function,而三个参数的时候,这个步骤就省略了。总结及说明这样大家就对这个函数很明白了吧,也可以知道Ext.extend的继承只会覆写构造函数prototype中的对象,使用的时候需要多加注意。注意下面一段代码:if (superFnPrototype.constructor = Ototype.constructor) superFnPrototype.constructor = superFn;这段代码我在改写的Ext.extend中省略掉了。原因在于我尝试了多次,发现参数为两个参数的时候,只有第一个参数为Object对象或者为3个参数的时候,第二个参数为Object才会进入此段代码。但是发现superFn也时function Object(),在IE和FF下都是如此。那么我就不是很清楚这段代码到底是什么用的了,若有清楚的,告诉一声,哈。YUI 拖放支持上一篇 / 下一篇 2007-10-13 15:28:51 / 个人分类:AJAX技术 查看( 9 ) / 评论( 0 ) / 评分( 0 / 0 ) 要支持拖放功能,必须包含如下脚本文件。!- Namespacesourcefile - script !- Dependencysourcefiles - script script !- DragandDropsourcefile - script 基本拖放功能YAHOO.util.DD要对任何一个DOM元素启用拖放功能,只需要创建一个的实例,提供需要支持拖放的元素ID,也可以提供一个元素对象。var dd1 = new YAHOO.util.DD( element1 );/ alternatively,useanelementreference / varel=YAHOO.util.Dom.get(element1); / vardd1=newYAHOO.util.DD(el); 上述代码使元素element1可以支持拖放。现在这个元素可以在页面上移动,这是通过改变元素的样式属性实现的,DOM元素的实际位置并没有改变。YAHOO.util.DDProxy许多拖放实现中在鼠标移动时,都不会移动需要被拖动的元素,因为需要被拖动的元素通常比较大。一个解决方法是使用一个代理元素,通常是一个小一些元素,在鼠标移动时跟着移动。YUL使实现此功能非常容易,只需要实例化一个YAHOO.util.DDProxy而不是一个YAHOO.util.DD即可。var dd2 = new YAHOO.util.DDProxy( element2 );这种情况下,元素element2可以拖动,但是响应拖动事件时,实际上是YUL拖放组件自动创建的代理元素在移动,可以参考API documentation for YAHOO.util.DDProxy 获取更多关于如何访问和样式代理元素的信息。当element2放置到目标位置时,代理元素将被隐藏。YAHOO.util.DDTarget这个对象表示拖放目标元素,但是他们本身是不可以拖动的。var dd3 = new YAHOO.util.DDTarget( element3 );上述示例中,element3是一个拖放目标对象,但是用来不能拖动element3。使用拖放功能拖放管理器YAHOO.util.DragDropMgr也可以简写为YAHOO.util.DDM,是一个单例对象,主要功能是管理页面中的拖放操作。拖放管理器控制许多关键的设置,用来配置拖放交互,比如当一个鼠标事件成为一个拖动事件的延迟时间。/ setsthetimedelaybetweenamousedownanda / drageventto1200milliseconds: YAHOO.util.DragDropMgr.clickTimeThresh = 1200 ; API documentation for this object可以获取更多选项设置信息。使用交互组每个拖放对象都属性一个或多个组。拖放事件只有在被拖动的元素和目标元素在一个组时才会激活。如果创建拖放对象时,在构造函数中没有指定组信息,将使用default组。/ Nogroupspecifiedsodd0isassignedtothedefaultgroup var dd0 = new YAHOO.util.DD( elementid0 );/ dd1isamemberofgroup1 var dd1 = new YAHOO.util.DD( elementid1 , group1 );/ dd2isamemberofgroup2 var dd2 = new YAHOO.util.DD( elementid2 , group2 );/ dd3isamemberofbothgroup1andgroup2 var dd3 = new YAHOO.util.DD( elementid3 , group1 );dd3.addToGroup( group2 );/ groupscanberemovedviascriptaswell: dd1.removeFromGroup( group1 );可选的配置参数拖放对象构造函数中还可以提供一个可选的参数,是一个包含配置信息的对象。下面的示例演示了如何使用这个参数对象来指定一个已经存在的HTML元素作为拖动代理,而不是使用缺省的拖动代理。 var dd = new YAHOO.example.DDProxy( dragDiv1 , proxytest , dragElId: existingProxyDiv )当前支持如下的配置属性: YAHOO.util.DragDrop: padding, isTarget, maintainOffset, primaryButtonOnly YAHOO.util.DD (包括YAHOO.util.DragDrop可用属性): scroll YAHOO.util.DDProxy (包括 YAHOO.util.DD可用属性): resizeFrame, centerFrame, dragElId 所有这些属性都可以通过类的属性进行访问,详情参见API文档 。Interesting Moments大多数情况下,拖放支持都要求写代码响应交互过程中的关键事件。当开始拖动时,当拖动一个对象进入另一个对象时等等。YUL的拖放支持提供事件激活方法,可以提供自定义的实现来决定当这些事件发生时的处理方式。事件描述onMouseDown鼠标事件,鼠标事件不总是会导致一个拖动操作。startDrag当鼠标按下事件的阀值达到时激活开始拖动事件,缺省的设置是鼠标移动3个像素或者保持鼠标按下1秒会激发此事件。onDrag当拖动过程中每次鼠标移动都激发此事件。onDragEnter当被拖动的对象第一次和另一个目标对象相交时激活。 onDragOver当被拖动的对象经过另一个目标对象过程中每次鼠标移动都激活此事件。onDragOut当被拖动的对象离开刚才进行的目标对象时激活此事件。onDragDrop当被拖动的对象落到目标对象时激活此事件。onInvalidDrop当被拖动的对象落在一个无效的目标对象时激活此事件。endDrag 在拖动开始后鼠标释放时激活此事件。onMouseUp无论是否拖动是否开始鼠标释放时都激活此事件。点模式和相交模式缺省拖放过程中,两个对象是否相交是通过鼠标的位置来定义的(点模式)。相交模式会考虑被拖动元素的尺寸.可以在任何时候通过设置YAHOO.util.DDM.mode 属性值为YAHOO.util.DDM.INTERSECT改变缺省设置。/ setDragandDroptoIntersectmode: YAHOO.util.DDM.mode = YAHOO.util.DDM.INTERSECT;/ setDragandDroptoPointmode(default): YAHOO.util.DDM.mode = YAHOO.util.DDM.POINT;使用相交模式的主要特性是可能会导致在一次拖动事件中同时有多个拖放对象相互压盖。这意味着onDragEnter事件,特别是onDragOver事件可能被激活多次。点模式和相交模式的根本区别是点模式返回目标拖放对象的id,而相交模式会返回拖放对象的id数组。点模式情况下,当一个被拖放对象进入两个堆起来的目标元素时,会激发两次onDragDrop事件,相交模式时只会激发一个事件,但是会返回一个目标对象的数组。性能问题响应事件时应用程序的逻辑复杂性可能造成显著的性能影响,特别是响应onDrag,onDragOver事件时,因此通常需要优化你的 onDrag 和onDragOver事件处理代码。获取和设置元素的位置是拖放操作的一个基本操作,元素在DOM层级越深,成本越高,因此如果你遇到性能问题,考虑使用YAHOO.util.DDProxy 代替YAHOO.util.DD,代理元素是绝对定位在页面中的,因此要求少一些的循环来获取位置信息。YAHOO.util.DragDropMgr提供创建拖拽应用的框架startX,startY用于计算拖动的距离是否满足触发startDrop事件的条件。deltaX,deltaY记录mousedown事件相对于linked元素的位移,用于实现令拖动元素相对于鼠标静止移动的效果。dragOvers通过此集合内容的变化能判断出当前DD对象与其它DD对象的交互情况(dragEnter、dragOver和dragOut)。fireEvents(e, isDrop)触发拖拽模块中的场景事件它主要是通过判断当前DD对象和其它DD对象位置上的关系来触发当前DD对象的dragEnter、dragOver、dragOut、dragDrop和invalidDrop等事件;在handleMouseMove和handleMouseUp方法中分别被调用。被handleMouseUp方法调用时isDrop为真,此时当前DD只会触发dragDrop而不是dragEnter或dragOver。当isDrop为假时反之。dragOut在两种情况下都有可能触发。每次document上的mousemove和mouseup事件触发时都可能被调用,要注意其对性能的影响。isOverTarget(pt, oTarget, intersect, curRegion)判断oTarget当前是否被覆盖了缓存oTarget的linked元素的Region,useCache控制是否每次都重新计算一次Region;如果当前拖动对象为空,或者交互模式是点模式而且没有任何区域限制,则返回pt是否在oTarget上;否则,返回当前拖动元素在constraint和tick影响下的Region是否与oTarget有交集。startDrag(x, y)触发startDrag事件的方法触发当前DD对象的b4StartDrag和startDrag事件。stopDrag(e, silent)触发endDrag事件的方法触发b4EndDrag、endDrag和mouseUp事件;清空“当前拖动对象”和“当前覆盖对象列表”两个状态。handleMouseDown(e, oDD)计算deltaX和deltaY的值;创建一个timer,在一段时间后触发dragStart事件,这个时间默认是一秒。这个timer可能会在其它事件触发时被清除。handleMouseMove(e)在document范围中监听mousemove事件当拖动时鼠标超出window边界时,调用handleMouseUp。在IE中当这种情况发生时,mousemove事件中的按键状态会从按下变成放开;但在其它浏览器中暂没方法检测这种情况;利用startX和startY判断当前拖动的距离是否满足触发startDrag的条件;触发当前DD对象的b4Drag、drag事件并调用fireEvents。handleMouseUp(e)在document范围中监听mouseup事件不明白为什么如果startDrag事件通过handleMouseDown中创建的timer触发时,要先调用一次handleMouseMove。注释说是为了得到dragOver事件,但为什么要得到这个事件呢?调用fireEvents方法;触发endDrag事件。getBes*tch(dds)在dds中找到一个最适合的dd首先看哪个DD是在光标下的;如果没有DD在光标下的,则看那个DD与当前拖动DD的相交面积最大。refreshCache(groups)刷新DD对象linked元素位置的缓存如果groups为空,则刷新所有DD对象的缓存。handleWasClicked(node, id)判断node是否为id所指DD对象的拖动柄在node和它的所有父节元素上用isHandle方法测试。getLocation(oDD)返回oDD的linked元素的Regionverify(el)检测el是否在DOM中lock()锁定unlock()解锁isLocked()判断锁regDragDrop(oDD, sGroup)注册DD对象在DragDrop.init中被调用。removeDDFromGroup(oDD, sGroup)注销DD对象在DragDrop.removeFromGroup中被调用,文档建议不要直接调用。unregAll()调用所有DD对象的unreg方法regHandle(sDDId, sHandleId)注册DD的拖动柄在DragDrop.setHandleElId中被调用。isDragDrop(id)判断是否是已注册的DD对象getRelated(p_oDD, bTargetsOnly)获取相关的DD对象isLegalTarget(oDD, oTargetDD)判断oTargetDD是否为oDD的合法目标isTypeOfDD(oDD)判断oDD是否为DD对象内部保存了一个_ygDragDrop属性作为DD对象的标示。ishandle(sDDId, sHandleId)判断拖动柄getDDById(id)根据id获取DD对象stopEvent(e)阻止事件传播和默认事件主要是根据stopPropagation和preventEvent两个布尔属性判断是否进行相应处理。swapNode(n1, n2)交换两个元素的位置_addListeners()使此模块可以在Event之前加载而不出错如果Event和document都已经加载了,调用_onLoad;否则,它会每10毫秒尝试调用自身一次,如果document加载完成后再尝试2000次都没有检测到Event则放弃。_onLoad()调用init;分别在document的mouseup、mousemove和window的unload、resize上注册相应方法。_onResize()调用所有DD对象的resetConstraints方法_remove(oDD)注销DD对象在DragDrop.unreg中被调用,文档建议不要直接调用。_onUnload()unload事件处理方法,调用unregAllYAHOO.util.DragDrop为拖拽提供基本操作和接口linked元素:定义与其他DD对象交互的边界;handle元素:拖动柄;drag元素:跟随光标移动的元素;b4为前缀的函数主要用于写基类;它通过augment继承了EventProvider的功能。on与subscribe等价DragDrop(id, sGroup, config)构造函数调用init。getEl()返回linked元素getDragEl()返回drag元素init(id, sGroup, config)调用initTarget;把handleMouseDown注册到id的mousedown事件;创建config.events中声明的事件对象。getTargetCoord(iPageX, iPageY)计算拖动元素的正确位置用deltaX和deltaY计算保持鼠标相对于拖动元素静止的坐标;用constraint和tick修正坐标。initTarget(id, sGroup, config)初始化把handleOnAvailable注册在id的available事件中;在不能触发startDrag的元素类型列表中加入A;调用applyConfig。applyConfig()根据构造方法的配置参数设置初始化对象状态handleOnAvailable()available事件的处理器调用resetConstraints和onAvailable。setPadding(iTop, iRight, iBot, iLeft)设置内边距setInitPosition(diffX, diffY)保存linked元素的初始位置把现在的坐标减去diff得到初始坐标;调用setStartPosition。setStartPosition(pos)设置起始位置把现在的坐标减去diff得到初始坐标;调用setStartPosition。addToGroup(sGroup)加入组removeFromGroup(sGroup)退出组清除对象自身的状态和DDM的状态。setDragElId(id)设置drag元素setHandleElId(id)设置在linked元素中的拖动柄如果id是一个dom元素且没有id属性,则为之生成;在DDM中注册此拖动柄。setOuterHandleElId(id)设置在linked元素外的拖动柄如果id是一个dom元素且没有id属性,则为之生成;在id的mousedown事件上注册handleMouseDown;在DDM中注册此拖动柄。unreg()注销此DD对象注销此DD对象linked元素的mousedown事件;在DDM中注销此对象。isLock()判断锁先检测DDM中的lock再检测自身。handleMouseDown(e, oDD)linked元素的mousedown事件的处理方法根据primaryButtonOnly判断鼠标的按键类型是否正确;判断锁状态;触发b4MouseDown和mouseDown事件,如果其中有一个返回false,则此方法立刻返回;刷新DDM中与此DD对象同组的DD对象的位置信息缓存;如果是合法的点击,保存此时的DD位置作为startDrag的起始位置并调用DDM的handleMouseDown。clickValidator(e)判断点击是否合法根据非法点击元素列表和DDM的wasValidClicked判断合法性。getTargetCoord(iPageX, iPageY)返回修正坐标通过delta、constraint和tic
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 2025年事业单位工勤技能-河南-河南农业技术员一级(高级技师)历年参考题库典型考点含答案解析
- 2025年事业单位工勤技能-河南-河南不动产测绘员五级(初级工)历年参考题库典型考点含答案解析
- 2025年事业单位工勤技能-河北-河北医技工三级(高级工)历年参考题库含答案解析
- 2025年事业单位工勤技能-江苏-江苏药剂员一级(高级技师)历年参考题库含答案解析(5套)
- 2025年事业单位工勤技能-广西-广西计算机信息处理员五级初级历年参考题库典型考点含答案解析
- 2025年事业单位工勤技能-广西-广西信号工-机车信号设备维修三级(高级工)历年参考题库典型考点含答案解析
- 2025年事业单位工勤技能-广东-广东汽车修理工(技师/高级技师)历年参考题库含答案解析
- 2025年事业单位工勤技能-广东-广东无损探伤工三级(高级工)历年参考题库典型考点含答案解析
- 2025年事业单位工勤技能-广东-广东保健按摩师五级(初级工)历年参考题库含答案解析
- 2025年事业单位工勤技能-安徽-安徽地质勘查员五级(初级工)历年参考题库典型考点含答案解析
- 黑龙江小学生诗词大赛备考试题库400题(一二年级适用)
- 《HSK标准教程1》第4课课件
- 双J管健康宣教
- 如何提高美术课堂教学的有效性
- 茂县生活垃圾资源化综合利用项目环评报告
- 水电站新ppt课件 第一章 水轮机的类型构造及工作原理
- 护理查对制度课件
- 市政工程占道施工方案
- GB/T 39965-2021节能量前评估计算方法
- GB/T 20671.1-2006非金属垫片材料分类体系及试验方法第1部分:非金属垫片材料分类体系
- GB/T 17449-1998包装玻璃容器螺纹瓶口尺寸
评论
0/150
提交评论