﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>博客园-Meetrice EXT JS 编程资料馆 </title><link>http://www.cnblogs.com/meetrice/</link><description>编程资料馆 - 浏览器,IE,FIREFOX,FIREBUG,APTANA,SPKET,WEB,2.0,EXT,JS,AJAX,RWC,RIA,JAVASCRIPT,JSON,XML,REST</description><language>zh-cn</language><lastBuildDate>Sat, 20 Mar 2010 22:34:39 GMT</lastBuildDate><pubDate>Sat, 20 Mar 2010 22:34:39 GMT</pubDate><ttl>60</ttl><item><title>解决方案</title><link>http://www.cnblogs.com/meetrice/archive/2010/02/05/1664390.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Fri, 05 Feb 2010 06:21:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2010/02/05/1664390.html</guid><description><![CDATA[<p>阅读: 9 评论: 0 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2010-02-05 14:21 <a href="http://www.cnblogs.com/meetrice/archive/2010/02/05/1664390.html" target="_blank">原文链接</a></p><p>&nbsp;</p>
<div>&nbsp;HP解决方案中心<br />http://h20427.www2.hp.com/solutions/supermarket/cn/zh/solution.html<br /><br /><br />IBM解决方案中心<br />http://www.ibm.com/solutions/cn/zh/<br /><br />SAP解决方案中心<br />http://www.sap.com/china/solutions/index.epx<br /><br />oracle解决方案<br />http://www.oracle.com/lang/cn/solutions/index.html&nbsp;</div>
<p><br />中小企业IT网方案库&nbsp;</p>
<p>http://www.cbismb.com/solution/</p>
<p>&nbsp;</p>
<p>docin解决方案资料</p>
<p>http://www.docin.com/app/docsearch?fn=&amp;searchType_banner=p&amp;dky=解决方案</p><img src="http://www.cnblogs.com/meetrice/aggbug/1664390.html?type=1" width="1" height="1" alt=""/><p>评论: 0　<a href="http://www.cnblogs.com/meetrice/archive/2010/02/05/1664390.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2010/02/05/1664390.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item><item><title>BCB使用IMAGEEN写EXIF信息</title><link>http://www.cnblogs.com/meetrice/archive/2010/02/05/1664181.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Fri, 05 Feb 2010 02:20:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2010/02/05/1664181.html</guid><description><![CDATA[<p>阅读: 15 评论: 0 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2010-02-05 10:20 <a href="http://www.cnblogs.com/meetrice/archive/2010/02/05/1664181.html" target="_blank">原文链接</a></p><p>&nbsp;</p>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">&nbsp;&nbsp;ImageEnView1-&gt;IO-&gt;LoadFromFile("c:\\a.jpg");</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">&nbsp;&nbsp;ImageEnView1-&gt;IO-&gt;Params-&gt;JPEG_Quality = 70; &nbsp;//压缩品质因子70</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">&nbsp;&nbsp;ImageEnView1-&gt;Update();</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">&nbsp;&nbsp;ImageEnIO1-&gt;Params-&gt;EXIF_HasEXIFData = true;</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">&nbsp;&nbsp;ImageEnIO1-&gt;Params-&gt;EXIF_XPTitle = "abdd";</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">&nbsp;&nbsp;ImageEnIO1-&gt;Update();</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">&nbsp;&nbsp;ImageEnIO1-&gt;SaveToFile("d:\\6.jpg");</div>
<div></div>
<p>ImageEnView1-&gt;IO-&gt;LoadFromFile("c:\\a.jpg");</p>
<p>ImageEnIO1-&gt;Params-&gt;EXIF_HasEXIFData = true; &nbsp;</p>
<p>ImageEnIO1-&gt;Params-&gt;EXIF_XPTitle = "meetrice jpg exif test";&nbsp;&nbsp;</p>
<p>ImageEnIO1-&gt;Update();&nbsp;&nbsp;</p>
<p>ImageEnIO1-&gt;SaveToFile("d:\\a.jpg");<br /></p>
<p>在窗体上关联&nbsp;ImageEnView1和ImageEnIO1</p>
<p>&nbsp;</p><img src="http://www.cnblogs.com/meetrice/aggbug/1664181.html?type=1" width="1" height="1" alt=""/><p>评论: 0　<a href="http://www.cnblogs.com/meetrice/archive/2010/02/05/1664181.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2010/02/05/1664181.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item><item><title>C++Builder中开发Activex</title><link>http://www.cnblogs.com/meetrice/archive/2010/01/20/1652468.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Wed, 20 Jan 2010 07:46:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2010/01/20/1652468.html</guid><description><![CDATA[<p>阅读: 32 评论: 0 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2010-01-20 15:46 <a href="http://www.cnblogs.com/meetrice/archive/2010/01/20/1652468.html" target="_blank">原文链接</a></p><p style="line-height: 23px; margin: 10px 0px; color: #3d3007">1.创建自己的ActiveX控件   <br style="line-height: 23px" />C++Buider开发ActiveX的功能非常强，但是这方面的资料却比较少，本人经过摸索终于搞定了创建Web方式Activex的基本方法    <br style="line-height: 23px" />⑴打开BCB6,新建一个Activex工程,选择时注意选择ActiveX标签页的Active Form    <br style="line-height: 23px" />⑵在弹出的对话框中设置ActiveX Name为&#160; ActFrm,后面的实现单元和工程名都会自动更改    <br style="line-height: 23px" />⑶勾选Make Control Licensed和Include Version Information,确定之后会出现一个和标准Form类似的    <br style="line-height: 23px" />⑷在C++Builder自动创建的窗体上面添加一个按钮,随便实现一些功能，如ShowMessage(&quot;点击了按钮&quot;);</p>  <p style="line-height: 23px; margin: 10px 0px; color: #3d3007">⑸设置Package相关参数。你肯定希望自己创建的ocx文件不依赖本机的开发环境，因此必须对编译器作适当的设置   <br style="line-height: 23px" /> ⅠProject-&gt;Option-&gt;Packages去掉<span style="line-height: 23px; color: #ff0000">Build With Runtime Packages</span> 前面的勾    <br style="line-height: 23px" /> ⅡProject-&gt;Option-&gt;Linker&#160; 去掉<span style="line-height: 23px; color: #ff0000">动态RTL</span>前面的勾,这样你产生的ocx文件就不会依赖BCB的开发环境了    <br style="line-height: 23px" />好了做完上面的步骤，一个简单的Activex就创建完成了,可以选择Run菜单下的Register ActiveX Server进行注册,你就可以看到你的开发成果了,如果需要发布到互联网上，通过浏览器进行注册的话，那就需要做下面的设置    <br style="line-height: 23px" />⑹设置Web Deployment Options    <br style="line-height: 23px" />&#160; 点击Web Deployment Options菜单，出现Web Deployment 选项设置窗口,有三个属性页    <br style="line-height: 23px" />&#160; Ⅰ Project主要用于设置Activex文件的位置信息    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160; ①Target dir(Full path of the deployed OCX) 设置OCX目录，也就是在选择Project-&gt;WebDeploy之后ocx文件将要拷贝到的目录,我们可以在当前工程下建立一个punlished目录作为发布目录    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160; e.g:当前工程目录为f:\projscts\firstocx&#160; 发布目录为f:\projscts\firstocx\published(也就是Target dir)    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160; ②Target&#160; URL( Virtual path of the deployed OCX)    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160; 如果客户端没有安装我们制作的activex控件,浏览器会自动到指定的网址进行寻找    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160; e.g:本机IP192.168.0.228 端口 8080 虚拟目录 myapp(使用的Web服务器是Tomcat,myapp也就是D:\Tomcat\webapps下的目录)    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160; 此处输入http://192.168.0.228:8080/myapp/    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160; ③HTML dir(Full path of the deployed HTML file)    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160; 和Activex文件配套的html文件的存放位置,这里可以把它设置成f:\projscts\firstocx\published,主要是为了方便管理    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160; 在General Options下勾选一下四项    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160; a.Use&#160; CAB file compression&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160; b.Deploy&#160; required packages    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160; c.Include file&#160; version number&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160; d.Deploy additional&#160; files    <br style="line-height: 23px" />&#160; ⅡPackages 这个页面用于发布控件中用到的额外的包，因为我们在第(5)步中已经去掉了额外的包，所以这一页为空    <br style="line-height: 23px" />&#160; ⅢAdditonal Files,这一页用于发布其它文件,至于ocx文件有没有用到其它的文件我们可以使用vc++带的工具 Dependency Walker来进行查看,根据<span style="line-height: 23px; color: #ff0000">Dependency Walker</span>的显示结果我们知道ocx使用到的dll文件在windows的目录下已经存在，没有必要随我们的ocx文件一起发布    <br style="line-height: 23px" />&#160;&#160;&#160; 但是由于我们制作控件的时候选择了Make Control Licensed，所以随包一起发布的应该还有一个lic文件，这个文件在工程目录下,我们在Additonal Files页中点击Add将lic文件包含进来就可以了    <br style="line-height: 23px" />&#160;&#160;&#160; 这个lic文件让我做控件走了不少弯路,开发出来的控件在本地可以运行良好(也就是在c++builder的run菜单里面使用register Activex server注册 ),但是一旦移到其它位置总是不能成功,而且最开始的时候也不知道使用vc++带的<span style="line-height: 23px; color: #ff0000">ActiveX Control Test Container</span>工具来测试已经生成的ocx控件    <br style="line-height: 23px" />恩,点击WebDeploy菜单就大功告成了么?没有。如果我们将published目录下的内容全部拷贝到tomcat的myapp目录下，然后将IE的安全等级调到最低，我们仍然无法浏览刚才生成的ActiveX控件，浏览器窗口上面始终显示一把红叉。真让人泄气    <br style="line-height: 23px" />不过不要放弃,我们继续进行第2步    <br style="line-height: 23px" />2.实现IObjectSafety    <br style="line-height: 23px" />&#160; 在IE6以及更高版本的浏览器中我们还必须实现IObjectSafety接口才能保证自己开发的ocx控件不会被IE禁用    <br style="line-height: 23px" />&#160; 怎么实现呢？其实很简单，加上几句话就可以了    <br style="line-height: 23px" />&#160; ①打开ActFrm的头文件,我们最开始的时候已经在这个Form上面加了一个按钮,打开它的头文件后可以看到一个类class TAcFrm&#160; 不要管它,跟它没有什么关系，接着往下看，可以看到类似    <br style="line-height: 23px" />&#160; class ATL_NO_VTABLE TActFrmImpl:    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160; VCLCONTROL_IMPL(TActFrmImpl, ActFrm ..........)之类的代码,我们在括号之后再给他加个接口    <br style="line-height: 23px" />&#160; 加完之后类似这样    <br style="line-height: 23px" />&#160;&#160; class ATL_NO_VTABLE TActFrmImpl:    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160; VCLCONTROL_IMPL(TActFrmImpl, ActFrm ..........)<span style="line-height: 23px; color: #ff0000">,</span><span style="line-height: 23px; color: #ff0000">public IObjectSafetyImpl&lt;TActFrmImpl,INTERFACESAFE_FOR_UNTRUSTED_CALLER&gt;</span>    <br style="line-height: 23px" />&#160; 注意不要丢了public前面的逗号,多重继承必须的    <br style="line-height: 23px" />&#160; ②然后再 void InitializeControl(){}函数结束之后加入    <br style="line-height: 23px" /><span style="line-height: 23px; background-color: #ff0000"><span style="line-height: 23px; background-color: #ffffff; color: #ff0000">&#160; BEGIN_CATEGORY_MAP(TActFrmImpl)       <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160; IMPLEMENTED_CATEGORY(CATID_SafeForScripting)        <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160; IMPLEMENTED_CATEGORY(CATID_SafeForInitializing)        <br style="line-height: 23px" />&#160; END_CATEGORY_MAP()</span>      <br style="line-height: 23px" /></span>&#160; ③BEGIN_COM_MAP(TActFrmImpl)    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160; VCL_CONTROL_COM_INTERFACE_ENTRIES(IActiveFrmX)    <br style="line-height: 23px" />&#160;&#160;&#160;&#160; <span style="line-height: 23px; color: #ff0000"> COM_INTERFACE_ENTRY(IObjectSafety)</span>//加入这样一行就ok了    <br style="line-height: 23px" />&#160;&#160; END_COM_MAP()    <br style="line-height: 23px" />&#160; 编译通过,应该没有问题    <br style="line-height: 23px" />3.添加自定义的方法（接口）    <br style="line-height: 23px" />&#160; 我们做的ActiveX控件应该要能够与javascript之类的脚本进行交互,所以我们在控件中要实现自己的接口    <br style="line-height: 23px" />&#160; 选择菜单view-&gt;type library出现tlb文件的浏览窗口,这里面有一大堆的东西，都不要管它，我们直奔主题，找到IActFrm点击右键新建一个方法,就叫做ShowValue吧    <br style="line-height: 23px" />&#160; 在改方法的parameters页中给这个方法添加一个参数,参数名使用longvalue，参数类型使用variant,点击刷新按钮C++builder将自动给我们添加一个叫做ShowValue的方法,参数类型都设置好了，我们在这个函数里面添加ShowMessage(longvalue.iVal);    <br style="line-height: 23px" />&#160; 然后在ocx对应的htm文件中添加相应的js代码    <br style="line-height: 23px" />&#160; 默认生成的htm文件加载activex控件时是没有添加ID的，我们需要手动给它添加,假设id=&quot;myocx&quot;，然后添加一个js函数    <br style="line-height: 23px" />&#160; &lt;script language=&quot;javascript&quot;&gt;    <br style="line-height: 23px" />&#160;&#160;&#160;&#160; function testfun(){    <br style="line-height: 23px" />&#160;&#160;&#160;&#160;&#160;&#160; myocx.ShowValue(12345);    <br style="line-height: 23px" />&#160;&#160;&#160;&#160; }    <br style="line-height: 23px" />&#160; &lt;/script&gt;    <br style="line-height: 23px" />&#160; 然后在这个页面中添加一个按钮，在这个按钮的onclick事件中触发testfun函数,此处不再噜苏    <br style="line-height: 23px" />&#160; <span style="line-height: 23px; color: #ff0000">记得把这些文件拷贝到服务器上，不然会因为.inf文件找不到而导致activex不能正常显示</span>    <br style="line-height: 23px" />4.使用ActiveX Control Test Container进行测试    <br style="line-height: 23px" />&#160; ActiveX Control Test Container是个好东西，没有它，我还真不知道我编写的activex控件那里有问题呐    <br style="line-height: 23px" />&#160; 这个工具随vc++一起安装，使用起来非常简单,打开之后选择edit-&gt;insert new control从控件列表中选择一个activex控件就可以了，这里当然是选择ActFrm罗    <br style="line-height: 23px" />5.实现数字签名    <br style="line-height: 23px" />&#160; 要是浏览器允许你任意下载activex控件的话，故事到这里也就结束了。可事实是，为了保证安全，浏览器是不会下载没有签名的控件的，如果控件没有签名，浏览器压根就不会给出任何提示，浏览器上面只有一把红叉    <br style="line-height: 23px" />&#160; ie有点残忍哈    <br style="line-height: 23px" />&#160; 没关系，自己Diy一个签名就可以让浏览器给出下载提示框了。    <br style="line-height: 23px" />&#160; 制作签名需要下面这些工具 makecert signcode cert2spc还有如果你需要自己打包ocx的话需要iexpress工具，这个工具在windows安装目录里面有    <br style="line-height: 23px" />&#160; 前面三个工具可以从微软的官方站点获取    <br style="line-height: 23px" />&#160; 手工编写一个bat文件(主要是不习惯一遍又一遍地敲命令),将这个bat文件放到f:\projscts\firstocx\published目录下    <br style="line-height: 23px" />&#160; makecert /sv &quot;ActFrmProj1.PVK&quot; /n &quot;CN=公司名称,E=email,O=作者&quot; ActFrmProj1.cer    <br style="line-height: 23px" />&#160; cert2spc ActFrmProj1.cer ActFrmProj1.spc    <br style="line-height: 23px" />&#160; signcode    <br style="line-height: 23px" />&#160; 当然要用到这三条命令的话你必须将这三个文件的路径加入到windows环境变量path中去    <br style="line-height: 23px" />&#160; 第一条命令产生ActFrmProj1.cer 和 ActFrmProj1.PVK 两个文件    <br style="line-height: 23px" />&#160; 第二步将ActFrmProj1.cer 转为ActiveProj1.spc文件    <br style="line-height: 23px" />&#160; 这个过程中会要求你输入密码,自己随便输一个，记不记得都没关系    <br style="line-height: 23px" />&#160; 第三步就是给我们生成的cab文件前面，图形界面操作很容易    <br style="line-height: 23px" />&#160; ①选择BCB自动生成的cab文件,应该在f:\projscts\firstocx\published目录下    <br style="line-height: 23px" />&#160; ②签名类型选择自定义    <br style="line-height: 23px" />&#160; ③从文件选择一个证书,这里没有其它选择只有一个文件就是f:\projscts\firstocx\published下的spc文件    <br style="line-height: 23px" />&#160; ④私钥位置选择CSP中的私钥    <br style="line-height: 23px" />&#160; ⑤密钥容器选择ActFrmPrj1.pvk,这个文件就是第一步生成的那个pvk    <br style="line-height: 23px" />&#160; ⑥算法选择md5或者sha都可以，然后在其它证书中浏览,选择我们生成的ActFrmProj1.cer搞定了    <br style="line-height: 23px" />&#160;&#160; <br style="line-height: 23px" />&#160; 然后将puulished目录下的文件全部拷贝到myapp目录下，通过浏览器进行访问， 浏览器会弹出提示问是否要安装Activex控件，当然选是呐，不然岂不是白忙活了？</p>  <p style="line-height: 23px; margin: 10px 0px; color: #3d3007">6.调试Activex的技巧   <br style="line-height: 23px" />当我们使用BCB开发控件的时候会发现F9不能运行，原因就是ocx工作方式和dll文件类似，我们可以通过设置运行参数来解决这个问题,Run-&gt;Paramters在host appliaction 中选择ie，e.g:C:\Program Files\Internet Explorer\IEXPLORE.EXE    <br style="line-height: 23px" />parameters输入如下:f:\projscts\firstocx\published\ActiveFrmProj.htm    <br style="line-height: 23px" />再按F9就可以直接运行了</p><img src="http://www.cnblogs.com/meetrice/aggbug/1652468.html?type=1" width="1" height="1" alt=""/><p>评论: 0　<a href="http://www.cnblogs.com/meetrice/archive/2010/01/20/1652468.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2010/01/20/1652468.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item><item><title>执行EXE程序出现unable to locate suitable Java runtime Environment on this machine java解决方法</title><link>http://www.cnblogs.com/meetrice/archive/2010/01/18/1650969.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Mon, 18 Jan 2010 11:30:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2010/01/18/1650969.html</guid><description><![CDATA[<p>阅读: 34 评论: 0 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2010-01-18 19:30 <a href="http://www.cnblogs.com/meetrice/archive/2010/01/18/1650969.html" target="_blank">原文链接</a></p><p>&nbsp;</p>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">Windows Registry Editor Version 5.00</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;"></div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment]</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">"CurrentVersion"="1.5"</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;"></div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;"></div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\1.5]</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">"JavaHome"="D:\\jdk1.5.0_11"</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">"RuntimeLib"="D:\\jdk1.5.0_11\\jre\bin\\client\\jvm.dll"</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">"MicroVersion"="0"</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;"></div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\1.5.0]</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">"JavaHome"="D:\\jdk1.5.0_11"</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">"MicroVersion"="0"</div>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 0px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">"RuntimeLib"="D:\\jdk1.5.0_11\\jre\bin\\client\\jvm.dll"</div>
<p>
Windows Registry Editor Version 5.00<br />[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment]"CurrentVersion"="1.5"<br /><br />[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\1.5]"JavaHome"="D:\\jdk1.5.0_11""RuntimeLib"="D:\\jdk1.5.0_11\\jre\bin\\client\\jvm.dll""MicroVersion"="0"<br />[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\1.5.0]"JavaHome"="D:\\jdk1.5.0_11""MicroVersion"="0""RuntimeLib"="D:\\jdk1.5.0_11\\jre\bin\\client\\jvm.dll"</p>
<p>&nbsp;</p><img src="http://www.cnblogs.com/meetrice/aggbug/1650969.html?type=1" width="1" height="1" alt=""/><p>评论: 0　<a href="http://www.cnblogs.com/meetrice/archive/2010/01/18/1650969.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2010/01/18/1650969.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item><item><title>BCB常见文件类型说明</title><link>http://www.cnblogs.com/meetrice/archive/2009/11/28/1612502.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Sat, 28 Nov 2009 02:31:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2009/11/28/1612502.html</guid><description><![CDATA[<p>阅读: 40 评论: 0 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2009-11-28 10:31 <a href="http://www.cnblogs.com/meetrice/archive/2009/11/28/1612502.html" target="_blank">原文链接</a></p><p>*.~*&nbsp;//备份 <br />*.bak&nbsp;//备份 <br />*.bat&nbsp;//命令行批处理文件 <br />*.tds&nbsp;//IDE环境布局配置文件，包括历史搜索项目等 <br />*.obj&nbsp;//编译后产生的目标文件 <br />*.dcu&nbsp;//Delphi源文件编译出来的目标文件 <br />*.ddp&nbsp;//Diagram(图示）文件 <br />*.tlb&nbsp;//由IDL(Interface&nbsp;Definition&nbsp;Language&nbsp;缩写)定义文件生成的类型库文件 <br />*.asm&nbsp;//汇编代码文件 <br />*.inc&nbsp;//汇编格式头文件 <br />*.hh,*.h,*.hpp&nbsp;//头文件&nbsp;*.hpp&nbsp;一般是由Delphi&nbsp;VCL转换而成 <br />*.cc,*.c,*.cpp&nbsp;//C/C++文件 <br />*.pas&nbsp;//Pascal/Delphi源文件 <br />*.dfm&nbsp;//窗体定义文件 <br />*.res&nbsp;//二进制资源文件 <br />*.reg&nbsp;//注册表定义文件 <br />*.rc&nbsp;//未编译的资源定义文件，此类文件编译后会生成.res，通常无须手动编译 <br />*.def&nbsp;//定义文件 <br />*.mak&nbsp;//低版本的工程文件 <br />*.bpr&nbsp;//工程文件(通常为UTF8编码格式) <br />*.dpr&nbsp;//Delphi&nbsp;工程文件 <br />*.bpk&nbsp;//组件包工程文件 <br />*.dpk&nbsp;//Delphi&nbsp;组件包工程文件 <br />*.dcr&nbsp;//组件图标资源文件 <br />*.str&nbsp;//资源字符串临时文件 <br />*.ico&nbsp;//标图文件 <br />*.cur&nbsp;//鼠光标文件 <br />*.ani&nbsp;//动态鼠光标文件 <br />*.sql&nbsp;//SQL&nbsp;脚本文件 <br />*.rtf&nbsp;//格式文本文件 <br />*.csv&nbsp;//带分隔符的文本型数据文件 <br />*.ini&nbsp;//配置文件 <br />*.inf&nbsp;//安装配置定义文件 <br />*.log&nbsp;//信息文件，通常为用来记录程序运行状态，从而方便跟踪调试 <br />*.cgl&nbsp;//CodeGuard&nbsp;CB自带的内存检查工具生成的信息文件 <br />*.cgi&nbsp;//网关接口可执行文件，相关请参考Web服务当中的CGI <br />*.mdb&nbsp;//Access&nbsp;数据库文件 <br />*.db&nbsp;//Borland&nbsp;Paradox&nbsp;桌面数据库表 </p><img src="http://www.cnblogs.com/meetrice/aggbug/1612502.html?type=1" width="1" height="1" alt=""/><p>评论: 0　<a href="http://www.cnblogs.com/meetrice/archive/2009/11/28/1612502.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2009/11/28/1612502.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item><item><title>&amp;lt;转&amp;gt;sqlplus常用命令使用</title><link>http://www.cnblogs.com/meetrice/archive/2009/11/25/1610714.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Wed, 25 Nov 2009 09:22:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2009/11/25/1610714.html</guid><description><![CDATA[<p>阅读: 144 评论: 0 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2009-11-25 17:22 <a href="http://www.cnblogs.com/meetrice/archive/2009/11/25/1610714.html" target="_blank">原文链接</a></p><div class="blog_content">
<p>show和set命令是两条用于维护SQL*Plus系统变量的命令<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; show all --查看所有68个系统变量值<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; show user --显示当前连接用户<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; show error　　　　　　　　　　　　　　　 --显示错误<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; set heading off --禁止输出列标题，默认值为ON<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; set feedback off --禁止显示最后一行的计数反馈信息，默认值为"对6个或更多的记录，回送ON"<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; set timing on --默认为OFF，设置查询耗时，可用来估计SQL语句的执行时间，&lt;nobr&gt;<a target="_blank" style="cursor: hand; color: #0000ff; background-color: transparent; text-decoration: underline;" class="iAs">测试</a>&lt;/nobr&gt;性能<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; set sqlprompt "SQL&gt; " --设置默认提示符，默认值就是"SQL&gt; "<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; set linesize 1000 --设置屏幕显示行宽，默认100<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; set autocommit ON --设置是否自动提交，默认为OFF<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; set pause on --默认为OFF，设置暂停，会使屏幕显示停止，等待按下ENTER键，再显示下一页<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; set arraysize 1 --默认为15<br /><br />&nbsp; &nbsp; &nbsp;SQL&gt; set long 1000 --默认为80<br /><br />&nbsp; &nbsp; &nbsp;说明：<br />&nbsp; &nbsp; &nbsp;long值默认为80，设置1000是为了显示更多的内容，因为很多数据字典视图中用到了long数据类型，如：<br /><br />SQL&gt; desc user_views<br />列名 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;可空值否 &nbsp; 类型<br />------------------------------- -------- ----<br />VIEW_NAME &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; NOT NULL VARCHAR2(30)<br />TEXT_LENGTH &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;NUMBER<br />TEXT &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; LONG<br /><br /><br /><br />命令列表： <br />假设当前执行命令为：select * from tab;<br /><br />(a)ppend　　　　 添加文本到缓冲区当前行尾　　　　a &nbsp;order by tname　结果：select * from tab order by tname;<br />　　　　　　　　　　　　　　　　　　　　　　　　　　　　　　　　　　　　　　（注：a后面跟2个空格）<br />(c)hange/old/new 在当前行用新的文本替换旧的文本　c/*/tname　　　　　结果：select tname from tab;<br />(c)hange/text　　从当前行删除文本　　　　　　　　c/tab　　　　　　　结果：select tname from ;<br />del　　　　　　　删除当前行<br />del n　　　　　　删除第n行<br />(i)nput 文本　　 在当前行之后添加一行<br />(l)ist　　　　　 显示缓冲区中所有行<br />(l)ist n　　　　 显示缓冲区中第 n 行<br />(l)ist m n　　　 显示缓冲区中 m 到 n 行<br />run　　　　　　　执行当前缓冲区的命令<br />/　　　　　　　　执行当前缓冲区的命令<br />r　　　　　　　　执行当前缓冲区的命令<br />@文件名　　　　　运行调入内存的sql文件，如：<br /><br />SQL&gt; edit s&lt;回车&gt;<br />如果当前目录下不存在s.sql文件，则系统自动生成s.sql文件，<br />在其中输入&ldquo;select * from tab;&rdquo;，存盘退出。<br /><br />SQL&gt; @s&lt;回车&gt;<br />系统会自动查询当前用户下的所有表、视图、同义词。<br /><br />@@文件名　　　　 在.sql文件中调用令一个.sql文件时使用<br /><br />save 文件名　　　将缓冲区的命令以文件方式存盘，缺省文件扩展名为.sql<br />get 文件名　　　 调入存盘的sql文件<br />start 文件名　　 运行调入内存的sql文件<br /><br />spool 文件名　　 把这之后的各种操作及执行结果&ldquo;假脱机&rdquo;即存盘到磁盘文件上，默认文件扩展名为.lst<br />spool　　　　　　显示当前的&ldquo;假脱机&rdquo;状态<br />spool off　　　　停止输出<br /><br />例：<br />SQL&gt; spool a<br />SQL&gt; spool<br />正假脱机到 A.LST<br />SQL&gt; spool off<br />SQL&gt; spool<br />当前无假脱机<br /><br /><br />exit　　　　　　 退出SQL*PLUS<br />desc 表名　　　　显示表的结构<br />show user　　　　显示当前连接用户<br />show error　　　 显示错误<br />show all　　　　 显示所有68个系统变量值<br />edit　　　　　　 打开默认编辑器，Windows系统中默认是notepad.exe，把缓冲区中最后一条SQL语句调入afiedt.buf文件中进行编辑<br />edit 文件名　　　把当前目录中指定的.sql文件调入编辑器进行编辑<br /><br />clear screen　　 清空当前屏幕显示 </p>
<p>&nbsp;-22-----------------------------------------------------------------------------------------------</p>
<p>第三章附：上机练习 <br /><br />内容：1.创建一数据库，启动实例并装配它。 <br />&nbsp;&nbsp;&nbsp;2.通过访问数据字典了解数据库的结构及实例结构。 <br /><br />步骤： <br />&nbsp;&nbsp;一．创建数据库 <br />用Netterm或Ptelnet，以Oracle8帐号登录uibm主机(IP:210.34.0.23)。 <br /><br />进入&nbsp;/oracle/目录，ls查看其结构。 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;--------&nbsp;clt1&nbsp;&nbsp;----&nbsp;oradata&nbsp;&nbsp;--&nbsp;ora <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|---&nbsp;testdata&nbsp;--&nbsp;test <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;| <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|-------&nbsp;ctl2&nbsp;&nbsp;-----&nbsp;oradata&nbsp;&nbsp;--&nbsp;ora <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|---&nbsp;&nbsp;testdata&nbsp;--&nbsp;test <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;| <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|-------&nbsp;ctl3&nbsp;&nbsp;&nbsp;&nbsp;&hellip;&nbsp;&nbsp;&hellip;&nbsp; <br />以上目录为各数据库中数据文件存放目录。 <br />效仿以上的目录结构，在ctl1、ctl2、clt3目录下再建一个tstdata目录，并在各tstdata<br />目录下建立一个tst目录 <br /><br />cd&nbsp;/oracle/app/oracle/admin <br />此目录为Oracle各数据库的管理目录。 <br />cd&nbsp;test <br />进入test目录了解Oracle目录组织结构(OFA结构)，结合ls命令。 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ora&nbsp;&nbsp;-------&nbsp;bdump&nbsp;&nbsp;后台存储文件目录(BACKGROUP_DUMP_DEST的值) <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|------&nbsp;udump&nbsp;&nbsp;用户转储文件目录(USER_DUMP_DEST的值) <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|------&nbsp;cdump&nbsp;&nbsp;核心文件 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|------&nbsp;pfile&nbsp;&nbsp;init.ora和任何其它数据库初始化参数 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|------&nbsp;create&nbsp;用于创建初始化数据和数据库对象的脚本 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|------&nbsp;SQL&nbsp;&nbsp;&nbsp;&nbsp;数据库管理SQL文件 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />进入create目录阅读crdbtest.sql及crdb2test.sql这两个数据库ORA的创建脚本，进而知<br />道创建数据库的过程命令。 <br /><br />&nbsp;效防test下的目录结构，创建一名为tst的目录，拷贝test/pfile及test/create下的所有<br />文件到对应目录。 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Cd&nbsp;/oracle/app/oracle/admin <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Mkdir&nbsp;tst <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Cd&nbsp;tst <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Mkdir&nbsp;bdump <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Mkdir&nbsp;udump <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Mkdir&nbsp;cdump <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Mkdir&nbsp;pfile <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Mkdir&nbsp;create <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Mkdir&nbsp;sql <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Cp&nbsp;../test/pfile/*&nbsp;pfile <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Cp&nbsp;../test/create/*&nbsp;create <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;进入tst/pfile目录，启动vi编辑器编辑configora.ora文件： <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;将所有与原来test目录有关的目录全以tst替换test. <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;如：原来的control_files参数中 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;把/oracle/ctl1/oradata/test/control01.ctl,改为 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;/oracle/ctl1/oradata/tst/control01.ctl, <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;需要改的地方还有：core_dump_dest <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;user_dump_dest&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;db_name&nbsp;参数行 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;把文件configtest.ora改名为configtst.ora <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;inittest.ora&nbsp;&nbsp;&nbsp;改名为inittst.ora <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;inittest_0.ora&nbsp;改名为inittst_0.ora <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;编辑inittst.ora及inittst_0.ora文件，把它们中的前面的ifile指 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;定文件原来为: <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ifile&nbsp;=&nbsp;/oracle/app/oracle/admin/test/pfile/configtest.ora&nbsp;&nbsp;&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;改为： <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ifile&nbsp;&nbsp;=&nbsp;/oracle/app/oracle/admin/tst/pfile/configtst.ora&nbsp;&nbsp;&nbsp; <br /><br /><br />进入tst/create目录 <br />把crdbtest.sql及crdb2test.sql改名为crdbtst.sql及crdb2tst.sql <br /><br />编辑crdbtst.sql文件，修改以下行（将test改为tst）: <br />&nbsp;&nbsp;spool&nbsp;/oracle/app/oracle/admin/test/create/crdbtest.lst <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;startup&nbsp;nomount&nbsp;pfile=&nbsp;&hellip; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;create&nbsp;database&nbsp;"test"&nbsp;改为create&nbsp;database&nbsp;&ldquo;tst&rdquo; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;将create&nbsp;database语句的用的character&nbsp;set改为ZHS16CGB231280， <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;原先为US7ASCII。ZHS16CGB231280为Oracle中支持中文国标的字符集名。 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;编辑crdb2tst.sql文件，将其做类似以上的修改(将创建命令中所用到的有关原来<br />test目录改为tst目录，并可以适当调节你所要建立数据库的相关数据文件大小。 <br /><br />修改ORACLE_SID环境变量值为新的SID名，此SID告诉oracle欲启动的实例名。 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ORACLE_SID=tst;exprot&nbsp;ORACLE_SID <br /><br />&nbsp;&nbsp;进入tst/create目录，启动服务器管理器(svrmgrl)执行crdbtst.sql脚本： <br />cd&nbsp;/oracle/app/oracle/admin/tst/create <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;svrmgrl&nbsp;&nbsp;@crdbtst.sql <br />&nbsp;&nbsp;&nbsp;&nbsp;执行后在svrmgrl状态下再执行crdb2tst.sql脚本。 <br />&nbsp;&nbsp;&nbsp;&nbsp;Svrmgrl&gt;&nbsp;start&nbsp;crdb2tst.sql <br />&nbsp;&nbsp;&nbsp;&nbsp;创建过程需要数分钟，请耐心等待&nbsp;&hellip;&nbsp; <br /><br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;等上以脚本执行完毕，新的数据库已建立。此时，可以退出svrmgrl。 <br /><br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;拷贝tst/pfile/inittst.ora文件至$ORACLE_HOME/dbs目录，省得每次启动svrmg<br />rl还要指定init.ora文件位置。在启动svrmgrl时，若没有特别指定init.ora的文件，ORA<br />CLE将在$ORACLE_HOME/dbs找init&lt;SID&gt;.ora作为其启动的初始化参数文件,SID为ORACLE_S<br />ID环境变量值。 <br /><br />再次启动svrmgrl(注意：ORACLE_SID值必须已改为新的SID值。) <br />&nbsp;&nbsp;svrmgrl <br />svrmgrl&gt;connect&nbsp;internal; <br />svrmgrl&gt;startup&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(启动数据库) <br />svrmgrl&gt;start&nbsp;$ORACLE_HOME\dbs\catproc.sql&nbsp; <br />&nbsp;&nbsp; <br />catproc.sql脚本安装Procedural&nbsp;Option所必需的脚本或PL/SQL对象及其支持的数据库结<br />构。 <br /><br />至此，我们已成功创建了一个新的数据库tst，并且我们也用实例tst来装配启动它。 <br />为了能够让用户从远程访问此数据库，我们还必须配置Oracle的TNS（Transparent&nbsp;Netwo<br />rk&nbsp;Service），配置这一服务只要改变一下其配置文件listener.ora即可，最简单的办法<br />是拷贝一个副本备份，然后直接编辑它，把原来的实例名更换为新的实例名即可。更名后<br />，重新启动tnslistener进程即生效。 <br />$lsnrctl&nbsp;stop&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(在操作系统状态下执行) <br />$lsnrctl&nbsp;start <br /><br /><br />更改SYS及SYSTEM用户的默让密码。 <br />&nbsp;&nbsp;grant&nbsp;connect&nbsp;to&nbsp;sys(或system)&nbsp;identified&nbsp;by&nbsp;&lt;new_password&gt; <br />&nbsp;或&nbsp;alter&nbsp;user&nbsp;sys&nbsp;identified&nbsp;by&nbsp;&lt;new_password&gt;&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;以上命令可以在服务器管理器状态下执行，也可以在Sqlplus下执行。 <br />&nbsp; <br /><br /><br />二、考察数据库及实例结构 <br />&nbsp;启动sqlplus用SYS或SYSTEM用户连接。 <br />或启动svrmgrl，connect&nbsp;internal <br /><br />1.&nbsp;查询实例启动时间。 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;select&nbsp;to_char(a.value,&rsquo;J&rsquo;)+b.value/86400, <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&rsquo;HH24:MI:SS&nbsp;DD-MON-RR&rsquo;)&nbsp;start_time&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from&nbsp;v$instance&nbsp;a,v$instance&nbsp;b <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;where&nbsp;a.key=&rsquo;STARTUP&nbsp;TIME&nbsp;&ndash;JULIAN&rsquo;&nbsp;AND <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;b.key=&rsquo;STARTUP&nbsp;TIME&nbsp;&ndash;SECONDS&rsquo;; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />观看实例存储器分配信息 <br />SELECT&nbsp;name,bytes&nbsp;from&nbsp;v$sgastat <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Where&nbsp;name&nbsp;in&nbsp;(&lsquo;free&nbsp;memory&rsquo;,&rsquo;fixed_sga&rsquo;,&rsquo;db_block_buffers&rsquo;, <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lsquo;log_buffer&rsquo;,&rsquo;dictionary&nbsp;cache&rsquo;,&rsquo;library&nbsp;cache&rsquo;, <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lsquo;sql&nbsp;area&rsquo;); <br /><br />查看进程实例进程 <br />select&nbsp;spid,name&nbsp;from&nbsp;v$process,&nbsp;v$bgprocess&nbsp;where&nbsp;addr&nbsp;=paddr;&nbsp; <br /><br />查看数据库用户 <br />select&nbsp;username&nbsp;from&nbsp;dba_users; <br /><br />查看活动的控制文件 <br />select&nbsp;*&nbsp;from&nbsp;v$controlfile <br /><br />查看回滚段信息 <br />select&nbsp;a.segment_name,b.bytes,b.extents,a.tablespace_name,&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;c.shrinks,c.extends,c.hwmsize <br />&nbsp;&nbsp;from&nbsp;dba_rollback_segs&nbsp;a,dba_segments&nbsp;b,v$rollstat&nbsp;c <br />&nbsp;&nbsp;where&nbsp;a.segment_id=c.usn&nbsp;and&nbsp;a.segment_name=b.segment_name; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />查看重做日志信息 <br />select&nbsp;&nbsp;&nbsp;member,bytes,members,a.status&nbsp; <br />&nbsp;&nbsp;&nbsp;from&nbsp;&nbsp;v$log,&nbsp;V$logfile&nbsp;b <br />&nbsp;&nbsp;&nbsp;where&nbsp;a.group#&nbsp;=&nbsp;b.group# <br />&nbsp;&nbsp;&nbsp;order&nbsp;by&nbsp;member; <br /><br />查看数据库链接 <br />select&nbsp;spid,mame&nbsp;from&nbsp;v$sysstatprocess,v$sysstatbgprocess <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;where&nbsp;paddr(+)=addr; <br /><br />查看多线程服务器进程 <br />&nbsp;&nbsp;&nbsp;select&nbsp;*&nbsp;from&nbsp;v$dispatcher; <br />&nbsp;&nbsp;&nbsp;select&nbsp;*&nbsp;from&nbsp;v$shared_server; <br /><br /><br /><br /><br /><br />第四章：SQL <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(本次课在机房，结合上机讲授) <br />本章介绍SQL的基础知识。理解了SQL就理解了关系数据库。Oracle与数据库的所有交互都<br />使用SQL(Structured&nbsp;Query&nbsp;Language)。SQL*Plus是基于SQL但又具有Oracle特定功能的一<br />种工具，它可用来生成报表、控制屏幕显示和打印输出格式。 <br /><br />术语 <br />下面介绍本章使用的一引技术术语： <br />■&nbsp;DDL(Data&nbsp;Definition&nbsp;Language)&nbsp;&nbsp;&nbsp;数据定义语言是SQL中定义数据库中数据的结构的<br />语言。定义数据时，将在Oracle的数据字典中生成数据项。常见的DDL关键字是create、r<br />evoke、grant和alter <br />DML(Data&nbsp;Manipulation&nbsp;Language)&nbsp;数据操纵语言为SQL结构，用来操纵数据库中数据（而<br />非定义数据，定义数据由DDL完成）。常见的DML关键字为select、insert、update和dele<br />te。 <br />在Oracle中，我们使用commit(提交)语句表示已经将修改后的数据保存到数据库。每次用<br />户保存结果时，Oracle将引用用户的提交操作。 <br />约束(constraint)&nbsp;是一种保证一个Oracle表的数据间关系或两不同表中数据间的一致性的<br />机制。 <br />Oracle8数据库中一个对象(object)是一个有意义的事物，可在其内部存放信息。我们常谈<br />的对象类型&mdash;&mdash;表和视图是两种最常见的。 <br />利用如SQL*Plus这样的程序将信息从Oracle数据库中提取出来的操作称为查询(query)。 <br /><br />■&nbsp;回滚（Rollback）为当某个对话更改了数据库中的数据后，由于某种原因不想提交些更<br />改时Oracle所采取的操作。这是一个把信息恢复到用户update前状态的操作。 <br /><br />&nbsp;&nbsp;&nbsp;SQL语句有两大类：DDL和DML。下面我们进一步来看看二者的差异： <br /><br />&nbsp;&nbsp;二．DDL <br />DDL数据定义语言是一组SQL命令，用于创建和定义数据库对象，并且将其保存在数据字典<br />中。 <br /><br />数据定义语言使用户能完成下列任务： <br />创建(create)数据库对象 <br />删除(drop)数据库对象 <br />更改(alter)数据库对象 <br />为数据库对象授权(grant) <br />回收已授给数据库对象的权限(revoke) <br /><br />当发布一条DDL&nbsp;SQL语句时，在每一条DDL语句执行前后，Oracle都将提交当前的事务，理<br />解这一上点很重要。因此如果用户插入（insert）记录到数据库中并且发布了一条DDL语句<br />，如create&nbsp;table，此时来自insert命令的数据将提交到数据库。 <br />&nbsp; <br />属于DDL的语句是自动提交的，这意味着当Oracle8通知用户比如&ldquo;Revoke&nbsp;succeeded&rdquo;，<br />此时命令已完成不能回滚了。 <br /><br />&nbsp;&nbsp;DDL语句部分列表： <br />&nbsp;&nbsp;alter&nbsp;procedure&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;重编译存贮过程 <br />&nbsp;&nbsp;alter&nbsp;table&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;增加表列、修改表列、更改存贮分配 <br />&nbsp;&nbsp;analyze&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;收集数据库对象的性能统计值并送入代价的优化器 <br />&nbsp;&nbsp;alter&nbsp;table&nbsp;add&nbsp;constraint&nbsp;&nbsp;&nbsp;在已有的表上增加约束 <br />&nbsp;&nbsp;create&nbsp;table&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;创建表 <br />&nbsp;&nbsp;create&nbsp;index&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;创建索引 <br />&nbsp;&nbsp;drop&nbsp;index&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;删除索引 <br />&nbsp;&nbsp;drop&nbsp;table&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;删除表 <br />&nbsp;&nbsp;grant&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;将权限或角色授予用户或其它角色 <br />&nbsp;&nbsp;truncate&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;删除表中所有行 <br />&nbsp;&nbsp;revoke&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;从用户或数据库角色回收权限 <br />&nbsp;&nbsp;三．DML <br />DML(数据操纵语言)允许用户对数据库中的数据进行insert、update、delete和select等操<br />作。正如名字所示，DML处理数据库中的数据内容。最常见的DML语句是insert、update、<br />delete和select。 <br /><br />Insert <br />Delete <br />Update <br />Select <br />Commit&nbsp;work&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;把当前事务所作的更改永久化（写入磁盘） <br />Rollback&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;作废上次提交以来的所有更改 <br />&nbsp;&nbsp;&nbsp;&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;在学习了两种主要类型的SQL语句后，下面作进一步的介绍。首先登录进SQL*Plus，<br />然后试一些最常见的DDL和DML语句。 <br />&nbsp;&nbsp;&nbsp;&nbsp; <br />&nbsp; <br />&nbsp;&nbsp;四.SQL*Plus入门 <br />学习SQL最简单的办法就是使用SQL*Plus。因此先登录到SQL*Plus。Oracle安装后有一用户<br />名scott,口令为tiger。我们可以用这个帐号登录试用。 <br />有两种方式进入SQL*Plus: <br />1.使用客户端的的SQL*&nbsp;Plus&nbsp;8.0。 <br />&nbsp;&nbsp;此程序项在启动菜单栏的Oracle&nbsp;For&nbsp;Windows95组中。启动它，在connect对话框中按提<br />示输入用户名、口令及主机字符串。如果单机已装了Personal&nbsp;Oracle的，主机字符串可以<br />不填，否则填上SQL&nbsp;*&nbsp;Net已配置的service&nbsp;name，所连接的数据库实例在service里已定<br />义，这些定义可以使用Oracle&nbsp;Net8&nbsp;Easy&nbsp;Config进行配置。 <br />其结果保存在\ORAWIN95\NET80\ADMIN\TNSNAMES.ORA文件中。 <br />&nbsp;&nbsp;&nbsp; <br />使用Unix上的SQL*Plus <br />登录到UNIX主机上， <br />打入命令&nbsp;sqlplus&nbsp;scott/tiger&nbsp;&nbsp;&nbsp;或sqlplus然后再按提示输入用户名及口令 <br /><br />SQL*Plus:&nbsp;Release&nbsp;8.0.4.0.0&nbsp;-&nbsp;Production&nbsp;on&nbsp;Sat&nbsp;Jul&nbsp;3&nbsp;0:31:55&nbsp;1999 <br /><br />(c)&nbsp;Copyright&nbsp;1997&nbsp;Oracle&nbsp;Corporation.&nbsp;&nbsp;All&nbsp;rights&nbsp;reserved. <br /><br />Connected&nbsp;to: <br />Oracle8&nbsp;Enterprise&nbsp;Edition&nbsp;Release&nbsp;8.0.4.0.0&nbsp;-&nbsp;Production <br />&nbsp;&nbsp;&nbsp;&nbsp;PL/SQL&nbsp;Release&nbsp;8.0.4.0.0&nbsp;-&nbsp;Production <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;SQL&gt; <br />&nbsp;&nbsp; <br />&nbsp;&nbsp;在进入SQL*Plus后，会看到SQL*Plus提示符SQL&gt; <br />这时您就可以键入想试验的SQL语句。 <br /><br />&nbsp;&nbsp;下面我们讲一下与SQL缓冲器一起使用的SQL*Plus命令,这些可以帮助我们高效地输入命<br />令。 <br />命令 &nbsp;&nbsp;缩写 动作 <br />APPEND&nbsp;text A&nbsp;text 在行尾增加text <br />CHANGE&nbsp;&nbsp;old/new C&nbsp;old/new 在一行中将old文本改为new文本 <br />CLEAR&nbsp;BUFFER CL&nbsp;BUFF&nbsp; 删除所有行 <br />DEL 删除缓冲器中所有行 <br />INPUT I&nbsp; 将一行或多行增加到缓冲器 <br />INPUT&nbsp;text I&nbsp;text 增加一由text组成的行 <br />LIST L 列出SQL*Plus缓冲器内容 <br />LIST&nbsp;n Ln或n 列出行n <br />LIST&nbsp;* L&nbsp;* 列出当前行 <br />LIST&nbsp;m&nbsp;n&nbsp; L&nbsp;m&nbsp;n 列出行m至行n <br />LIST&nbsp;LAST&nbsp; L&nbsp;LAST 列出缓冲器中的最后一行 <br />RUN 运行缓冲器中的命令 <br />&nbsp;SQL*Plus中的命令行以分号(;)结束。 <br /><br />&nbsp;下面我们给出一些SQL语句，大家可以在自己的机器上试验一下： <br />select&nbsp;table_name&nbsp;from&nbsp;user_tables <br />&nbsp;&nbsp;此命令用数据字典user_tables中列出用登录用户所拥有的表。 <br />若用scott登录，列出的结果如下： <br />TABLE_NAME <br />------------------------------ <br />BONUS <br />DEPT <br />DUMMY <br />EMP <br />HELP <br />&nbsp;&nbsp;&nbsp;SALGRADE <br /><br />&nbsp;&nbsp;&nbsp;这些表是在数据库安装时建立的让用户试验学习的表，查看这些表的结构可以用descr<br />ibe命令，例如： <br />&nbsp;&nbsp;&nbsp;SQL&gt;describe&nbsp;emp&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />&nbsp;&nbsp;&nbsp;查看emp表的结构，结果如下： <br />&nbsp;Name&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Null?&nbsp;&nbsp;&nbsp;&nbsp;Type <br />&nbsp;-------------------------------&nbsp;--------&nbsp;---- <br />&nbsp;EMPNO&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;NOT&nbsp;NULL&nbsp;NUMBER(4) <br />&nbsp;ENAME&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;VARCHAR2(10) <br />&nbsp;JOB&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;VARCHAR2(9) <br />&nbsp;MGR&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;NUMBER(4) <br />&nbsp;HIREDATE&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;DATE <br />&nbsp;SAL&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;NUMBER(7,2) <br />&nbsp;COMM&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;NUMBER(7,2) <br />&nbsp;&nbsp;&nbsp;&nbsp;DEPTNO&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;NUMBER(2) <br />&nbsp;&nbsp;&nbsp;SQL&gt;select&nbsp;empno,ename&nbsp;from&nbsp;emp <br />&nbsp;&nbsp;&nbsp;查看表内容。 <br /><br />&nbsp;&nbsp;２.create语句 <br />&nbsp;&nbsp;&nbsp;在任何数据库总是以DDL语句开始，因为创建数据库对象的工作是由DDL语句来完成的。<br />首先，我们将创建四个表：Customer、State、X和Y： <br />SQL&gt;create&nbsp;table&nbsp;customer&nbsp;( <br />last_name&nbsp;&nbsp;varchar2&nbsp;(30)&nbsp;not&nbsp;null, <br />state_cd&nbsp;&nbsp;&nbsp;varchar(2), <br />sales&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;number) <br />tablespace&nbsp;&nbsp;users <br />storage&nbsp;(initial&nbsp;25k&nbsp;next&nbsp;25k&nbsp;minextents&nbsp;1); <br />Table&nbsp;created. <br />SQL&gt;create&nbsp;table&nbsp;state&nbsp;( <br />&nbsp;&nbsp;&nbsp;2&nbsp;&nbsp;state_cd&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;varchar(2)&nbsp;not&nbsp;null, <br />&nbsp;&nbsp;&nbsp;3&nbsp;&nbsp;state_name&nbsp;&nbsp;&nbsp;varchar2(30); <br />Table&nbsp;created. <br />SQL&gt;create&nbsp;table&nbsp;x( <br />&nbsp;&nbsp;&nbsp;2&nbsp;&nbsp;col&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;varchar2(30); <br />Table&nbsp;created. <br />SQL&gt;create&nbsp;table&nbsp;y( <br />col&nbsp;varchar2(30)); <br />Table&nbsp;created. <br /><br />▲Null与Not&nbsp;Null <br />&nbsp;&nbsp;&nbsp;&nbsp;在创建customer表时，last_name表列后跟一个限定符&ldquo;not&nbsp;null&rdquo;，这表示数据库不<br />接受没有表列数据行到customer表中。换句话说，not&nbsp;null表列是强制性字段，在表cust<br />omer和state中，这意味着要在表中插入一行，last_name和state_cd字段必须含有值。 <br /><br /><br />什么是空值(null&nbsp;value) <br />空(null)是不包括数据的表列。可以将null理解为长度为0的字符串。很多时候若不知道某<br />表列的类型可以给它赋一空值。但人们最容易犯的一个错误就是将空值加载到一个数值型<br />表列中，而问题在于&ldquo;1+null=null&rdquo;！因此，如果用户偶然将空值加载至数值域中，那么<br />产生的统计报表肯定不正确。 <br /><br />３．Insert <br />&nbsp;&nbsp;&nbsp;现在我们已经建立了一些表，让我们用不用DML语句，在我们建立的表上插入一些数据<br />，这些数据也将作为我们试验命令的数据。 <br />SQL&gt;insert&nbsp;into&nbsp;customer&nbsp;values&nbsp;(&lsquo;Teplow&rsquo;,&rsquo;MA&rsquo;,23445.67); <br />SQL&gt;insert&nbsp;into&nbsp;customer&nbsp;values&nbsp;(&lsquo;Abbev&rsquo;,&rsquo;CA&rsquo;,6969.96); <br /><br />每次成功地完成一条insert语句后，均返回建立信息， <br />1&nbsp;row&nbsp;created. <br />该信息通知用户建立的行数。 <br /><br />SQL&gt;insert&nbsp;into&nbsp;customer&nbsp;values&nbsp;(&lsquo;Porter&rsquo;,&rsquo;CA&rsquo;,6989.99); <br />SQL&gt;insert&nbsp;into&nbsp;customer&nbsp;values&nbsp;(&lsquo;Martin&rsquo;,&rsquo;CA&rsquo;,2345.45); <br />SQL&gt;insert&nbsp;into&nbsp;customer&nbsp;values&nbsp;(&lsquo;Laursen&rsquo;,&rsquo;CA&rsquo;,34.34); <br />SQL&gt;insert&nbsp;into&nbsp;customer&nbsp;values&nbsp;(&lsquo;Bambi&rsquo;,&rsquo;CA&rsquo;,1234.55); <br />SQL&gt;insert&nbsp;into&nbsp;customer&nbsp;values&nbsp;(&lsquo;McGraw&rsquo;,&rsquo;NJ&rsquo;,123.45); <br /><br />现在我们用稍加变化的insert命令的数据插入state表。我们将指定数据要插入的表列名。<br />这在处理大表时很有用，因为用户可能没有表中每一列的数据。例如：在一个预算系统中<br />，只有在月末才有实际的花销数。 <br /><br />SQL&gt;insert&nbsp;into&nbsp;state&nbsp;(state_name,state_cd) <br />values&nbsp;(&lsquo;Massachusetts&rsquo;,&rsquo;MA&rsquo;); <br />SQL&gt;insert&nbsp;into&nbsp;state&nbsp;(state_name,state_cd) <br />values&nbsp;(&lsquo;California&rsquo;,&rsquo;CA&rsquo;); <br />&nbsp;&nbsp; <br />&nbsp;&nbsp;最后我们再插入一些数据到表X和表Y中。 <br />SQL&gt;insert&nbsp;into&nbsp;x&nbsp;values&nbsp;(&lsquo;1&rsquo;); <br />SQL&gt;insert&nbsp;into&nbsp;x&nbsp;values&nbsp;(&lsquo;2&rsquo;); <br />SQL&gt;insert&nbsp;into&nbsp;x&nbsp;values&nbsp;(&lsquo;3&rsquo;); <br />SQL&gt;insert&nbsp;into&nbsp;y&nbsp;values&nbsp;(&lsquo;3&rsquo;); <br />SQL&gt;insert&nbsp;into&nbsp;y&nbsp;values&nbsp;(&lsquo;4&rsquo;); <br />SQL&gt;insert&nbsp;into&nbsp;y&nbsp;values&nbsp;(&lsquo;5&rsquo;); <br /><br />４．Select&nbsp; <br />select命令用于从Oracle数据库中检索数据，select是用户最常用的ＳＱＬ语句，select<br />命令由四个基本部分构成： <br />1).select后跟用户要检索的信息（表或视图中的列名），这是select命令不可少的部分，<br />可用*号代表全部列。 <br />2).from后跟检索对象(如存放数据的一个或多个表或视图的名称)，from部分也是必不可少<br />的。 <br />3).where后跟检索条件，可选的。 <br />4).order&nbsp;by后跟分类准则，可选的。 <br /><br />现在我们来查看我们刚才插入的数据： <br />SQL&gt;select&nbsp;*&nbsp;from&nbsp;customer; <br />SQL&gt;select&nbsp;state_name&nbsp;from&nbsp;state; <br />SQL&gt;select&nbsp;*&nbsp;from&nbsp;x; <br />SQL&gt;select&nbsp;*&nbsp;from&nbsp;y; <br /><br />&nbsp;&nbsp;&nbsp;下面我们来看一下条件及范围检索： <br />select&nbsp;last_name,state_cd,sales&nbsp;from&nbsp;customer&nbsp;where&nbsp;state_cd=&rsquo;MA&rsquo;; <br />查看state_cd值为MA的所有客户。 <br /><br />select&nbsp;*&nbsp;from&nbsp;customer&nbsp;where&nbsp;state_cd=&rsquo;CA&rsquo;&nbsp;and&nbsp;sales&gt;6000 <br />&nbsp;&nbsp;select&nbsp;*&nbsp;from&nbsp;customer&nbsp;where&nbsp;state_cd=&rsquo;CA&rsquo;&nbsp;or&nbsp;sales&gt;6000 <br />&nbsp;&nbsp;select&nbsp;*&nbsp;from&nbsp;customer&nbsp;where&nbsp;state_cd!=&rsquo;MA&rsquo;; <br /><br />带检索表 <br />select&nbsp;*&nbsp;from&nbsp;customer&nbsp;where&nbsp;state_cd&nbsp;in&nbsp;(&lsquo;NJ&rsquo;,&rsquo;CA&rsquo;); <br /><br />带匹配条件 <br />Select&nbsp;*&nbsp;from&nbsp;customer&nbsp;where&nbsp;last_name&nbsp;like&nbsp;&lsquo;M%&rsquo;; <br />Select&nbsp;*&nbsp;from&nbsp;customer&nbsp;where&nbsp;last_name&nbsp;like&nbsp;&lsquo;%tin%; <br /><br />&nbsp;&nbsp;总结： <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;= <br />&nbsp;!=&nbsp;&nbsp;&nbsp;不等于 <br />&nbsp;^=&nbsp;&nbsp;&nbsp;不等于 <br />^=&nbsp;&nbsp;&nbsp;不等于 <br />&lt;&gt;&nbsp;&nbsp;&nbsp;不等于 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&gt; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;= <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&gt;= <br />in&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;等于括号内任一成员 <br />not&nbsp;in&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;不等于括号内任一成员 <br />between&nbsp;A&nbsp;and&nbsp;B&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;大于等于A与小于等于B <br />not&nbsp;between&nbsp;A&nbsp;and&nbsp;B&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;不大于等于A与小于等于B <br />like&nbsp;&lsquo;%tin%&rsquo;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;包括给定子串(即&lsquo;tin&rsquo;) <br /><br /><br />Order&nbsp;by: <br />&nbsp;&nbsp;&nbsp;Select&nbsp;*&nbsp;from&nbsp;customer&nbsp;order&nbsp;by&nbsp;last_name&nbsp;desc; <br />&nbsp;&nbsp;&nbsp;Select&nbsp;*&nbsp;from&nbsp;customer&nbsp;order&nbsp;by&nbsp;last_name; <br />&nbsp;&nbsp;&nbsp;在order&nbsp;by子句中未指定升序或降序时，Oracle按升序排序。 <br /><br />5.Update、Delete和Alter <br /><br />Update修改表中的数据 <br />&nbsp;&nbsp;SQL&gt;Update&nbsp;customer&nbsp;set&nbsp;sales=23890.66&nbsp;where&nbsp;state_cd=&rsquo;MA&rsquo;; <br /><br />&nbsp;&nbsp;若没有用where指定修改的条件行，将修改表中全部行。 <br /><br />Delete删除行数据 <br />&nbsp;&nbsp;Delete&nbsp;from&nbsp;customer，将删除customer表的所有记录；delete&nbsp;from&nbsp;customer&nbsp;where<br />&nbsp;state_cd=&rsquo;CA&rsquo;，将删除state_cd为CA的客户记录。 <br /><br />Alter&nbsp;table修改表结构 <br />&nbsp;&nbsp;此语句有如Foxpro中的Modify&nbsp;stru语句。在创建表后，用户可能想要增加表列。这时就<br />要用到alter&nbsp;table命令了。 <br /><br />&nbsp;&nbsp;Alter&nbsp;table&nbsp;customer&nbsp;add&nbsp;(sale_date&nbsp;date)； <br />&nbsp;&nbsp;将成功地把表列sale_date加到表customer中。 <br /><br />&nbsp;&nbsp;Alter&nbsp;table&nbsp;x&nbsp;modify(col&nbsp;date)，改变一个已存在表列的数据类型。 <br /><br />6．连接两个表 <br />现实中，用户需要的大量数据往往存放在多个表中。很多情况下需要处理多个表。例如，<br />customer表中只存放州代码(state_code)，然而用户还想知道州名，这时需要将表custom<br />er与表state连接。这就要用到表的连接。通过定义，Oracle一类的关系数据库允许用户基<br />于公共域连接两个或更多表。这些公共域通常称为键域(key&nbsp;field)。 <br />有两种类型的键：主键（primary）和外部键(foreign)。主键使表中的数据行保持唯一。<br />在表state中，state_cd就是主键。表customer中也包含有state_cd,此时的state_cd就是<br />外部键。一个表的外部键用于从其他（foreign）表中获取信息。 <br />SQL&gt;select&nbsp;*&nbsp;right.col,left.col&nbsp;from&nbsp;x&nbsp;right,y&nbsp;left&nbsp; <br />where&nbsp;right.col=left.col; <br /><br /><br />五．内部函数 <br />数值型函数 <br />&nbsp;函&nbsp;&nbsp;数 &nbsp;&nbsp;&nbsp;返回值 &nbsp;&nbsp;&nbsp;样&nbsp;&nbsp;例 显示 <br />Abs(n) N的绝对值 Select&nbsp;abs(-321)&nbsp;from&nbsp;dual; 321 <br />Ceil(n) 大于等于数值n的最大整数 Select&nbsp;ceil(10.6)&nbsp;from&nbsp;dual; 11 <br />Floor(n) 小于等于数值n的最大整数 Select&nbsp;floor(10.6)&nbsp;from&nbsp;dual; 10 <br />Mod(m,n) M除以n的余数，若n=0返回n Select&nbsp;mod(7,5)&nbsp;from&nbsp;dual; 2 <br />Power(m,n) M的n次方 Select&nbsp;power(3,2)&nbsp;from&nbsp;dual; 9 <br />Round(n,m) 将n四舍五入，保留小数点后m位 Select&nbsp;round(1234.5678,2)&nbsp;from&nbsp;dual 12<br />34.57 <br />Sign(n) N=0,返回0;n&gt;0,返回1;n&lt;0,返回-1 Select&nbsp;sign(12)&nbsp;from&nbsp;dual; 1 <br />Sqrt(n) N的平方根 Select&nbsp;sqrt(25)&nbsp;from&nbsp;dual; 5 <br />&nbsp;&nbsp;Dual表拥有者为SYS，在句法正确，而数据库中没有其他表可用于该语句时，可使用dua<br />l表。 <br />&nbsp;&nbsp;&nbsp;2.字符串函数 <br />&nbsp;函&nbsp;&nbsp;&nbsp;数 &nbsp;&nbsp;返回值 样例 显示 <br />initcap(char)&nbsp;&nbsp; 把每个字符串的第一个字符换成大写 Select&nbsp;initcap(&lsquo;mr.telpow&rsquo;)<br />&nbsp;from&nbsp;dual; Mr.Telplow <br />Lower(char) 整个字符串换成小写 Select&nbsp;lower(&lsquo;Mr.Frank&nbsp;Townson&rsquo;)&nbsp;from&nbsp;dual; m<br />r.frank&nbsp;townson <br />Replace(char,str1,str2) 字符串中所有str1换成str2 Select&nbsp;replace(&lsquo;Scott&rsquo;,&nbsp;&nbsp;&rsquo;<br />S&rsquo;,&rsquo;Boy&rsquo;)&nbsp;from&nbsp;dual; Boycott <br />Soundex(char) 字符串的语音表示，查找发音相似拼写不同的字符串 Select&nbsp;last_name&nbsp;<br />from&nbsp;employee&nbsp;where&nbsp;soundex&nbsp;(last_name)&nbsp;=&nbsp;soundex(&lsquo;SMYTHE&rsquo;); SMITH <br />Substr(char,m,n) 取出从m字符开始的n个字符的子串 Select&nbsp;substr(&lsquo;ABCDEF&rsquo;,2,1)&nbsp;<br />from&nbsp;dual; B <br />Length(char) 求字符串的长度 Select&nbsp;length(&lsquo;Anderson&rsquo;)&nbsp;From&nbsp;dual; 8 <br />&nbsp; <br />&nbsp;&nbsp;||&nbsp;&nbsp;并置运算符。 <br />&nbsp;&nbsp;Select&nbsp;&lsquo;Dear&rsquo;||&rsquo;John&rsquo;||&rsquo;:&rsquo;&nbsp;from&nbsp;customer&nbsp; <br />&nbsp;&nbsp;将返回&nbsp;&lsquo;DearJohn:&rsquo; <br /><br />&nbsp;&nbsp;&nbsp;3.日期型函数 <br />&nbsp;&nbsp;函数 返回值 样例 显示 <br />Sysdate 当前日期和时间 Select&nbsp;sysdate&nbsp;from&nbsp;dual; <br />Last_day 本月最后一天 Select&nbsp;last_day(sysdate)&nbsp;From&nbsp;dual <br />Add_month(d,n) 当前日期d后推n个月 Select&nbsp;add_months(sysdate,2)&nbsp;from&nbsp;dual; <br />Months_between&nbsp;(f,s) 日期f和s间相差月数 Select&nbsp;months_between(sysdate,&rsquo;12-MAR<br />-99&rsquo;)&nbsp;from&nbsp;dual; <br />Next_day(d,day) D后第一周指定day的日期 Select&nbsp;next_day(sysdate,&rsquo;Monday&rsquo;)&nbsp;fro<br />m&nbsp;dual; <br />Oracle缺省的日期格式为DD-MON-YY。为保证进入21世纪不出问题，请尽可能用四位数字的<br />年份。Oracle提供了一种特殊的世纪日期格式标记为DD-MON-RR。 <br /><br />常用日期格式 <br />格式 返回值 样例 <br />Y、YY或YYY 年的最后一位，两位或三位 Select&nbsp;to_char(sysdate,&rsquo;YYY&rsquo;)&nbsp;from&nbsp;dual;<br /><br />SYEAR或YEAR 年，SYEAR公元前的年前加一负号 Select&nbsp;to_char(sysdate,&rsquo;SYEAR&rsquo;)&nbsp;fr<br />om&nbsp;dual; <br />Q 季度，1到3月为第一季度 Select&nbsp;to_char(sysdate,&rsquo;Q&rsquo;)&nbsp;from&nbsp;dual; <br />MM 月份数 <br />Month 用9个字符长度表示月分(英文) <br />WW 当年第几周 <br />W 本月第几周 <br />D 周内第几天 <br />DD 当月第几天 <br />DY 周内第几天缩写(如：SUN) <br />HH 12进制小时数 <br />HH24 24进制小时数 <br />MI 分钟数 <br />SS 秒数 <br /><br />类型转换 <br />&nbsp;&nbsp;&nbsp;to_char&nbsp;&nbsp;将任意类型的数据转换成字符串 <br />&nbsp;&nbsp;&nbsp;to_number <br />&nbsp;&nbsp;&nbsp;to_date <br /><br /><br />六．格式化输出 <br />在SQL*Plus中，有许多参数可以控制SQL*Plus的输出显示格式，利用SQL*Plus命令show&nbsp;a<br />ll用户能知道显示格式的当前设置。 <br />SQL&gt;show&nbsp;all; <br />appinfo&nbsp;is&nbsp;ON&nbsp;and&nbsp;set&nbsp;to&nbsp;"SQL*Plus" <br />arraysize&nbsp;15 <br />autocommit&nbsp;OFF <br />autoprint&nbsp;OFF <br />autotrace&nbsp;OFF <br />shiftinout&nbsp;INVISIBLE <br />blockterminator&nbsp;"."&nbsp;(hex&nbsp;2e) <br />btitle&nbsp;OFF&nbsp;and&nbsp;is&nbsp;the&nbsp;1st&nbsp;few&nbsp;characters&nbsp;of&nbsp;the&nbsp;next&nbsp;SELECT&nbsp;statement <br />cmdsep&nbsp;OFF <br />colsep&nbsp;"&nbsp;" <br />compatibility&nbsp;version&nbsp;NATIVE <br />concat&nbsp;"."&nbsp;(hex&nbsp;2e) <br />copycommit&nbsp;0 <br />COPYTYPECHECK&nbsp;is&nbsp;ON <br />define&nbsp;"&amp;"&nbsp;(hex&nbsp;26) <br />echo&nbsp;OFF <br />editfile&nbsp;"afiedt.buf" <br />&nbsp;&nbsp;&nbsp;embedded&nbsp;OFF <br />&nbsp;&nbsp;&nbsp;&nbsp;&hellip;&nbsp;&nbsp;... <br /><br />1).行和页的大小 <br />&nbsp;&nbsp;&nbsp;set&nbsp;linesize&nbsp;&lt;n&gt; <br />&nbsp;&nbsp;&nbsp;set&nbsp;pagesize&nbsp;&lt;n&gt; <br />&nbsp;例： <br />&nbsp;&nbsp;SQL&gt;set&nbsp;linesize&nbsp;80; <br />&nbsp;&nbsp;SQL&gt;set&nbsp;pagesize&nbsp;25; <br /><br />2)&nbsp;页头标、页脚标 <br />&nbsp;&nbsp;&nbsp;ttitle&nbsp;&nbsp;&lt;Title&nbsp;string&gt; <br />&nbsp;&nbsp;&nbsp;btitle&nbsp;&nbsp;&lt;Foot&nbsp;title&nbsp;string&gt; <br /><br />&nbsp;例：&nbsp;&nbsp;(connect&nbsp;as&nbsp;scott) <br />&nbsp;&nbsp;SQL&gt;ttitle&nbsp;&lsquo;Database&nbsp;Technoloies|&nbsp;Customer&nbsp;Report&rsquo;; <br />&nbsp;&nbsp;SQL&gt;select&nbsp;empno,ename&nbsp;from&nbsp;emp; <br />&nbsp;&nbsp;SQL&gt;btitle&nbsp;&lsquo;-----------Sample.sql------------&lsquo;; <br />&nbsp;&nbsp;SQL&gt;select&nbsp;empno,ename&nbsp;from&nbsp;emp; <br />&nbsp; <br />&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;表示换行。 <br /><br /><br />3).SQL*Plus结果到文件 <br />&nbsp;&nbsp;spool&nbsp;&nbsp;&lt;目标文件&gt; <br />&nbsp;&nbsp;如：spool&nbsp;&nbsp;c:\temp\out.list <br />&nbsp;&nbsp;这个输出将放在spool命令指定的文件中。为停止假脱机(spooling)，可用命令spool&nbsp;o<br />ff或spool&nbsp;out。后者关闭输出文件并打印输出。 <br /><br />4).格式化输出列表 <br />column <br /><br />大多数情况下，用户需要格式化实例的表列数据。Column命令可完成这项工作。下面我们<br />先执行两条格式化命令，然后再查询customer表。 <br />&nbsp;&nbsp;&nbsp;SQL&gt;column&nbsp;last_name&nbsp;format&nbsp;a8&nbsp;wrap&nbsp;heading&nbsp;&lsquo;Last&nbsp;|Name&rsquo;; <br />&nbsp;&nbsp;&nbsp;SQL&gt;column&nbsp;state_cd&nbsp;format&nbsp;a8&nbsp;heading&nbsp;&lsquo;State&nbsp;|&nbsp;Code&rsquo;&nbsp;; <br />&nbsp;&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;8&nbsp;&nbsp;表示显示宽度， <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;a&nbsp;&nbsp;表示每个位置只能是字符 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;wrap&nbsp;说明若last_name长度大于8个字符，多余的字符显示下一行的对应<br />位置。 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Heading&nbsp;部分告诉SQL*plus，last_name的列标。 <br />&nbsp;&nbsp;&nbsp;现在我们查询一下customer表来看不下输出效果： <br />SQL&gt;select&nbsp;*&nbsp;from&nbsp;customer&nbsp;; <br />Sun&nbsp;Jul&nbsp;04&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;page&nbsp;&nbsp;&nbsp;&nbsp;1 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Database&nbsp;Technologies <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Customer&nbsp;Report <br /><br />Last&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;State <br />Name&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Code&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;SALES <br />--------&nbsp;--&nbsp;---------- <br />Teplow&nbsp;&nbsp;&nbsp;MA&nbsp;&nbsp;&nbsp;23445.67 <br />Abbev&nbsp;&nbsp;&nbsp;&nbsp;CA&nbsp;&nbsp;&nbsp;&nbsp;6969.96 <br />Porter&nbsp;&nbsp;&nbsp;CA&nbsp;&nbsp;&nbsp;&nbsp;6989.99 <br />Martin&nbsp;&nbsp;&nbsp;CA&nbsp;&nbsp;&nbsp;&nbsp;2345.45 <br />Laursen&nbsp;&nbsp;CA&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;34.34 <br />Bambi&nbsp;&nbsp;&nbsp;&nbsp;CA&nbsp;&nbsp;&nbsp;&nbsp;1234.55 <br />McGraw&nbsp;&nbsp;&nbsp;NJ&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;123.45 <br /><br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-------------------sample.sql--------------------- <br /><br /><br /><br />本章小结： <br />本章简要地介绍了SQL及其一些常用的命令，及SQL*Plus的应用。有关SQL的更详细的使用<br />说明可以参阅本第4章至第8章，课本在从建表到查询等操作都有较为详细的介绍，虽然书<br />中的章节较长，但其内容简单易懂，由于课时所限无法在此逐一介绍。建议大家可以在自<br />己的PC上安装个Personal&nbsp;Oracle&nbsp;8，按课本的例子，进行学习试验。 <br /><br /><br />第五章．PL/SQＬ <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;前面我们所使用的SQL语言，它不具备过程能力，但Oracle通过PL/SQL语言对SQL进行<br />了过程语言功能的扩展。PL/SQL是一种比较复杂的的程序设计语言，用于从不同环境中访<br />问Oracle数据库，。 <br />PL/SQL是Procedural&nbsp;Language/SQL（过程性语言的缩写）。正如其名所表达的，PL/SQL通<br />过增加了用在其他过程性语言中的结构(construct)来对SQL进行了扩展，例如： <br />变量和类型（包括预定义的和用户定义的） <br />控制结构,例如IF-THEN-ELSE语句和循环。 <br />过程和函数 <br />对象类型和方法 <br />&nbsp;&nbsp;&nbsp;&nbsp;过程性结构与Oracle&nbsp;SQL无缝地集成在一起，这样便产生了一种结构化的强有力的语<br />言。在使用Oracle的存储过程、数据库触发器、包和函数都要用PL/SQL编写代码。因此，<br />如果不了解PL/SQL就不能深入掌握Oracle。 <br />&nbsp;&nbsp;&nbsp;&nbsp;PL/SQL具有高度的可移植性，在所有Oracle平台上都是标准化的。因为其数据类型基<br />于数据库服务器，所以语言完全与机器无关。你无需针对UNIX、Windows、Netware等等去<br />学习各种PL/SQL。PL/SQL程序可以在任何Oracle&nbsp;Server上编译和运行而无需进行任何修改<br />。 <br /><br /><br />一．PL/SQL基础&nbsp;&nbsp;&nbsp;&nbsp; <br />&nbsp;下面我们通过实例程序来学习PL/SQL： <br />首先我们可以运行一下hello.sql这一简单的程序，此程序输出&rdquo;Hello,world!&rdquo;。 <br />Hello.sql <br />SET&nbsp;SERVEROUTPUT&nbsp;ON <br />BEGIN <br />&nbsp;&nbsp;DBMS_OUTPUT.enable; <br />&nbsp;&nbsp;DBMS_OUTPUT.put_line(&lsquo;Hello,&nbsp;world!&rsquo;); <br />END; <br />/ <br />&nbsp;&nbsp;&nbsp;启动SQL*plus并以system帐号连接Oracle. <br />&nbsp;SQL&gt;start&nbsp;c:\plssql\hello.sql&nbsp; <br />&nbsp;&nbsp;&nbsp;用以上命令运行些程序。 <br />&nbsp;&nbsp;&nbsp;第1行让SQL*Plus写出服务器返回给它的内容。 <br />&nbsp;&nbsp;&nbsp;第2行和第5&nbsp;行提供当前块的作用范围。 <br />&nbsp;&nbsp;&nbsp;第3行打开输出机制。 <br />&nbsp;&nbsp;&nbsp;第4行打印簇&ldquo;Hello,&nbsp;world!&rdquo;。 <br />&nbsp;&nbsp;&nbsp;第6行执行这个无名PL/SQL块。 <br />服务器响应如下： <br />Hello,&nbsp;World! <br />PL/SQL过程已成功完成. <br />SQL&gt; <br />&nbsp;&nbsp;&nbsp;&nbsp;在PL/SQL中字符串用单引号围起来，PL/SQL对文字大小写唯一敏感的地方是在字符串<br />是，对一些变量、命令等大小写不敏感。 <br />数据文字可以任何整数或浮点数值，例如： <br />整数文字 <br />-12345.0&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;浮点数文字 <br />1234.567890&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;浮点文字可以是任意精度 <br />这也是浮点文字，精度为零 <br />1.2345E2&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;可以使用科学计数 <br />1.2345E-3 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;0.123&nbsp;或&nbsp;.123&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;开头的0是可选择的 <br /><br />下面我们再来看另一个程序: <br />Circle.sql <br />DECLARE <br />&nbsp;&nbsp;PI&nbsp;CONSTANT&nbsp;REAL:=3.14159265359;&nbsp;&nbsp;&nbsp;--&nbsp;PI常量值 <br />&nbsp;&nbsp;Circumference&nbsp;REAL;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;--周长 <br />&nbsp;&nbsp;Area&nbsp;REAL;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;--面积 <br />&nbsp;&nbsp;Radius&nbsp;REAL:=&amp;Radius;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;--半径 <br />BEGIN <br />&nbsp;&nbsp;Circumference:=PI*radius*2.0; <br />&nbsp;&nbsp;Area:=PI*radius**2; <br />&nbsp;&nbsp;DBMS_OUTPUT.put_line(&lsquo;Radius=&rsquo;||To_CHAR(radius)|| <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&rsquo;,Circumference=&rsquo;||To_CHAR(circumference)|| <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lsquo;,Area=&rsquo;||To_CHAR(area)); <br />END; <br />/ <br />SQL&gt;&nbsp;start&nbsp;c:\plsql\circle.sql <br />在运行这个程序时，SQL*Plus首先提示你给&amp;号指定的联编变量指定一个值（第5行）屏幕<br />显示信息为： <br />输入radius的值：&nbsp;5 <br />原值&nbsp;&nbsp;&nbsp;5：&nbsp;&nbsp;Radius&nbsp;REAL:=&amp;Radius; <br />新值&nbsp;&nbsp;&nbsp;5：&nbsp;&nbsp;Radius&nbsp;REAL:=5; <br />Radius=5,Circumference=31.4159265359,Area=78.53981633975 <br /><br />PL/SQL&nbsp;过程已成功完成。 <br /><br />&nbsp;&nbsp;&nbsp;SQL&gt; <br /><br />程序注释 <br />单行注释 <br />&nbsp;&nbsp;单行注释由两个连字符开始，后面一直到行尾都是注释（回车符标识着注释的结束）。<br /><br />如上边程序中的： <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;PI&nbsp;CONSTANT&nbsp;REAL:=3.14159265359;&nbsp;&nbsp;&nbsp;--&nbsp;PI常量值 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;如果行注释超过一行，必须在每一行的开头上使用双连字符(--)。 <br /><br />多行注释 <br />多行注释由/*开始，由*/结束。这是C语言中使用的注释风格。如circle.sql中的开头部分<br />所示。 <br />多行注释可以扩展到任意多的行上，但它们不能嵌套。 <br /><br />PL/SQL块结构 <br />PL/SQL块是基本的编程结构，用块结构进行编程适用于自上而下的结构化积木式编程和直<br />观逻辑组织。 <br />一个无名PL/SQL块有三部分：说明部分、正文（体）部分和异常部分。其中异常部分为可<br />选项。 <br />&nbsp;&nbsp;&nbsp;&nbsp;DECLARE <br />----&nbsp;declarations&nbsp;(说明) <br />&nbsp;BEGIN <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;----executable&nbsp;code(执行代码) <br />EXCEPTION <br />&nbsp;&nbsp;&nbsp;&nbsp;----&nbsp;&nbsp;exception&nbsp;handlers(异常处理代码) <br />END; <br />实际上说明部分也是可选项，但不声明变量是不能执行实质性的工作。用户定义的全部变<br />量、常数、数据类型、指示器、函数和过程均在这一部分中说明。若没有定义其中任何一<br />个，你可以略去这一部分。 <br /><br />变量声明 <br />&nbsp;&nbsp;&nbsp;PL/SQL提供了SQL没有的附加数据类型。除一般的Oracle&nbsp;SQL数据类型外，PL/SQL还可<br />以让您用用这些数据类型对变量进行说明： <br /><br />&nbsp;&nbsp;&nbsp;BOOLEAN&nbsp;&nbsp;&nbsp;布尔类型&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;可用预定义常量TRUE、FALSE或NULL对一个布尔变量赋值。<br /><br />&nbsp;&nbsp;&nbsp;BINARY-INTEGER&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;该类型适用于在-2,147,483,647到2,147,483,643 <br />&nbsp;&nbsp;&nbsp;(二进制整数)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;范围内的带符号整数 <br />&nbsp;&nbsp;&nbsp;NATURAL(自然数)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;是BINARY-INTEGER的一个子集，这种数据类型是整数集的<br />一部分，从0到2,147,483,647。 <br />&nbsp;&nbsp;&nbsp;POSITIVE（正整数）&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;是BINARY-INTEGER的另一个子集,&nbsp;这种数据类型是整数<br />集的一部分，从0到2,147,483,647。 <br />&nbsp;&nbsp;&nbsp;%TYPE&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;这种设计可使您说明一个变量的数据类型与某一指定列的<br />数据类型相同，其结果产生更易于维护的PL/SQL代码。 <br />&nbsp;&nbsp;&nbsp;%ROWTYPE&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;用这种数据类型您可以说明一个复合变量，与一特定表中的<br />一行相同，这种复合变量是由引用表中的列名和数据类型组成的。 <br />&nbsp;&nbsp;&nbsp;除此之外，PL/SQL还提供两种复合数据类型：TABLE类型和RECORD型。我们将在以后介<br />绍。 <br />变量作用域 <br />&nbsp;&nbsp;&nbsp;变量在仅它所在的块内块内是可见的。 <br />&lt;&lt;l_outer&gt;&gt; <br />DECLARE <br />&nbsp;&nbsp;V_AvailableFlag&nbsp;BOOLEAN; <br />&nbsp;&nbsp;V_SSN&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;NUMBER(9); <br />BEGIN <br />fds <br />DECLARE <br />&nbsp;&nbsp;V_SSN&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;CHAR(11); <br />BEGIN <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;--v_SSN(char&nbsp;11)是可见的，要引用v_SSN(number&nbsp;9)可用 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;--&nbsp;l_outerV_SSN <br />END; <br /><br />END; <br /><br />变量名风格 <br />变量名的关键是它们是描述性的。声明 <br />&nbsp;x&nbsp;number; <br />不会告诉您有关x的用途的任何事情。但是 <br />&nbsp;v_StudenID&nbsp;&nbsp;NUMBER(5); <br />将告诉我们该变量可能要用来存储学生ID号，尽管在声明旁边没有解释的注释。请记住，<br />PL/SQL标识符的最大长度是30个字符，所有的字符都可以用来传递一些含义的。30个字符<br />通常足以用来存储一个描述性的名称了。 <br />变量名也可以告诉我们该变量的用途。有的人使用下划线将一个字母代码和变量的其他部<br />分分隔来以指明这一点。例如： <br />v_VariableName&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;程序变量 <br />e_ExceptionName&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;用户定义异常 <br />t_TypeName&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;用户定义类型 <br />p_ParameterName&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;过程或函数参数 <br />c_ConstantValue&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;常量 <br /><br /><br /><br /><br />&nbsp;&nbsp;下面我们再来看一个程序,&nbsp;loop.sql&nbsp;&nbsp;(参见课本P198) <br />CREATE&nbsp;TABLE&nbsp;test_table&nbsp;(record_number&nbsp;number(3),current_date&nbsp;date); <br /><br />DECLARE <br />&nbsp;&nbsp;max_records&nbsp;CONSTANT&nbsp;int:=100; <br />&nbsp;&nbsp;I&nbsp;&nbsp;&nbsp;int:=1; <br />BEGIN <br />&nbsp;&nbsp;FOR&nbsp;I&nbsp;in&nbsp;1..max_records&nbsp;LOOP <br />&nbsp;&nbsp;&nbsp;&nbsp;If&nbsp;&nbsp;(mod(i,10)=0)&nbsp;&nbsp;&nbsp;then <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;INSERT&nbsp;INTO&nbsp;test_table <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(record_number,current_date) <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;VALUES <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(I,&nbsp;SYSDATE); <br />&nbsp;&nbsp;&nbsp;&nbsp;ELSE <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;NULL; <br />&nbsp;&nbsp;&nbsp;&nbsp;END&nbsp;IF; <br />&nbsp;&nbsp;END&nbsp;LOOP; <br />&nbsp;&nbsp;COMMIT; <br />END; <br />/ <br /><br />COLUMN&nbsp;current_date&nbsp;FORMAT&nbsp;a20 <br />SELECT&nbsp;&nbsp;record_number,to_char(sysdate,'HH24:MI&nbsp;SS')&nbsp;&nbsp;FROM&nbsp;test_table; <br />&nbsp;&nbsp;&nbsp;&nbsp;DROP&nbsp;TABLE&nbsp;test_table; <br /><br />循环语句&nbsp;(P.195) <br />&nbsp;FOR-LOOP&nbsp;与&nbsp;WHILE-LOOP&nbsp;&nbsp; <br />&nbsp;&nbsp;语法： <br />&nbsp;FOR&nbsp;loop&nbsp;variable&nbsp;IN&nbsp;[REVERSE]&nbsp;lower-bound..upper-bound&nbsp;LOOP <br />&nbsp;&nbsp;&nbsp;Statement;&nbsp;&hellip;&nbsp;statemnet; <br />&nbsp;END&nbsp;LOOP; <br /><br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;WHILE&nbsp;condition&nbsp;LOOP <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Statement;&nbsp;&hellip;&nbsp;statement; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;END&nbsp;LOOP; <br /><br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Condition是一个有效的PL/SQL条件； <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Statement是一个有效的PL/SQL语句。 <br />&nbsp; <br />简单的LOOP语句 <br />&nbsp;&nbsp;语法： <br />LOOP&nbsp; <br />&nbsp;&nbsp;&nbsp;Statement;&nbsp;&hellip;&nbsp;statement; <br />END&nbsp;LOOP; <br />无条件循环，为了跳出循环，可在当一个条件被满足时执行EXIT语句。 <br /><br />&nbsp;&nbsp;EXIT语句： <br />EXIT&nbsp;&nbsp;[lable-name]&nbsp;&nbsp;WHEN&nbsp;condition; <br />&nbsp; <br />&nbsp;IF语句 <br />&nbsp;&nbsp;&nbsp;IF&nbsp;&nbsp;condition&nbsp;THEN <br />Statement;&nbsp;&nbsp;&hellip;&nbsp;statement; <br />[ELSIF&nbsp;&nbsp;condition&nbsp;&nbsp;THEN&nbsp; <br />&nbsp;&nbsp;Statement;&nbsp;&nbsp;&hellip;&nbsp;statement; <br />&nbsp;&nbsp;&hellip; <br />[ELSIF&nbsp;&nbsp;condition&nbsp;THEN <br />&nbsp;&nbsp;statement;&nbsp;&hellip;&nbsp;statement; <br />[ELSE&nbsp; <br />&nbsp;&nbsp;statement;&nbsp;&nbsp;&hellip;&nbsp;statement;] <br />END&nbsp;IF; <br />&nbsp;&nbsp;注意拼写：是ELSIF而不是ELSEIF；END&nbsp;IF而不是ENDIF。 <br /><br /><br />使用过程 <br />&nbsp;&nbsp;&nbsp;过程是执行少量重复工作、严格地通过参数列表传入和传出值的子例行程序。 <br />&nbsp;&nbsp;&nbsp;Table.sql&nbsp; <br />SET&nbsp;SERVEROUTPUT&nbsp;ON <br />DECLARE&nbsp; <br />&nbsp;&nbsp;--&nbsp;&nbsp;常量 <br />&nbsp;&nbsp;TB&nbsp;CONSTANT&nbsp;VARCHAR2(1):=CHR(9);&nbsp;&nbsp;&nbsp;--&nbsp;TAB <br />&nbsp;&nbsp;--&nbsp;&nbsp;变量 <br />&nbsp;&nbsp;status&nbsp;NUMERIC; <br />&nbsp;&nbsp;table_rec&nbsp;&nbsp;all_tables%ROWTYPE; <br />&nbsp;&nbsp;--&nbsp;&nbsp;例程&nbsp; <br />&nbsp;&nbsp;PROCEDURE&nbsp;get_table(Powner&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;IN&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;all_tables.owner%TYPE, <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Ptable&nbsp;&nbsp;&nbsp;&nbsp;IN&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;all_tables.table_name%TYPE, <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Prec&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;OUT&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;all_tables%ROWTYPE, <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Pstatus&nbsp;&nbsp;&nbsp;&nbsp;IN&nbsp;&nbsp;&nbsp;OUT&nbsp;NUMBER)&nbsp;IS <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;--&nbsp;Local&nbsp;cursors <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;CURSOR&nbsp;table_cur&nbsp;(Cowner&nbsp;all_tables.owner%TYPE, <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Ctable&nbsp;all_tables.table_name%TYPE)&nbsp;IS <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;SELECT&nbsp;&nbsp;*&nbsp; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;FROM&nbsp;all_tables <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;WHERE&nbsp;owner=Cowner&nbsp;AND&nbsp;table_name&nbsp;=&nbsp;Ctable; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;--&nbsp;局部变量 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Lowner&nbsp;&nbsp;all_tables.owner%TYPE; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Ltable&nbsp;&nbsp;all_tables.table_name%TYPE; <br />&nbsp;&nbsp;BEGIN <br />&nbsp;&nbsp;&nbsp;&nbsp;Pstatus:=0;&nbsp;&nbsp;&nbsp;&nbsp;--&nbsp;OK <br />&nbsp;&nbsp;&nbsp;&nbsp;Lowner:=UPPER(Powner); <br />&nbsp;&nbsp;&nbsp;&nbsp;Ltable:=UPPER(Ptable); <br />&nbsp;&nbsp;&nbsp;&nbsp;OPEN&nbsp;table_cur(Lowner,&nbsp;Ltable); <br />&nbsp;&nbsp;&nbsp;&nbsp;FETCH&nbsp;table_cur&nbsp;INTO&nbsp;Prec; <br />&nbsp;&nbsp;&nbsp;&nbsp;IF&nbsp;(table_cur%NOTFOUND)&nbsp;THEN <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;RAISE&nbsp;NO_DATA_FOUND; <br />&nbsp;&nbsp;&nbsp;&nbsp;END&nbsp;IF; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;CLOSE&nbsp;table_cur; <br />&nbsp;&nbsp;&nbsp;&nbsp;EXCEPTION <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;WHEN&nbsp;OTHERS&nbsp;THEN <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;BEGIN <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Pstatus:=SQLCODE;&nbsp;&nbsp;&nbsp;--&nbsp;捕获错误代码 <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;IF&nbsp;(table_cur%ISOPEN)&nbsp;THEN <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;CLOSE&nbsp;table_cur; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;END&nbsp;IF; <br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Pr</p>
</div><img src="http://www.cnblogs.com/meetrice/aggbug/1610714.html?type=1" width="1" height="1" alt=""/><p>评论: 0　<a href="http://www.cnblogs.com/meetrice/archive/2009/11/25/1610714.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2009/11/25/1610714.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item><item><title>(转)用Delphi中的TADOQuery查询Oracle10G中的数据表时,Open时提示&amp;quot;数据类型不被支持&amp;quot;的处理方法</title><link>http://www.cnblogs.com/meetrice/archive/2009/11/23/1608534.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Mon, 23 Nov 2009 02:48:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2009/11/23/1608534.html</guid><description><![CDATA[<p>阅读: 61 评论: 0 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2009-11-23 10:48 <a href="http://www.cnblogs.com/meetrice/archive/2009/11/23/1608534.html" target="_blank">原文链接</a></p><p>原因是你用的ADO&nbsp;&nbsp; for&nbsp;&nbsp; ORACLE的驱动是微软的Microsoft OLE DB provider&nbsp;&nbsp; for Oracle，不支持BLOB字段, 应使用ORACLE的驱动ORACLE&nbsp;&nbsp; provider&nbsp;&nbsp; for&nbsp;&nbsp; OLE&nbsp;&nbsp; DB，如果未装Oracle，可以&nbsp;&nbsp; <br />&nbsp; 去Oracle公司网站下载这个驱动。</p>
<p>Microsoft OLE DB provider&nbsp;&nbsp; for Oracle 的连接字符串:</p>
<p>Provider=MSDAORA.1;Password=nchyuser;User ID=nchyuser;Data Source=ncms</p>
<p>ORACLE&nbsp;&nbsp; provider&nbsp;&nbsp; for&nbsp;&nbsp; OLE&nbsp;&nbsp; DB的连接字符串:</p>
<p>Provider=OraOLEDB.Oracle;Password=nchyuser;Persist Security Info=True;User ID=nchyuser;Data Source=NCMS;Extended Properties=""</p>
<p>使用ORACLE&nbsp;&nbsp; provider&nbsp;&nbsp; for&nbsp;&nbsp; OLE&nbsp;&nbsp; DB的连接字符串就OK.</p>
<p>&nbsp;</p>
<p>本文来自CSDN博客，转载请标明出处：<a href="http://blog.csdn.net/zhuchengchuan/archive/2009/07/18/4358996.aspx">http://blog.csdn.net/zhuchengchuan/archive/2009/07/18/4358996.aspx</a></p><img src="http://www.cnblogs.com/meetrice/aggbug/1608534.html?type=1" width="1" height="1" alt=""/><p>评论: 0　<a href="http://www.cnblogs.com/meetrice/archive/2009/11/23/1608534.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2009/11/23/1608534.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item><item><title>extjs数据存储与传输</title><link>http://www.cnblogs.com/meetrice/archive/2009/11/17/1604780.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Tue, 17 Nov 2009 09:21:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2009/11/17/1604780.html</guid><description><![CDATA[<p>阅读: 624 评论: 1 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2009-11-17 17:21 <a href="http://www.cnblogs.com/meetrice/archive/2009/11/17/1604780.html" target="_blank">原文链接</a></p><p>
<p class="MsoNormal"><span><span class="5"><span>本章内容</span></span><span class="5"><span lang="EN-US"></span></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>简介</span><span lang="EN-US"></span></span></p>
<p class="a2"><span class="50"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span></p>
<p class="a2"><span class="50"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span></p>
<p class="a2"><span class="50"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>常用</span></span><span><span class="50"><span lang="EN-US">proxy</span></span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>常用</span></span><span><span class="50"><span lang="EN-US">reader</span></span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>高级</span></span><span><span class="50"><span lang="EN-US">store</span></span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span lang="EN-US"><span>EXT</span></span><span>中的</span><span lang="EN-US"><span>Ajax</span></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>关于</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>和</span></span><span><span class="50"><span lang="EN-US">createDelegate()</span></span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span lang="EN-US"><span>DWR</span></span><span>与</span><span lang="EN-US"><span>EXT</span></span><span>整合</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085913"></a><a name="_Toc205277864"></a><a name="ext-ch-03-01"></a><span><span><span><span lang="EN-US"><span>10.1</span></span></span></span><span><span><span>　</span><span lang="EN-US"><span>Ext.data</span></span></span></span><span><span><span>简介</span></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>Ext.data</span></span><span>在命名空间中定义了一系列</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>。</span><span lang="EN-US"><span>Grid</span></span><span>和</span><span lang="EN-US"><span>ComboxBox</span></span><span>都是以</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>为媒介获取数据的，它包含异步加载、类型转换、分页等功能。</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>默认支持</span></span><span class="50"><span lang="EN-US"><span>Array</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>JSON</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>XML</span></span></span><span><span>等数据格式，可以通过</span><span lang="EN-US"><span>Memory</span></span><span>、</span><span lang="EN-US"><span>HTTP</span></span><span>、</span><span lang="EN-US"><span>ScriptTag</span></span><span>等方式获得这些格式的数据。如果要实现新的协议和新的数据结构，只需要扩展</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>即可。</span><span lang="EN-US"><span>DWRProxy</span></span><span>就实现了自身的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>，让</span><span lang="EN-US"><span>EXT</span></span><span>可以直接从</span><span lang="EN-US"><span>DWR</span></span><span>获得数据。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085914"></a><a name="_Toc205277865"><span><span lang="EN-US"><span>10.2</span></span></span></a><span><span><span><span>　</span></span></span><span><span><strong><span lang="EN-US">Ext.data.Connection</span></strong></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>是对</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>的封装，它提供了配置使用</span><span lang="EN-US"><span>Ajax</span></span><span>的通用方式，它在内部通过</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>实现与后台的异步调用。与底层的</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>相比，</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Connection</span></span></span><span><span>提供了更简洁的配置方式，使用起来更方便。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>主要用于在</span></span><span class="50"><span lang="EN-US"><span>Ext.data.HttpProxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>Ext.data.ScriptTagProxy</span></span></span><span><span>中执行与后台交互的任务，它会从指定的</span><span lang="EN-US"><span>URL</span></span><span>获得数据，并把后台返回的数据交给</span><span lang="EN-US"><span>HttpProxy</span></span><span>或</span><span lang="EN-US"><span>ScriptTagProxy</span></span><span>处理，</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>的使用方式如代码清单</span><span lang="EN-US"><span>10-1</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span></span><span class="5"><span lang="EN-US"><span>10-1</span></span></span><span>　使用</span></span></span><span><span><span class="50"><span lang="EN-US">Ext.data.Connection</span></span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var conn = new Ext.data.Connection({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>autoAbort: false,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>defaultHeaders: {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>referer: 'http://localhost:8080/'</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>disableCaching : false,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>extraParams : {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'name'</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>method : 'GET',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>timeout : 300,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>url : '01-01.txt'</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在使用</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>之前，都要像上面这样创建一个新的</span></span><span class="50"><span lang="EN-US"><span>Ext.Connection</span></span></span><span><span>实例。我们可以在构造方法里配置对应的参数，比如</span></span><span class="50"><span lang="EN-US"><span>autoAbort</span></span></span><span><span>表示链接是否会自动断开、</span></span><span class="50"><span lang="EN-US"><span>default- Headers</span></span></span><span><span>参数表示请求的默认首部信息、</span></span><span class="50"><span lang="EN-US"><span>disableCaching</span></span></span><span><span>参数表示请求是否会禁用缓存、</span></span><span class="50"><span lang="EN-US"><span>extraParams</span></span></span><span><span>参数代表请求的额外参数、</span></span><span class="50"><span lang="EN-US"><span>method</span></span></span><span><span>参数表示请求方法、</span></span><span class="50"><span lang="EN-US"><span>timeout</span></span></span><span><span>参数表示连接的超时时间、</span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>参数表示请求访问的网址等。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>在创建了</span></span><span class="50"><span lang="EN-US"><span>conn</span></span></span><span><span>之后，可以调用</span></span><span class="50"><span lang="EN-US"><span>request()</span></span></span><span><span>函数发送请求，处理返回的结果，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>conn.request({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>success: function(response) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('info', response.responseText);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>failure: function</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>&nbsp;{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('warn', 'failure');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Request()</span></span></span><span><span>函数中可以设置</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>failure</span></span></span><span><span>两个回调函数，分别在请求成功和请求失败时调用。请求成功时，</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>函数的参数就是后台返回的信息。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>我们再来看一下</span></span><span class="50"><span lang="EN-US"><span>request</span></span></span><span><span>函数中的其他参数。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>url:String</span></span></span><span><span>：请求</span><span lang="EN-US"><span>url</span></span><span>。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>params:Object/String/Function</span></span></span><span><span>：请求传递的参数。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>method:String</span></span></span><span><span>：请求方法，通常为</span></span><span class="50"><span lang="EN-US"><span>GET</span></span></span><span><span>或</span></span><span class="50"><span lang="EN-US"><span>POST</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>callback:Function</span></span></span><span><span>：请求完成后的回调函数，无论是成功还是失败，都会执行。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>success:Function</span></span></span><span><span>：请求成功时的回调函数。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>failure:Function</span></span></span><span><span>：请求失败时的回调函数</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>scope:Object</span></span></span><span><span>：回调函数的作用域。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>form:Object/String</span></span></span><span><span>：绑定的</span></span><span class="50"><span lang="EN-US"><span>form</span></span></span><span><span>表单。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>isUpload:Boolean</span></span></span><span><span>：是否执行文件上传。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>headers:Object</span></span></span><span><span>：请求首部信息。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>xmlData:Object</span></span></span><span><span>：</span><span lang="EN-US"><span>XML</span></span><span>文档对象，可以通过</span><span lang="EN-US"><span>URL</span></span><span>附加参数的方式发起请求。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>disableCaching:Boolean</span></span></span><span><span>：是否禁用缓存，默认为禁用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>还提供了</span></span><span class="50"><span lang="EN-US"><span>abort([Number transactionId])</span></span></span><span><span>函数，当同时有多个请求发生时，根据指定的事务</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>放弃其中的某一个请求。如果不指定事务</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>，就会放弃最后一个请求。</span></span><span class="50"><span lang="EN-US"><span>isLoading([Number transactionId])</span></span></span><span><span>函数的用法与</span></span><span class="50"><span lang="EN-US"><span>abort()</span></span></span><span><span>类似，可以根据事务</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>判断对应的请求是否完成。如果未指定事务</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>，就判断最后一个请求是否完成。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085915"></a><a name="_Toc205277866"><span><span lang="EN-US"><span>10.3</span></span></span></a><span><span><span><span>　</span></span></span><span><span><strong><span lang="EN-US">Ext.data.Record</span></strong></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>就是一个设定了内部数据类型的对象，它是</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>的最基本组成部分。如果把</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>看作是一张二维表，那么它的每一行就对应一个</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Record</span></span></span><span><span>实例。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>的主要功能是保存数据，并且在内部数据发生改变时记录修改的状态，它还可以保留修改之前的原始值。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>我们使用</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>时通常都是由</span></span><span class="50"><span lang="EN-US"><span>create()</span></span></span><span><span>函数开始，首先用</span></span><span class="50"><span lang="EN-US"><span>create()</span></span></span><span><span>函数创建一个自定义的</span></span><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>类型，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var PersonRecord = Ext.data.Record.create([</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name: 'name', type: 'string'},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name: 'sex', type: 'int'}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>]);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>PersonRecord</span></span></span><span><span>就是我们定义的新类型，包含字符串类型的</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>和整数类型的</span></span><span class="50"><span lang="EN-US"><span>sex</span></span></span><span><span>两个属性，然后我们使用</span></span><span class="50"><span lang="EN-US"><span>new</span></span></span><span><span>关键字创建</span></span><span class="50"><span lang="EN-US"><span>PersonRecord</span></span></span><span><span>的实例，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var boy = new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'boy',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>创建对象时，可以直接通过构造方法为对象赋予初始值，将</span></span><span class="50"><span lang="EN-US"><span>'boy'</span></span></span><span><span>赋值给</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>，</span></span><span class="50"><span lang="EN-US"><span>0</span></span></span><span><span>赋值给</span></span><span class="50"><span lang="EN-US"><span>sex</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>现在，我们得到了</span></span><span class="50"><span lang="EN-US"><span>PersonRecord</span></span></span><span><span>的实例</span></span><span class="50"><span lang="EN-US"><span>boy</span></span></span><span><span>，如何才能得到它的属性呢？以下三种方式都可以获得</span><span class="50"><span lang="EN-US">boy</span></span><span>中</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>属性的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(boy.data.name);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(boy.data['name']);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(boy.get('name'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这里涉及</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>属性，这是定义在</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>中的一个公共属性，用于保存当前</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>对象的所有数据。它是一个</span><span lang="EN-US"><span>JSON</span></span><span>对象，可以直接从它里面获得需要的数据。可以通过</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>get()</span></span></span><span><span>函数方便地从</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>属性中获得指定的属性值。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果我们需要修改</span></span><span class="50"><span lang="EN-US"><span>boy</span></span></span><span><span>中的数据，请不要使用以下方式直接操作</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>boy.data.name = 'boy name';</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>boy.data['name'] = 'boy name';</span></span></span></p>
<p class="MsoNormal"><span><span>而应该使用</span></span><span class="50"><span lang="EN-US"><span>set()</span></span></span><span><span>函数，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>boy.set('name', 'body name');</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>set()</span></span></span><span><span>函数会判断属性值是否发生了改变，如果改变了，就要将当前对象的</span></span><span class="50"><span lang="EN-US"><span>dirty</span></span></span><span><span>属性设置为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>，并将修改之前的原始值放入</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>对象中，供其他函数使用。如果直接操作</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>中的值，</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>就无法记录属性数据的修改情况。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>的属性数据被修改后，我们可以执行如下几种操作。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>commit()</span></span></span><span><span>（提交）：这个函数的效果是设置</span></span><span class="50"><span lang="EN-US"><span>dirty</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>，并删除</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>中保存的原始数据。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>reject()</span></span></span><span><span>（撤销）：这个函数的效果是将</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>中已经修改了的属性值都恢复成</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>中保存的原始数据，然后设置</span></span><span class="50"><span lang="EN-US"><span>dirty</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>，并删除保存原始数据的</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>对象。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>getChanges()</span></span></span><span><span>获得修改的部分：这个函数会把</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>中经过修改的属性和数据放在一个</span><span lang="EN-US"><span>JSON</span></span><span>对象里并返回。例如上例中，</span></span><span class="50"><span lang="EN-US"><span>getChanges()</span></span></span><span><span>返回的结果是</span></span><span class="50"><span lang="EN-US"><span>{name:&rsquo;body name&rsquo;}</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>我们还可以调用</span></span><span class="50"><span lang="EN-US"><span>isModified()</span></span></span><span><span>判断当前</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>中的数据是否被修改。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>还提供了用于复制</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>实例的函数</span></span><span class="50"><span lang="EN-US"><span>copy()</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;</span>var copyBoy = boy.copy</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这样我们就得到了</span></span><span class="50"><span lang="EN-US"><span>boy</span></span></span><span><span>的一个副本，它里面包含了</span></span><span class="50"><span lang="EN-US"><span>boy</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span class="50"><span>数据</span></span><span>，但</span></span><span class="50"><span lang="EN-US"><span>copy()</span></span></span><span><span>函数不会复制</span></span><span class="50"><span lang="EN-US"><span>dirty</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>等额外的属性值。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>中其他的参数大多与</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>有关，请参考与</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>相关的讨论。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085916"></a><a name="_Toc205277867"><span><span lang="EN-US"><span>10.4</span></span></span></a><span><span><span><span>　</span></span></span><span><span><strong><span lang="EN-US">Ext.data.Store</span></strong></span></span><strong><span lang="EN-US"></span></strong><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><a name="ext-ch-08-04-01-01"></a><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>是</span><span lang="EN-US"><span>EXT</span></span><span>中用来进行数据交换和数据交互的标准中间件，无论是</span><span lang="EN-US"><span>Grid</span></span><span>还是</span><span lang="EN-US"><span>ComboBox</span></span><span>，都是通过它实现数据读取、类型转换、排序分页和搜索等操作的。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>中有一个</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>数组，所有数据都存放在这些</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Record</span></span></span><span><span>实例中，为后面的读取和修改操作做准备。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085917"></a><a name="_Toc205277868"></a><span><span><span><span><span>10.4.1</span></span></span></span><span><span><span>　</span></span></span><span><span><span>基本应用</span></span></span><span></span></span></p>
<p class="MsoNormal"><span><span>在使用之前，首先要创建一个</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>的实例，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var data = [</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>['boy', 0],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>['girl', 1]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>];</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var store = new Ext.data.Store({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy: new Ext.data.MemoryProxy(data),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ArrayReader({}, PersonRecord)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span>store.load</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>每个</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>最少需要两个组件的支持，分别是</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>，</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>用于从某个途径读取原始数据，</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>用于将原始数据转换成</span></span><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>实例。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>这里我们使用的是</span></span><span class="50"><span lang="EN-US"><span>Ext.data.MemoryProxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>Ext.data.ArrayReader</span></span></span><span><span>，将</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>数组中的数据转换成对应的几个</span></span><span class="50"><span lang="EN-US"><span>PersonRecord</span></span></span><span><span>实例，然后放入</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中。</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>创建完毕之后，执行</span></span><span class="50"><span lang="EN-US"><span>store.load()</span></span></span><span><span>实现这个转换过程。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>经过转换之后，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>里的数据就可以提供给</span><span lang="EN-US"><span>Grid</span></span><span>或</span><span lang="EN-US"><span>ComboBox</span></span><span>使用了，这就是</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Store</span></span></span><span><span>的最基本用法。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085918"></a><a name="_Toc205277869"></a><span><span><span><span><span>10.4.2</span></span></span></span><span><span><span>　</span></span></span><span><span><span>对数据进行排序</span></span></span><span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>提供了一系列属性和函数，利用它们对数据进行排序操作。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>可以在创建</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>时使用</span></span><span class="50"><span lang="EN-US"><span>sortInfo</span></span></span><span><span>参数指定排序的字段和排序方式，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var store = new Ext.data.Store({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy: new Ext.data.MemoryProxy(data),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ArrayReader({}, PersonRecord),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sortInfo: {field: 'name', direction: 'DESC'}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这样，在</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>加载数据之后，就会自动根据</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>字段进行降序排列。对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>使用</span></span><span class="50"><span lang="EN-US"><span>store.setDefaultSort('name','DESC');</span></span></span><span><span>也会达到同样效果。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>也可以在任何时候调用</span></span><span class="50"><span lang="EN-US"><span>sort()</span></span></span><span><span>函数，比如</span></span><span class="50"><span lang="EN-US"><span>store.sort('name', 'DESC');</span></span></span><span><span>，对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行排序。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果我们希望获得</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>的排序信息，可以调用</span></span><span class="50"><span lang="EN-US"><span>getSortState()</span></span></span><span><span>函数，返回的是类似</span></span><span class="50"><span lang="EN-US"><span>{field: "name", direction: " DESC"}</span></span></span><span><span>的</span><span lang="EN-US"><span>JSON</span></span><span>对象。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>与排序相关的参数还有</span></span><span class="50"><span lang="EN-US"><span>remoteSort</span></span></span><span><span>，这个参数是用来实现后台排序功能的。当设置为</span></span><span class="50"><span lang="EN-US"><span>remoteSort:true</span></span></span><span><span>时，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>会在向后台请求数据时自动加入</span></span><span class="50"><span lang="EN-US"><span>sort</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>dir</span></span></span><span><span>两个参数，分别对应排序的字段和排序的方式，由后台获取并处理这两个参数，在后台对所需数据进行排序操作。</span></span><span class="50"><span lang="EN-US"><span>remoteSort:true</span></span></span><span><span>也会导致每次执行</span></span><span class="50"><span lang="EN-US"><span>sort()</span></span></span><span><span>时都要去后台重新加载数据，而不能只对本地数据进行排序。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>详细的用法可以参考第</span><span lang="EN-US"><span>2</span></span><span>章。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085919"></a><a name="_Toc205277870"></a><span><span><span><span><span>10.4.3</span></span></span></span><span><span><span>　</span></span></span><span><span><span>从</span></span></span><span><span><strong><span>store</span></strong></span></span><span><span><span>中获取数据</span></span></span><span></span></span></p>
<p class="MsoNormal"><span><span>从</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中获取数据有很多种途径，可以依据不同的要求选择不同的函数。最直接的方法是根据</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>在</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的行号获得对应的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，得到了</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>就可以使用</span></span><span class="50"><span lang="EN-US"><span>get()</span></span></span><span><span>函数获得里面的数据了，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.getAt(0).get('name')</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>通过这种方式，我们可以遍历</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中所有的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，依次得到它们的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>for (var i = 0; i &lt; store.getCount</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>; i++) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>var record = store.getAt(i);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>alert(record.get('name'));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Store.getCount()</span></span></span><span><span>返回的是</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的所有数据记录，然后使用</span></span><span class="50"><span lang="EN-US"><span>for</span></span></span><span><span>循环遍历整个</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>，从而得到每条记录。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>除了使用</span></span><span class="50"><span lang="EN-US"><span>getCount()</span></span></span><span><span>的方法外，还可以使用</span></span><span class="50"><span lang="EN-US"><span>each()</span></span></span><span><span>函数，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.each(function(record) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>alert(record.get('name'));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Each()</span></span></span><span><span>可以接受一个函数作为参数，遍历内部</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，并将每个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>作为参数传递给</span></span><span class="50"><span lang="EN-US"><span>function()</span></span></span><span><span>处理。如果希望停止遍历，可以让</span></span><span class="50"><span lang="EN-US"><span>function()</span></span></span><span><span>返回</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>也可以使用</span></span><span class="50"><span lang="EN-US"><span>getRange()</span></span></span><span><span>函数连续获得多个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，只需要指定开始和结束位置的索引值，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var records = store.getRange(0, 1);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>for (var i = 0; i &lt; records.length; i++) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>var record = records[i];</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>alert(record.get('name'));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果确实不知道</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>，也可以根据</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>本身的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>从</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中获得对应的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.getById(1001).get('name')</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>EXT</span></span><span>还提供了函数</span></span><span class="50"><span lang="EN-US"><span>find()</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>，可以利用它们对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行搜索，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>find( String property, String/RegExp value, [Number startIndex], [Boolean anyMatch],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>[Boolean caseSensitive] )</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在这</span><span lang="EN-US"><span>5</span></span><span>个参数中，只有前两个是必须的。第一个参数</span></span><span class="50"><span lang="EN-US"><span>property</span></span></span><span><span>代表搜索的字段名；第二个参数</span></span><span class="50"><span lang="EN-US"><span>value</span></span></span><span><span>是匹配用字符串或正则表达式；第三个参数</span></span><span class="50"><span lang="EN-US"><span>startIndex</span></span></span><span><span>表示从第几行开始搜索，第四个参数</span></span><span class="50"><span lang="EN-US"><span>anyMatch</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，不必从头开始匹配；第五个参数</span></span><span class="50"><span lang="EN-US"><span>caseSensitive</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，会区分大小写。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如下面的代码所示：</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var index = store.find('name','g');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.getAt(index).get('name'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>与</span></span><span class="50"><span lang="EN-US"><span>find()</span></span></span><span><span>函数对应的</span></span><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>函数的定义格式如下：</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>findBy( Function fn, [Object scope], [Number startIndex] ) : Number</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>函数允许用户使用自定义函数对内部数据进行搜索。</span></span><span class="50"><span lang="EN-US"><span>fn</span></span></span><span><span>返回</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，表示查找成功，于是停止遍历并返回行号。</span></span><span class="50"><span lang="EN-US"><span>fn</span></span></span><span><span>返回</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>时，表示查找失败（即未找到），继续遍历，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>index = store.findBy(function(record, id) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>return record.get('name') == 'girl' &amp;&amp; record.get('sex') == 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.getAt(index).get('name'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>通过</span></span><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>函数，我们可以同时判断</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>中的多个字段，在函数中实现复杂逻辑。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>我们还可以使用</span></span><span class="50"><span lang="EN-US"><span>query</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>queryBy</span></span></span><span><span>函数对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行查询。与</span></span><span class="50"><span lang="EN-US"><span>find</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>findBy</span></span></span><span><span>不同的是，</span></span><span class="50"><span lang="EN-US"><span>query</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>queryBy</span></span></span><span><span>返回的是一个</span></span><span class="50"><span lang="EN-US"><span>MixCollection</span></span></span><span><span>对象，里面包含了搜索得到的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.query('name', 'boy'));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>alert(store.queryBy(function(record) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>return record.get('name') == 'girl' &amp;&amp; record.get('sex') == 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}));</span></span></span></p>
<p class="111"><a name="_Toc216085920"></a><a name="_Toc205277871"></a><span><span><span><span lang="EN-US"><span>10.4.4</span></span></span></span><span><span><span>　</span></span></span><span><span><span>更新</span></span></span><span><span><strong><span lang="EN-US">store</span></strong></span></span><span><span><span>中的数据</span></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>可以使用</span></span><span class="50"><span lang="EN-US"><span>add(Ext.data.Record[] records)</span></span></span><span><span>向</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>末尾添加一个或多个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，使用的参数可以是一个</span><span lang="EN-US"><span>record</span></span><span>实例，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.add(new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Add()</span></span></span><span><span>的也可以添加一个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>数组，如下面的代码所示：</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.add([new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other1',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}), new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other2',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>})]);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Add()</span></span></span><span><span>函数每次都会将新数据添加到</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>的末尾，这就有可能破坏</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>原有的排序方式。如果希望根据</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>原来的排序方式将新数据插入到对应的位置，可以使用</span></span><span class="50"><span lang="EN-US"><span>addSorted()</span></span></span><span><span>函数。它会在添加新数据之后立即对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>进行排序，这样就可以保证</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据有序地显示，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.addSorted(new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'lili',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 1</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>会根据排序信息查找这条</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>应该插入的索引位置，然后根据得到的索引位置插入数据，从而实现对整体进行排序。这个函数需要预先为</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>设置本地排序，否则会不起作用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果希望自己指定数据插入的索引位置，可以使用</span></span><span class="50"><span lang="EN-US"><span>insert()</span></span></span><span><span>函数。它的第一个参数表示插入数据的索引位置，可以使用</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>实例或</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>实例的数组作为参数，插入之后，后面的数据自动后移，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.insert(3, new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.insert(3, [new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other1',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}), new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other2',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>})]);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>删除操作可以使用</span></span><span class="50"><span lang="EN-US"><span>remove()</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>removeAll()</span></span></span><span><span>函数，它们分别可以删除指定的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>和清空整个</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.remove(store.getAt(0));</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span>store.removeAll</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中没有专门提供修改某一行</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>的操作，我们需要先从</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中获取一个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>。对这个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>内部数据的修改会直接反映到</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>上，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.getAt(0).set('name', 'xxxx');</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>修改</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>的内部数据之后有两种选择：执行</span></span><span class="50"><span lang="EN-US"><span>rejectChanges()</span></span></span><span><span>撤销所有修改，将修改过的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>恢复到原来的状态；执行</span></span><span class="50"><span lang="EN-US"><span>commitChanges()</span></span></span><span><span>提交数据修改。在执行撤销和提交操作之前，可以使用</span></span><span class="50"><span lang="EN-US"><span>getModifiedRecords()</span></span></span><span><span>获得</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中修改过的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>数组。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>与修改数据相关的参数是</span></span><span class="50"><span lang="EN-US"><span>pruneModifiedRecords</span></span></span><span><span>，如果将它设置为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>，当每次执行删除或</span></span><span class="50"><span lang="EN-US"><span>reload</span></span></span><span><span>操作时，都会清空所有修改。这样，在每次执行删除或</span></span><span class="50"><span lang="EN-US"><span>reload</span></span></span><span><span>操作之后，</span></span><span class="50"><span lang="EN-US"><span>getModifiedRecords()</span></span></span><span><span>返回的就是一个空数组，否则仍然会得到上次修改过的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>记录。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085921"></a><a name="_Toc205277872"></a><span><span><span><span><span>10.4.5</span></span></span></span><span><span><span>　</span></span></span><span><span><span>加载及显示数据</span></span></span><span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>创建好后，需要调用</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>函数加载数据，加载成功后才能对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行操作。</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>调用的完整过程如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.load({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>params: {start:0,limit:20},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>callback: function(records, options, success){</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('info', '</span></span><span>加载完毕</span><span lang="EN-US"><span>');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>scope: store,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>add: true</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>是在</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>加载时发送的附加参数。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>是加载完毕时执行的回调函数，它包含</span><span lang="EN-US"><span>3</span></span><span>个参数：</span></span><span class="50"><span lang="EN-US"><span>records</span></span></span><span><span>参数表示获得的数据，</span></span><span class="50"><span lang="EN-US"><span>options</span></span></span><span><span>表示执行</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>时传递的参数，</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>表示是否加载成功。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Scope</span></span></span><span><span>用来指定回调函数执行时的作用域。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Add</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>得到的数据会添加在原来的</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>数据的末尾，否则会先清除之前的数据，再将得到的数据添加到</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>一般来说，为了对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行初始化，</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>函数只需要执行一次。如果用</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>参数指定了需要使用的参数，以后再次执行</span></span><span class="50"><span lang="EN-US"><span>reload()</span></span></span><span><span>重新加载数据时，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>会自动使用上次</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>中包含的</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>参数内容。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果有一些需要固定传递的参数，也可以使用</span></span><span class="50"><span lang="EN-US"><span>baseParams</span></span></span><span><span>参数执行，它是一个</span><span lang="EN-US"><span>JSON</span></span><span>对象，里面的数据会作为参数发送给后台处理，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.baseParams.start = 0;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.baseParams.limit = 20;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>为</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>加载数据之后，有时不需要把所有数据都显示出来，这时可以使用函数</span></span><span class="50"><span lang="EN-US"><span>filter</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>filterBy</span></span></span><span><span>对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行过滤，只显示符合条件的部分，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>filter( String field, String/RegExp value, [Boolean anyMatch],&nbsp;<br />[Boolean caseSensitive] ) : void</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>filter()</span></span></span><span><span>函数的用法与之前谈到的</span></span><span class="50"><span lang="EN-US"><span>find()</span></span></span><span><span>相似，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.filter('name', 'boy');</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>对应的</span></span><span class="50"><span lang="EN-US"><span>filterBy()</span></span></span><span><span>与</span></span><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>类似，也可以在自定义的函数中实现各种复杂判断，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.filterBy(function(record) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>return record.get('name') == 'girl' &amp;&amp; record.get('sex') == 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果想取消过滤并显示所有数据，那么可以调用</span></span><span class="50"><span lang="EN-US"><span>clearFilter()</span></span></span><span><span>函数，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>store.clearFilter</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果想知道</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>上是否设置了过滤器，可以通过</span></span><span class="50"><span lang="EN-US"><span>isFiltered()</span></span></span><span><span>函数进行判断。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085922"></a><a name="_Toc205277873"></a><span><span><span><span lang="EN-US"><span>10.4.6</span></span></span></span><span><span><span>　</span></span></span><span><span><span>其他功能</span></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>除了上面提到的数据获取、排序、更新、显示等功能外，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>还提供了其他一些功能函数。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>collect( String dataIndex, [Boolean allowNull], [Boolean bypassFilter] ) : Array</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>collect</span></span></span><span><span>函数获得指定的</span></span><span class="50"><span lang="EN-US"><span>dataIndex</span></span></span><span><span>对应的那一列的数据，当</span></span><span class="50"><span lang="EN-US"><span>allowNull</span></span></span><span><span>参数为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，返回的结果中可能会包含</span></span><span class="50"><span lang="EN-US"><span>null</span></span></span><span class="50"><span><span>、</span></span></span><span class="50"><span lang="EN-US"><span>undefined</span></span></span><span><span>或空字符串，否则</span></span><span class="50"><span lang="EN-US"><span>collect</span></span></span><span><span>函数会自动将这些空数据过滤掉。当</span></span><span class="50"><span lang="EN-US"><span>bypassFilter</span></span></span><span><span>参数为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，</span></span><span class="50"><span lang="EN-US"><span>collect</span></span></span><span><span>的结果不会受查询条件的影响，无论查询条件是什么都会忽略掉，返回的信息是所有的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.collect('name'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这样会获得所有</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>列的值，示例中返回的是包含了</span></span><span class="50"><span lang="EN-US"><span>'boy'</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>'girl'</span></span></span><span><span>的数组。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span class="50"><span lang="EN-US">getTotalCount</span></span><span lang="EN-US">()</span></span><span><span>用于在翻页时获得后台传递过来的数据总数。如果没有设置翻页，</span></span><span><span class="50"><span lang="EN-US">get- TotalCount</span></span><span lang="EN-US">()</span></span><span><span>的结果与</span></span><span><span class="50"><span lang="EN-US">getCount</span></span><span lang="EN-US">()</span></span><span><span>相同，都是返回当前的数据总数，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>alert(store.getTotalCount</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>indexOf(Ext.data.Record record)</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>indexOfId(String id)</span></span></span><span><span>函数根据</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>或</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>获得</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>对应的行号，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.indexOf(store.getAt(1)));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.indexOfId(1001));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>loadData(object data, [Boolean append])</span></span></span><span><span>从本地</span><span lang="EN-US"><span>JavaScript</span></span><span>变量中读取数据，</span></span><span class="50"><span lang="EN-US"><span>append</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，将读取的数据附加到原数据后，否则执行整体更新，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.loadData(data, true);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Sum(String property, Number start, Number end):Number</span></span></span><span><span>用于计算某一个列从</span><span lang="EN-US"><span>start</span></span><span>到</span><span lang="EN-US"><span>end</span></span><span>的总和，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.sum('sex'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果省略参数</span></span><span class="50"><span lang="EN-US"><span>start</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>end</span></span></span><span><span>，就计算全部数据的总和。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>还提供了一系列事件（见表</span><span lang="EN-US"><span>10-1</span></span><span>），让我们可以为对应操作设定操作函数。</span><span lang="EN-US"></span></span></p>
<p align="center" class="MsoNormal"><span>表</span><span lang="EN-US">10-1</span><span>　</span><strong><span lang="EN-US">store</span></strong><span>提供的事件</span><span lang="EN-US"></span></p>
<div>
<table width="556" cellpadding="0" cellspacing="0" border="1" class="MsoNormalTable">
<tbody>
<tr>
<td valign="top" width="115">
<p align="center" class="MsoNormal"><span>事件名</span><span lang="EN-US"></span></p>
</td>
<td valign="top" width="453">
<p align="center" class="MsoNormal"><span>参　　数</span><span lang="EN-US"></span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">add</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Ext.data.Record[] records, Number index )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">beforelaod</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Object options )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">clear</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">datachanged</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">load</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Ext.data.Record[] records, Object options )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">loadexception</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">()</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">metachange</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Object meta. )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">remove</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Ext.data.Record record, Number index )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">update</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Ext.data.Record record, String operation )</span></p>
</td>
</tr>
</tbody>
</table>
</div>
<p class="MsoNormal"><span><span>至此，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>等组件已经讲解完毕，下面我们主要讨论一下常用的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>组件。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085923"></a><a name="_Toc205277874"><span><span lang="EN-US"><span>10.5</span></span></span></a><span><span><span><span>　常用</span></span></span><span><span><strong><span lang="EN-US">proxy</span></strong></span></span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085924"></a><a name="_Toc205277875"></a><span><span><span><span><span>10.5.1</span></span></span></span><span><span><span>　</span></span></span><span><span><strong><span>MemoryProxy</span></strong></span></span><span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>MemoryProxy</span></span></span><span><span>只能从</span><span lang="EN-US"><span>JavaScript</span></span><span>对象获得数据，可以直接把数组，或</span><span lang="EN-US"><span>JSON</span></span><span>和</span><span lang="EN-US"><span>XML</span></span><span>格式的数据交给它处理，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;proxy =&nbsp;<strong>new</strong>&nbsp;Ext.data.MemoryProxy([</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>[<strong>'id1'</strong>,<strong>'name1'</strong>,<strong>'descn1'</strong>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>[<strong>'id2'</strong>,<strong>'name2'</strong>,<strong>'descn2'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>]);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="111"><a name="_Toc216085925"></a><a name="_Toc205277876"></a><a name="ext-ch-08-04-01-02"></a><span><span><span><span>10.5.2</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>HttpProxy</span></strong></span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>使用</span><span lang="EN-US"><span>HTTP</span></span><span>协议，通过</span><span lang="EN-US"><span>Ajax</span></span><span>去后台取数据，构造它时需要设置</span></span><span class="50"><span lang="EN-US"><span>url:'xxx.jsp'</span></span></span><span><span>参数。这里的</span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>可以替换成任何一个合法的网址，这样</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>才知道去哪里获取数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;proxy =&nbsp;<strong>new</strong>&nbsp;Ext.data.HttpProxy({url:<strong>'xxx.jsp'</strong>});<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>后台需要返回</span><span lang="EN-US"><span>EXT</span></span><span>所需要的</span><span lang="EN-US"><span>JSON</span></span><span>格式的数据，下面的内容就是后台使用</span><span lang="EN-US"><span>JSP</span></span><span>的一个范例，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>response.setContentType(<strong>"application/x-json"</strong>);</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>Writer out = response.getWriter</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>out.print(<strong>"["</strong>&nbsp;+</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"['id1','name1','descn1']"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"['id2','name2','descn2']"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"]"</strong>);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>请注意，这里的</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>不支持跨域，它只能从同一域中获得数据。如果想跨域，请参考下面的</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085926"></a><a name="_Toc205277877"></a><a name="ext-ch-08-04-01-03"></a><span><span><span><span>10.5.3</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>ScriptTagProxy</span></strong></span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>的用法几乎和</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>一样，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;proxy =&nbsp;<strong>new</strong>&nbsp;Ext.data.ScriptTagProxy({url:<strong>'xxx.jsp'</strong>});<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>从这里也看不出来它是如何支持跨域的，我们还需要在后台进行相应的处理，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>String cb = request.getParameter(<strong>"callback"</strong>);</span></span></p>
<p class="a1"><span lang="EN-US"><span>response.setContentType(<strong>"text/javascript"</strong>);</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>Writer out = response.getWriter</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>out.write(cb +&nbsp;<strong>"("</strong>);</span></span></p>
<p class="a1"><span lang="EN-US"><span>out.print(<strong>"["</strong>&nbsp;+</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"['id1','name1','descn1']"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"['id2','name2','descn2']"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"]"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>out.write(<strong>");"</strong>);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>其中的关键就在于从请求中获得的</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>参数，这个参数叫做回调函数。</span></span><span class="50"><span lang="EN-US"><span>ScriptTag- Proxy</span></span></span><span><span>会在当前的</span><span lang="EN-US"><span>HTML</span></span><span>页面里添加一个</span></span><span class="50"><span lang="EN-US"><span>&lt;script type="text/javascript"src="xxx.jsp"&gt; &lt;/script&gt;</span></span></span><span><span>标签，然后把后台返回的内容添加到这个标签中，这样就可以解决跨域访问数据的问题。为了让后台返回的内容可以在动态生成的标签中运行，</span><span lang="EN-US"><span>EXT</span></span><span>会生成一个名为</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>的回调函数，并把回调函数的名称传递给后台，由后台生成</span></span><span class="50"><span lang="EN-US"><span>callback(data)</span></span></span><span><span>形式的响应内容，然后返回给前台自动运行。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>虽然上述处理过程比较难理解，但是我们只需要了解</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>的用法就足够了。如果还想进一步了解</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>的运行过程，可以使用</span></span><span class="50"><span lang="EN-US"><span>Firebug</span></span></span><span><span>查看动态生成的</span></span><span class="50"><span lang="EN-US"><span>HTML</span></span></span><span><span>以及响应的</span><span lang="EN-US"><span>JSON</span></span><span>内容。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>最后我们来分析一下</span><span lang="EN-US"><span>EXT</span></span><span>的</span><span lang="EN-US"><span>API</span></span><span>文档中提供的示例，这段后台代码会自动判断请求的类型，返回支持</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>或</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>的数据，如代码清单</span><span lang="EN-US"><span>10-2</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-2</span></span><span>　在后台同时支持</span></span></span><span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>和</span></span><span><span class="50"><span lang="EN-US">ScriptTagProxy</span></span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">boolean</span></strong><span lang="EN-US">&nbsp;scriptTag = false;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>String cb = request.getParameter(<strong>"callback"</strong>);</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">if</span></strong><span lang="EN-US">&nbsp;(cb != null) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>scriptTag = true;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>response.setContentType(<strong>"text/javascript"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}&nbsp;<strong>else</strong>&nbsp;{</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>response.setContentType(<strong>"application/x-json"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>Writer out = response.getWriter</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">if</span></strong><span lang="EN-US">&nbsp;(scriptTag) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>out.write(cb +&nbsp;<strong>"("</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>out.print(dataBlock.toJsonString</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">if</span></strong><span lang="EN-US">&nbsp;(scriptTag) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>out.write(<strong>");"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>代码中通过判断请求中是否包含</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>参数来决定返回何种数据类型。如果包含，就返回</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>需要的数据；否则，就当作</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>处理。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085927"></a><a name="_Toc205277878"></a><a name="ext-ch-08-04-02"></a><a name="ext-ch-08-04-02-01"></a><span><span><span><span lang="EN-US"><span>10.6</span></span></span></span><span><span><span>　常用</span></span></span><span><span><strong><span lang="EN-US">Reader</span></strong></span></span></span></p>
<p class="111"><a name="_Toc216085928"></a><a name="_Toc205277879"></a><span><span><span><span>10.6.1</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>A</span></strong></span></span><span><span><strong><span>rrayReader</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>从</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>中读取的数据需要进行解析，这些数据转换成</span></span><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>数组后才能提供给</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Store</span></span></span><span><span>使用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>ArrayReader</span></span></span><span><span>的作用是从二维数组里依次读取数据，然后生成对应的</span></span><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>。默认情况下是按列顺序读取数组中的数据，不过你也可以考虑用</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>指定</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>与原始数组对应的列号。</span></span><span class="50"><span lang="EN-US"><span>ArrayReader</span></span></span><span><span>的用法很简单，但缺点是不支持分页。使用二维数组的方式如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;data = [</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>[<strong>'id1'</strong>,<strong>'name1'</strong>,<strong>'descn1'</strong>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>[<strong>'id2'</strong>,<strong>'name2'</strong>,<strong>'descn2'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>];</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>对应的</span></span><span class="50"><span lang="EN-US"><span>ArrayReader</span></span></span><span><span>如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.ArrayReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:1</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>},[</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'name'</strong>,mapping:1},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'descn'</strong>,mapping:2},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'id'</strong>,mapping:0},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>我们演示的是字段顺序不一致的情况，如果字段顺序和列顺序一致，就不用额外配置</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085929"></a><a name="_Toc205277880"></a><a name="ext-ch-08-04-02-02"></a><span><span><span><span>10.6.2</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>JsonReader</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>在</span><span lang="EN-US"><span>JavaScript</span></span><span>中，</span><span lang="EN-US"><span>JSON</span></span><span>是一种非常重要的数据格式，</span></span><span class="50"><span lang="EN-US"><span>key:value</span></span></span><span><span>的形式比</span><span lang="EN-US"><span>XML</span></span><span>那种复杂的标签结构更容易理解，代码量也更小，很多人倾向于使用它作为</span><span lang="EN-US"><span>EXT</span></span><span>的数据交换格式。为</span></span><span class="50"><span lang="EN-US"><span>Json- Reader</span></span></span><span><span>准备的</span><span lang="EN-US"><span>JSON</span></span><span>数据如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;data = {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:0,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty:2,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>successProperty:<strong>true</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:[</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{id:<strong>'id1'</strong>,name:<strong>'name1'</strong>,descn:<strong>'descn1'</strong>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{id:<strong>'id2'</strong>,name:<strong>'name2'</strong>,descn:<strong>'descn2'</strong>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>};</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>与数组相比，</span><span lang="EN-US"><span>JSON</span></span><span>的最大优点就是支持分页，我们可以使用</span></span><span class="50"><span lang="EN-US"><span>totalProperty</span></span></span><span><span>参数表示数据的总量。</span></span><span class="50"><span lang="EN-US"><span>successProperty</span></span></span><span><span>参数是可选的，可以用它判断当前请求是否执行成功，进而判断是否进行数据加载。在不希望</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>处理响应数据时，可以把</span></span><span class="50"><span lang="EN-US"><span>successProperty</span></span></span><span><span>设置成</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>现在来讨论一下</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>，看看它是如何与上面的</span><span lang="EN-US"><span>JSON</span></span><span>数据对应的，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.JsonReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>successProperty:&nbsp;<strong>"successproperty"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty:&nbsp;<strong>"totalProperty"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:&nbsp;<strong>"root"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:&nbsp;<strong>"id"</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}, [</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'id'</strong>,mapping:<strong>'id'</strong>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'name'</strong>,mapping:<strong>'name'</strong>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'descn'</strong>,mapping:<strong>'descn'</strong>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>上例中的对应方式不够简洁，因为</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>部分的内容是相同的，其实这里的</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>可以省略，默认会用</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>参数从</span><span lang="EN-US"><span>JSON</span></span><span>中获得对应的数据。如果不想与</span><span lang="EN-US"><span>JSON</span></span><span>里的名字一样，也可以使用</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>修改。不过，</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>在这里还有其他用途，如代码清单</span><span lang="EN-US"><span>10-3</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-3</span></span><span>　为</span></span></span><span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>设置</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>进行数据映射</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;data = {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:0,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty:2,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>successProperty:<strong>true</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:[</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{id:<strong>'id1'</strong>,name:<strong>'name1'</strong>,descn:<strong>'descn1'</strong>,person:{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>id:1,name:<strong>'man'</strong>,sex:<strong>'male'</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>}},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{id:<strong>'id2'</strong>,name:<strong>'name2'</strong>,descn:<strong>'descn2'</strong>,person:{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>id:2,name:<strong>'woman'</strong>,sex:<strong>'female'</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>}}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>};</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.JsonReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>successProperty:&nbsp;<strong>"successproperty"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty:&nbsp;<strong>"totalProperty"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:&nbsp;<strong>"root"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:&nbsp;<strong>"id"</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}, [</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>'id'</strong>,<strong>'name'</strong>,<strong>'descn'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'person_name'</strong>,mapping:<strong>'person.name'</strong>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'person_sex'</strong>,mapping:<strong>'person.sex'</strong>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在上面的代码中，我们使用</span><span lang="EN-US"><span>JSON</span></span><span>支持更复杂的嵌套结构，其中的</span></span><span class="50"><span lang="EN-US"><span>person</span></span></span><span><span>对象自身就拥有</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>、</span><span><span>&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>sex</span></span></span><span><span>等属性。在</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>中可以用</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>把这些嵌套的内部属性映射出来，赋予对应的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，而其他字段都不变。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085930"></a><a name="_Toc205277881"></a><a name="ext-ch-08-04-02-03"></a><span><span><span><span>10.6.3</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>XmlReader</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>XML</span></span><span>是非常通用的数据传输格式，</span></span><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>使用的</span><span lang="EN-US"><span>XML</span></span><span>格式的数据如代码清单</span><span lang="EN-US"><span>10-4</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-4</span></span><span>　</span></span></span><span><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>使用的</span><span lang="EN-US"><span>XML</span></span></span><span><span>格式的数据</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><strong><span lang="EN-US"><span><span>&lt;?xml version="1.0" encoding="utf-8"?&gt;</span></span></span></strong></p>
<p class="a1"><strong><span lang="EN-US"><span><span>&lt;dataset&gt;</span></span></span></strong></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>id</strong>&gt;1&lt;/<strong>id</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>totalRecords</strong>&gt;2&lt;/<strong>totalRecords</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>success</strong>&gt;true&lt;/<strong>success</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>record</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>id</strong>&gt;1&lt;/<strong>id</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>name</strong>&gt;name1&lt;/<strong>name</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>descn</strong>&gt;descn1&lt;/<strong>descn</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;/<strong>record</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>record</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>id</strong>&gt;2&lt;/<strong>id</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>name</strong>&gt;name2&lt;/<strong>name</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>descn</strong>&gt;descn2&lt;/<strong>descn</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;/<strong>record</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&lt;/<strong>dataset</strong>&gt;</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这里一定要用</span></span><span class="50"><span lang="EN-US"><span>dataset</span></span></span><span><span>作为</span><span lang="EN-US"><span>XML</span></span><span>根元素。再让我们看一下如何对</span></span><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>进行配置，从而读取上面示例中的</span><span lang="EN-US"><span>XML</span></span><span>数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.XmlReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span>totalRecords:&nbsp;<strong>'totalRecords'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span>success:&nbsp;<strong>'success'</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span>record:&nbsp;<strong>'record'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span>id:&nbsp;<strong>"id"</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}, [<strong>'id'</strong>,<strong>'name'</strong>,<strong>'descn'</strong>]);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>使用的参数与之前介绍的</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>有些不同，我们可以看到这里用到了</span></span><span class="50"><span lang="EN-US"><span>totalRecords</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>两个参数，其中</span></span><span class="50"><span lang="EN-US"><span>totalRecords</span></span></span><span><span>用来指定从</span></span><span class="50"><span lang="EN-US"><span>&rsquo;totalRecords&rsquo;</span></span></span><span><span>标签里获得后台数据总数，</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>则表示</span><span lang="EN-US"><span>XML</span></span><span>中放在</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>标签里的数据是我们需要显示的结果数据。其他两个参数</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>的含义和</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>中对应的参数相似，分别用来判断操是否成功和这次返回的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>。因为</span><span lang="EN-US"><span>XML</span></span><span>中的标签和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>里需要的名字是相同的，所以简化了配置，将</span></span><span class="50"><span lang="EN-US"><span>[{name:&rsquo;id&rsquo;},{name:&rsquo;name&rsquo;},{name:&rsquo;descn&rsquo;}]</span></span></span><span><span>直接写成了</span></span><span class="50"><span lang="EN-US"><span>[&lsquo;id&rsquo;,&rsquo;name&rsquo;,&rsquo;descn&rsquo;]</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>因为</span></span><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>不能将</span><span lang="EN-US"><span>JavaScript</span></span><span>中的字符串自动解析成</span><span lang="EN-US"><span>XML</span></span><span>格式的数据，因此我们需要利用其他方法进行演示。参考</span></span><span class="50"><span lang="EN-US"><span>localXHR.js</span></span></span><span><span>中构造</span><span lang="EN-US"><span>XML</span></span><span>的方式，我们有了下面的解决方案，如代码清单</span><span lang="EN-US"><span>10-5</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-5</span></span><span>　通过本地字符串构造</span><span lang="EN-US"><span>XML</span></span><span>对象</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;data = "<strong>&lt;?xml version='1.0' encoding='utf-8'?&gt;</strong>" +</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>"&lt;<strong>dataset</strong>&gt;" +</span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US"><span>&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>"&lt;id&gt;1&lt;/id&gt;"&nbsp;</span></strong><span lang="EN-US">+<strong></strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;totalRecords&gt;2&lt;/totalRecords&gt;"&nbsp;</strong>+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;success&gt;true&lt;/success&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;record&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;id&gt;1&lt;/id&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;name&gt;name1&lt;/name&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;descn&gt;descn1&lt;/descn&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;/record&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;record&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;id&gt;2&lt;/id&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>"<strong>&lt;name&gt;name2&lt;/name&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;descn&gt;descn2&lt;/descn&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;/record&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;/dataset&gt;"</strong>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;xdoc;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">if</span></strong><span lang="EN-US">(<strong>typeof</strong>(DOMParser) ==&nbsp;<strong>'undefined'</strong>){</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>xdoc =&nbsp;<strong>new</strong>&nbsp;ActiveXObject(<strong>"Microsoft.XMLDOM"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>xdoc.async="<strong>false</strong>";</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>xdoc.loadXML(data);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}<strong>else</strong>{</span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>var</strong>&nbsp;domParser =&nbsp;<strong>new</strong>&nbsp;DOMParser</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>xdoc = domParser.parseFromString(data,&nbsp;<strong>'application/xml'</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>domParser =&nbsp;<strong>null</strong>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;proxy =&nbsp;<strong>new</strong>&nbsp;Ext.data.MemoryProxy(xdoc);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.XmlReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalRecords:&nbsp;<strong>'totalRecords'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>success:&nbsp;<strong>'success'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>record:&nbsp;<strong>'record'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id: "<strong>id</strong>"</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}, [<strong>'id','name','descn'</strong>]);</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;ds =&nbsp;<strong>new</strong>&nbsp;Ext.data.Store({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy: proxy,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: reader</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="11"><a name="_Toc216085931"></a><a name="_Toc205277882"></a><a name="ext-ch-08-04-03"></a><span><span><span><span lang="EN-US"><span>10.7</span></span></span></span><span><span><span>　高级</span></span></span><span><span><strong><span lang="EN-US">store</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>实际开发时，并不需要每次都对</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>这三个对象进行配置，</span><span lang="EN-US"><span>EXT</span></span><span>为我们提供了几种可选择的整合方案。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>SimpleStore</span></span></span><span lang="EN-US"><span>&nbsp;=&nbsp;</span></span><span class="50"><span lang="EN-US"><span>Store</span></span></span><span lang="EN-US"><span>&nbsp;+&nbsp;</span></span><span class="50"><span lang="EN-US"><span>MemoryProxy</span></span></span><span lang="EN-US"><span>&nbsp;+&nbsp;</span></span><span><span class="50"><span lang="EN-US">ArrayReader</span></span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><strong>var</strong>&nbsp;ds = Ext.data.SimpleStore({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>data: [</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span>&nbsp;&nbsp;</span>[<strong>'id1'</strong>,<strong>'name1'</strong>,<strong>'descn1'</strong>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span>&nbsp;&nbsp;</span>[<strong>'id2'</strong>,<strong>'name2'</strong>,<strong>'descn2'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>fields: [<strong>'id'</strong>,<strong>'name'</strong>,<strong>'descn'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>SimpleStore</span></span></span><span><span>是专为简化读取本地数组而设计的，设置上</span></span><span class="50"><span lang="EN-US"><span>MemoryProxy</span></span></span><span><span>需要的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>ArrayReader</span></span></span><span><span>需要的</span></span><span class="50"><span lang="EN-US"><span>fields</span></span></span><span><span>就可以使用了。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>JsonStore</span></span></span><span lang="EN-US"><span>&nbsp;=&nbsp;</span></span><span class="50"><span lang="EN-US"><span>Store</span></span></span><span lang="EN-US"><span>&nbsp;+&nbsp;</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span lang="EN-US"><span>&nbsp;+&nbsp;</span></span><span><span class="50"><span lang="EN-US">JsonReader</span></span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><strong>var</strong>&nbsp;ds = Ext.data.JsonStore({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>url:&nbsp;<strong>'xxx.jsp'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:&nbsp;<strong>'root'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>fields: [<strong>'id'</strong>,<strong>'name'</strong>,<strong>'descn'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>JsonStore</span></span></span><span><span>将</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>整合在一起，提供了一种从后台读取</span><span lang="EN-US"><span>JSON</span></span><span>信息的简便方法，大多数情况下可以考虑直接使用它从后台读取数据。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.GroupingStore</span></span></span><span><span>对数据进行分组</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.GroupingStore</span></span></span><span><span>继承自</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>，它的主要功能是可以对内部的数据进行分组，我们可以在创建</span></span><span class="50"><span lang="EN-US"><span>Ext.data.GroupingStore</span></span></span><span><span>时指定根据某个字段进行分组，也可以在创建实例后调用它的</span></span><span class="50"><span lang="EN-US"><span>groupBy()</span></span></span><span><span>函数对内部数据重新分组，如下面的代码所示。</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>var ds = new Ext.data.GroupingStore({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>data: [</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id1','name1','female','descn1'],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id2','name2','male','descn2'],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id3','name3','female','descn3'],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id4','name4','male','descn4'],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id5','name5','female','descn5']</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ArrayReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>fields: ['id','name','sex','descn']</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>}),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>groupField: 'sex',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>groupOnSort: true</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>上例中，我们使用</span></span><span class="50"><span lang="EN-US"><span>groupField</span></span></span><span><span class="50"><span>作为</span></span><span>参数，为</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Grouping</span></span></span><span><span>设置了分组字段，另外还设置了</span></span><span class="50"><span lang="EN-US"><span>groupOnSort</span></span></span><span><span>参数，这个参数可以保证只有在进行分组时才会对</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Grouping- Store</span></span></span><span><span>内部的数据进行排序。如果采用默认值，就需要手工指定</span></span><span class="50"><span lang="EN-US"><span>sortInfo</span></span></span><span><span>参数，从而指定默认的排序字段和排序方式，否则就会出现错误。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>创建</span></span><span class="50"><span lang="EN-US"><span>Ext.data.GroupingStore</span></span></span><span><span>的实例之后，我们还可以调用</span></span><span class="50"><span lang="EN-US"><span>groupBy()</span></span></span><span><span>函数重新对数据进行分组。因为我们设置了</span></span><span class="50"><span lang="EN-US"><span>groupOnSort:true</span></span></span><span><span>，所以在重新分组时，</span><span lang="EN-US"><span>EXT</span></span><span>会使用分组的字段对内部数据进行排序。如果不希望对数据进行分组，也可以调用</span></span><span class="50"><span lang="EN-US"><span>clearGrouping()</span></span></span><span><span>函数清除分组信息，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>ds.groupBy('id');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>ds.clearGrouping();<span></span></span></span></span></p>
<p class="11"><a name="_Toc216085932"></a><a name="_Toc205277883"></a><a name="ext-ch-08-05"></a><a name="ext-ch-08-06"></a><span><span><span><span lang="EN-US"><span>10.8</span></span></span></span><span><span><span>　</span><span lang="EN-US"><span>EXT</span></span></span></span><span><span><span>中的</span><span lang="EN-US"><span>Ajax</span></span></span></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>EXT</span></span><span>与后台交换数据时，很大程度上依赖于底层实现的</span><span lang="EN-US"><span>Ajax</span></span><span>。所谓底层实现，就是说很可能就是我们之前提到的</span><span><span>&nbsp;<span lang="EN-US">Prototype</span></span></span><span>、</span><span lang="EN-US"><span>jQuery</span></span><span>或</span><span lang="EN-US"><span>YUI</span></span><span>中提供的</span><span lang="EN-US"><span>Ajax</span></span><span>功能。为了统一接口，</span><span lang="EN-US"><span>EXT</span></span><span>在它们的基础上进行了封装，让我们可以用同一种写法&ldquo;游走&rdquo;于各种不同的底层实现之间。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085933"></a><span><span><span>10.8.1</span></span><span><span>　</span></span><span><span>最容易看到的</span></span><span><strong><span>Ext.Ajax</span></strong></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>的基本用法如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>Ext.Ajax.request({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>url: '07-01.txt',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>success: function(response) {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('</span></span><span>成功</span><span lang="EN-US"><span>', response.responseText);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>failure: function(response) {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('</span></span><span>失败</span><span lang="EN-US"><span>', response.responseText);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>params: { name: 'value' }</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这里调用的是</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>request</span></span></span><span><span>函数，它的参数是一个</span><span lang="EN-US"><span>JSON</span></span><span>对象，具体如下所示。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>参数表示将要访问的后台网址。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>参数表示响应成功后的回调函数。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>上例中我们直接从</span></span><span class="50"><span lang="EN-US"><span>response</span></span></span><span><span>取得返回的字符串，用</span></span><span class="50"><span lang="EN-US"><span>Ext.Msg.alert</span></span></span><span><span>显示出来。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>failure</span></span></span><span><span>参数表示响应失败后的回调函数。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>注意，这里的响应失败并不是指数据库操作之类的业务性失败，而是指</span><span lang="EN-US"><span>HTTP</span></span><span>返回</span><span lang="EN-US"><span>404</span></span><span>或</span><span lang="EN-US"><span>500</span></span><span>错误，请不要把</span><span lang="EN-US"><span>HTTP</span></span><span>响应错误与业务错误混淆在一起。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>参数表示请求时发送到后台的参数，既可以使用</span><span lang="EN-US"><span>JSON</span></span><span>对象，也可以直接使用</span></span><span class="50"><span lang="EN-US"><span>"name=value"</span></span></span><span><span>形式的字符串。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>上面的示例可以在</span><span lang="EN-US"><span>10.store/07-01.html</span></span><span>中找到。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>直接继承自</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>，不同的是，它是一个单例，不需要用</span></span><span class="50"><span lang="EN-US"><span>new</span></span></span><span><span>创建实例，可以直接使用。在使用</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>前需要先创建实例，因为</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Connection</span></span></span><span><span>是为了给</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>中的各种</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>提供</span></span><span class="50"><span lang="EN-US"><span>Ajax</span></span></span><span><span>功能，分配不同的实例更有利于分别管理。</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>为用户提供了一个简易的调用接口，实际使用时，可以根据自己的需要进行选择。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085934"></a><span><span><span>10.8.2</span></span><span><span>　</span></span><span><span>Ext.lib.Ajax</span></span><span><span>是更底层的封装</span></span></span></p>
<p class="MsoNormal"><span><span>其实</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>的内部功能实现都是依靠</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>来完成的，在</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>下面就是各种底层库的</span><span lang="EN-US"><span>Ajax</span></span><span>了。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果使用</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>实现以上的功能，就需要写成下面的形式，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>Ext.lib.Ajax.request(</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>'POST',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>'07-01txt',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{success: function(response){</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('</span></span><span>成功</span><span lang="EN-US"><span>', response.responseText);</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},failure: function</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>{</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('</span></span><span>失败</span><span lang="EN-US"><span>', response.responseText);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>'data=' + encodeURIComponent(Ext.encode({name:'value'}))</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>我们可以看到，使用</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>时需要传递</span><span lang="EN-US"><span>4</span></span><span>个参数，分别为</span></span><span class="50"><span lang="EN-US"><span>method</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>。它们的含义与</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>中的参数都是一一对应的，唯一没有提到过的</span></span><span class="50"><span lang="EN-US"><span>method</span></span></span><span><span>参数表示请求</span><span lang="EN-US"><span>HTTP</span></span><span>的方法，它也可以在</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>中使用</span></span><span class="50"><span lang="EN-US"><span>method:'POST'</span></span></span><span><span>的方式设置。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>相对于</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>来说，</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>有如下几个缺点。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>参数的顺序被定死了，第一个参数是</span></span><span class="50"><span lang="EN-US"><span>method</span></span></span><span><span>，第二个参数是</span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>，第三个参数是回调函数</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>，第四个参数是</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>。这样既不容易记忆，也无法省略其中某个不需要的参数。</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>中用</span><span lang="EN-US"><span>JSON</span></span><span>对象来定义参数，使用起来更灵活。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>在</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>部分，</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>必须使用字符串形式，显得有些笨重。</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>则可以在</span><span lang="EN-US"><span>JSON</span></span><span>对象和字符串之间随意选择，非常灵活。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>比与</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>相比，</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>的唯一优势就是它可以在</span><span lang="EN-US"><span>EXT 1.x</span></span><span>中使用。如果你使用的是</span><span lang="EN-US"><span>EXT 2.0</span></span><span>或更高的版本，那么就放心大胆地使用</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>吧，它会带给你更多的惊喜。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>该示例在</span><span lang="EN-US"><span>10.store/07-02.html</span></span><span>中。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085935"></a><a name="_Toc205277884"><span><span lang="EN-US"><span>10.9</span></span></span></a><span><span><span><span>　关于</span></span></span><span><span><strong><span lang="EN-US">scope</span></strong></span></span><span><span><span>和</span></span></span><span><span><strong><span lang="EN-US">createDelegate()</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>关于</span><span lang="EN-US"><span>JavaScript</span></span><span>中</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>的使用，这是一个由来已久的问题了。我们这里就不介绍它的发展历史了，只结合具体的例子，告诉大家可能会遇到什么问题，在遇到这些问题时</span><span lang="EN-US"><span>EXT</span></span><span>是如何解决的。在使用</span><span lang="EN-US"><span>EXT</span></span><span>时，最常碰到的就是使用</span><span lang="EN-US"><span>Ajax</span></span><span>回调函数时出现的问题，如下面的代码所示。</span><span lang="EN-US"><span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span lang="EN-US">&lt;<strong><em>input</em></strong>&nbsp;<span class="hl-attribute"><span>type</span></span>=<span class="hl-value"><span>"text"</span></span>&nbsp;<span class="hl-attribute"><span>name</span></span>=<span class="hl-value"><span>"text"</span></span>&nbsp;<span class="hl-attribute"><span>id</span></span>=<span class="hl-value"><span>"text"</span></span>&gt;</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&lt;input type="button" name="button" id="button" value="button"&gt;</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>现在的</span><span lang="EN-US"><span>HTML&nbsp;</span></span><span>页面中有一个</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>输入框和一个按钮。我们希望按下这个按钮之后，能用</span><span lang="EN-US"><span>Ajax</span></span><span>去后台读取数据，然后把后台响应的数据放到</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>中，实现过程如代码清单</span><span><span lang="EN-US">1</span><span lang="EN-GB">0</span><span lang="EN-US">-6</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-6</span></span><span>　</span><span lang="EN-US"><span>Ajax</span></span></span><span><span>中使用回调函数</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><span><strong><span lang="EN-US">functio</span>n</strong></span><span lang="EN-US">&nbsp;doSuccess(response) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>text.dom.value = response.responseText;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>Ext.onReady(function</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>{</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.get('button').on('click', function</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>var text = Ext.get('text');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.lib.Ajax.request(</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>'POST',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>'08.txt',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{success:doSuccess},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>'param=' + encodeURIComponent(text.dom.value)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>});</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在上面的代码中，</span><span lang="EN-US"><span>Ajax</span></span><span>已经用</span></span><span class="50"><span lang="EN-US"><span>Ext.get('text')</span></span></span><span><span>获得了</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>，以为后面可以直接使用，没想到回调函数</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>不会按照你写的顺序去执行。当然，也不会像你所想的那样使用局部变量</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>。实际上，如果什么都不做，仅仅只是使用回</span><span>调函数，你不得不再次使用</span></span><span class="50"><span lang="EN-US"><span>Ext.get('text')</span></span></span><span><span>重新获得元素，否则浏览器就会报</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>未定义的错误。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>在此使用</span></span><span class="50"><span lang="EN-US"><span>Ext.get('text')</span></span></span><span><span>重新获取对象还比较简单，在有些情况下不容易获得需要处理的对象，我们要在发送</span><span lang="EN-US"><span>Ajax</span></span><span>请求之前获取回调函数中需要操作的对象，有两种方法可供选择：</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>createDelegate</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>为</span><span lang="EN-US"><span>Ajax</span></span><span>设置</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>。</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>function</strong></span></span>&nbsp;doSuccess(response) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>this</strong></span></span>.dom.value = response.responseText;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>Ext.lib.Ajax.request(</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'POST'</strong></span></span>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'08.txt'</strong></span></span>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{success:doSuccess,scope:text},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'param='</strong></span></span>&nbsp;+ encodeURIComponent(text.dom.value)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在</span><span lang="EN-US"><span>Ajax</span></span><span>的</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>参数部分添加一个</span></span><span class="50"><span lang="EN-US"><span>scope:text</span></span></span><span><span>，把回调函数的</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>指向</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>，它的作用就是把</span></span><span class="50"><span lang="EN-US"><span>doSuccess</span></span></span><span><span>函数里的</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>指向</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>对象。然后再把</span></span><span class="50"><span lang="EN-US"><span>doSuccess</span></span></span><span><span>里改成</span></span><span class="50"><span lang="EN-US"><span>this.dom. value</span></span></span><span><span>，这样就可以了。如果想再次在回调函数里用某个对象，必须配上</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>，这样就能在回调函数中使用</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>对它进行操作了。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>添加</span></span><span class="50"><span lang="EN-US"><span>createDelegate()</span></span></span><span><span>。</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>function</strong></span></span>&nbsp;doSuccess(response) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>this</strong></span></span>.dom.value = response.responseText;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>&nbsp;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>Ext.lib.Ajax.request(</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'POST'</strong></span></span>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'08.txt'</strong></span></span>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{success:doSuccess.createDelegate(text)},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'param='</strong></span></span>&nbsp;+ encodeURIComponent(text.dom.value)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>createDelegate</span></span></span><span><span>只能在</span></span><span class="50"><span lang="EN-US"><span>function</span></span></span><span><span>上调用，它把函数里的</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>强行指向我们需要的对象，然后我们就可以在回调函数</span></span><span class="50"><span lang="EN-US"><span>doSuccess</span></span></span><span><span>里直接通过</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>来引用</span></span><span class="50"><span lang="EN-US"><span>createDelegate()</span></span></span><span><span>中指定的这个对象了。它可以作为解决</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>问题的一个备选方案。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果让我选择，我会尽量选择</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>，因为</span></span><span class="50"><span lang="EN-US"><span>createDelegate</span></span></span><span><span>是要对原来的函数进行封装，重新生成</span></span><span class="50"><span lang="EN-US"><span>function</span></span></span><span><span>对象。简单环境下，</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>就够用了，倒是</span></span><span class="50"><span lang="EN-US"><span>createDelegate</span></span></span><span><span>还有其他功能，比如修改调用参数等。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>示例在</span><span lang="EN-US"><span>10.store/08.html</span></span><span>中。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085936"></a><a name="_Toc205277885"></a><a name="ext-ch-10-01"></a><span><span><span><span lang="EN-US"><span>10.10</span></span></span></span><span><span><span>　</span><span lang="EN-US"><span>DWR</span></span></span></span><span><span><span>与</span><span lang="EN-US"><span>EXT</span></span></span></span><span><span><span>整合</span></span></span></span></p>
<p class="MsoNormal"><span><span>据不完全统计，从事</span><span lang="EN-US"><span>Ajax</span></span><span>开发的</span><span lang="EN-US"><span>Java</span></span><span>程序员有一大半都使用</span><span lang="EN-US"><span>DWR</span></span><span>。我们下面来介绍一下如何在</span><span lang="EN-US"><span>EXT</span></span><span>中使用</span><span lang="EN-US"><span>DWR</span></span><span>与后台交互。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085937"></a><a name="_Toc205277886"></a><a name="ext-ch-10-01-01"></a><span><span><span><span>10.10.1</span></span></span><span><span><span>　</span></span></span><span><span><span>在</span><span>EXT</span></span></span><span><span><span>中直接使用</span><span>DWR</span></span></span></span></p>
<p class="MsoNormal"><span><span>因为</span><span lang="EN-US"><span>DWR</span></span><span>在前台的表现形式和普通的</span><span lang="EN-US"><span>JavaScript</span></span><span>完全一样，所以我们不需要特地去做些什么，直接使用</span><span lang="EN-US"><span>EXT</span></span><span>调用</span><span lang="EN-US"><span>DWR</span></span><span>生成的</span><span lang="EN-US"><span>JavaScript</span></span><span>函数即可。以</span><span lang="EN-US"><span>Grid</span></span><span>为例，比如现在我们要显示一个通讯录的信息，后台记录的数据有：</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>sex</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>email</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>tel</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>addTime</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>descn</span></span></span><span><span>。编写对应的</span><span lang="EN-US"><span>POJO</span></span><span>，代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>public</strong></span></span><span lang="EN-US">&nbsp;<span class="hl-keyword1"><span><strong>cla</strong></span></span>ss Info {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>long id;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String name;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int sex;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String email;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String tel;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>Date addTime;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String descn;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>然后编写操作</span><span lang="EN-US"><span>POJO</span></span><span>的</span></span><span class="50"><span lang="EN-US"><span>manager</span></span></span><span><span>类，代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>public</strong></span></span><span lang="EN-US">&nbsp;<span class="hl-keyword1"><span><strong>class</strong></span></span>&nbsp;InfoManager {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>private List infoList = new ArrayList</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>public List getResult</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>&nbsp;{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>return infoList;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>代码部分有些删减，我们只保留了其中的关键部分，就这样把这两个类配置到</span><span lang="EN-US"><span>dwr.xml</span></span><span>中，让前台可以对这些类进行调用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>下面是</span><span lang="EN-US"><span>EXT</span></span><span>与</span><span lang="EN-US"><span>DWR</span></span><span>交互的关键部分，我们要对</span><span lang="EN-US"><span>JavaScript</span></span><span>部分做如下修改，如代码清单</span><span lang="EN-US"><span>10-7</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-7</span></span><span>　使用</span><span lang="EN-US"><span>EXT</span></span><span>调用</span></span><span lang="EN-US"><span><span>DWR</span></span></span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>var</strong></span></span><span lang="EN-US">&nbsp;cm =&nbsp;<span class="hl-keyword1"><span><strong>new</strong></span></span>&nbsp;Ext.grid.ColumnModel([</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>编号</span><span lang="EN-US"><span>',dataIndex:'id'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>名称</span><span lang="EN-US"><span>',dataIndex:'name'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>性别</span><span lang="EN-US"><span>',dataIndex:'sex'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>邮箱</span><span lang="EN-US"><span>',dataIndex:'email'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>电话</span><span lang="EN-US"><span>',dataIndex:'tel'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>添加时间</span><span lang="EN-US"><span>',dataIndex:'addTime'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>备注</span><span lang="EN-US"><span>',dataIndex:'descn'}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>var store = new Ext.data.JsonStore({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>fields: ["id","name","sex",'email','tel','addTime','descn']</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>//&nbsp;</span></span><span>调用</span><span lang="EN-US"><span>DWR</span></span><span>取得数据</span></span></p>
<p class="a1"><span lang="EN-US"><span>infoManager.getResult(function(data) {</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>store.loadData(data);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>var grid = new Ext.grid.GridPanel({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>renderTo: 'grid',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>store: store,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>cm: cm</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>注意，执行</span></span><span class="50"><span lang="EN-US"><span>infoManager.getResult()</span></span></span><span><span>函数时，</span><span lang="EN-US"><span>DWR</span></span><span>就会使用</span><span lang="EN-US"><span>Ajax</span></span><span>去后台取数据了，操作成功后调用我们定义的匿名回调函数。在这里我们只做一件事，那就是将返回的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>直接注入到</span></span><span class="50"><span lang="EN-US"><span>ds</span></span></span><span><span>中。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>DWR</span></span><span>返回的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>可以被</span></span><span class="50"><span lang="EN-US"><span>JsonStore</span></span></span><span><span>直接读取，我们需要设置对应的</span></span><span class="50"><span lang="EN-US"><span>fields</span></span></span><span><span>参数，以告诉</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>需要哪些属性。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>在这里，</span><span lang="EN-US"><span>EXT</span></span><span>和</span><span lang="EN-US"><span>DWR</span></span><span>两者之间没有任何关系，将它们任何一方替换掉都可以。实际上它们只是在一起运行，并没有整合。我们给出的这个示例也是说明了一种松耦合的可能性，实际操作中完全可以使用这种方式。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085938"></a><a name="_Toc205277887"></a><a name="ext-ch-10-01-02"></a><span><span><span><span>10.10.2</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>DWRProxy</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>要结合使用</span><span lang="EN-US"><span>EXT</span></span><span>和</span><span lang="EN-US"><span>DWR</span></span><span>，不需要对后台程序进行任何修改，可以直接让前后台数据进行交互。不过还要考虑很多细节，比如</span><span lang="EN-US"><span>Grid</span></span><span>分页、刷新、排序、搜索等常见的操作。</span><span lang="EN-US"><span>EXT</span></span><span>的官方网站上已经有人放上了</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>，借助它可以让</span><span lang="EN-US"><span>DWR</span></span><span>和</span><span lang="EN-US"><span>EXT</span></span><span>连接得更加紧密。不过，需要在后台添加</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>所需要的</span><span lang="EN-US"><span>Java</span></span><span>类，这可能不是最好的解决方案。但我们相信，通过对它的内在实现的讨论，我们可以有更多的选择和想象空间。</span><span lang="EN-US"></span></span></p>
<div>
<p class="055205505"><span><span class="5"><span>注意</span></span><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span><span>这个</span><span><span>DWRProxy.js</span></span><span>一定要放在</span><span><span>ext-base.js</span></span><span>和</span><span><span>ext-all.js</span></span><span>后面，否则会出错。</span><span></span></span></p>
</div>
<p class="MsoNormal"><span><span>我们现在就用</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>来实现一个分页的示例。除了准备好插件</span><span lang="EN-US"><span>DWRProxy.js</span></span><span>外，还要在后台准备一个专门用于分页的封装类。因为不仅要告诉前台显示哪些数据，还要告诉前台一共有多少条数据。现在我们来重点看一下</span></span><span class="50"><span lang="EN-US"><span>ListRange.java</span></span></span><span><span>，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>public class ListRange {</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>Object[] data;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int totalSize;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>其实</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>非常简单，只有两个属性：提供数据的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>和提供数据总量的</span></span><span class="50"><span lang="EN-US"><span>totalSize</span></span></span><span><span>。再看一下</span></span><span class="50"><span lang="EN-US"><span>InfoManager.java</span></span></span><span><span>，为了实现分页，我们专门编写了一个</span></span><span class="50"><span lang="EN-US"><span>getItems</span></span></span><span><span>方法，代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>pub</strong></span></span><span lang="EN-US">lic ListRange getItems(Map conditions) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int start = 0;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int pageSize = 10;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int pageNo = (start / pageSize) + 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>try {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>start = Integer.parseInt(conditions.get("start").toString</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>pageSize = Integer.parseInt(conditions.get("limit").toString</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>pageNo = (start / pageSize) + 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>} catch (Exception ex) {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>ex.printStackTrace</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>List list = infoList.subList(start, start + pageSize);</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>return new ListRange(list.toArray</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>, infoList.size</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>getItems()</span></span></span><span><span>的参数是</span></span><span class="50"><span lang="EN-US"><span>Map</span></span></span><span><span>，我们从中获得需要的参数，比如</span></span><span class="50"><span lang="EN-US"><span>start</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>limit</span></span></span><span><span>。不过</span><span lang="EN-US"><span>HTTP</span></span><span>里的参数都是字符串，而我们需要的是数字，所以要对类型进行相应的转换。根据</span></span><span class="50"><span lang="EN-US"><span>start</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>limit</span></span></span><span><span>两个属性从全部数据中截取一部分，放进新建的</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>中，然后把生成的</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>返回给前台，于是一切都解决了。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>重头戏要上演了，我们就要使用传说中的</span></span><span class="50"><span lang="EN-US"><span>Ext.data.DWRProxy</span></span></span><span><span>了，还有</span></span><span class="50"><span lang="EN-US"><span>Ext.data.List- RangeReader</span></span></span><span><span>。通过这两个扩展，</span><span lang="EN-US"><span>EXT</span></span><span>完全可以支持</span><span lang="EN-US"><span>DWR</span></span><span>的数据传输协议。实际上，这正是</span><span lang="EN-US"><span>EXT</span></span><span>要把数据和显示分离设计的原因，这样你只需要添加自定义的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>，不需要修改</span><span lang="EN-US"><span>EXT</span></span><span>的其他部分，就可以实现从特定途径获取数据的功能。后台还是</span><span lang="EN-US"><span>DWR</span></span><span>，所以至少在</span><span lang="EN-US"><span>Grid</span></span><span>部分，我们可以很好地使用它们的结合，主要代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>var</strong></span></span><span lang="EN-US">&nbsp;store =&nbsp;<span class="hl-keyword1"><span><strong>new</strong></span></span>&nbsp;Ext.data.Store({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy:&nbsp;<span class="hl-keyword1"><span><strong>new</strong></span></span>&nbsp;Ext.data.DWRProxy(infoManager.getItems,&nbsp;<span class="hl-keyword1"><span><strong>true</strong></span></span>),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ListRangeReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty: 'totalSize',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>root: 'data',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>id: 'id<span class="hl-string1"><span><strong>'</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}, info),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>remoteSort: true</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>与我们上面说的一样，我们修改了</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>，也修改了</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>，其他地方都不需要进行修改，</span><span lang="EN-US"><span>Grid</span></span><span>已经可以正常运行了。需要提醒的是</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>的用法，其中包括两个参数：第一个是</span></span><span class="50"><span lang="EN-US"><span>dwr- Call</span></span></span><span><span>，它把一个</span><span lang="EN-US"><span>DWR</span></span><span>函数放进去，它对应的是后台的</span></span><span class="50"><span lang="EN-US"><span>getItems</span></span></span><span><span>方法；第二个参数是</span></span><span class="50"><span lang="EN-US"><span>paging- AndSort</span></span></span><span><span>，这个参数控制</span><span lang="EN-US"><span>DWR</span></span><span>是否需要分页和排序。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>ListRangeReader</span></span></span><span><span>部分与后台的</span></span><span class="50"><span lang="EN-US"><span>ListRange.java</span></span></span><span><span>对应。</span></span><span class="50"><span lang="EN-US"><span>totalProperty</span></span></span><span><span>表示后台数据总数，我们通过它指定从</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>中读取</span></span><span class="50"><span lang="EN-US"><span>totalSize</span></span></span><span><span>属性的值来作为后台数据总数。还需要指定</span></span><span class="50"><span lang="EN-US"><span>root</span></span></span><span><span>参数，以告诉它在</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>中的数据变量的名称为</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>，随后</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>会从</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>中的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>属性中获取数据并显示到页面上。如果不想使用我们提供的</span></span><span class="50"><span lang="EN-US"><span>ListRange.java</span></span></span><span><span class="50"><span>类</span></span><span>，也可以自己创建一个类，只要把</span></span><span class="50"><span lang="EN-US"><span>totalProperty</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>两个属性与之对应即可。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085939"></a><a name="_Toc205277888"></a><a name="ext-ch-10-01-03"></a><span><span><span><span>10.10.3</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>DWRTreeLoader</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>我们现在来尝试一下让树形也支持</span><span lang="EN-US"><span>DWR</span></span><span>。有了前面的基础，整合</span><span lang="EN-US"><span>DWR</span></span><span>和</span><span lang="EN-US"><span>tree</span></span><span>就更简单了。在后台，我们需要树形节点对应的</span></span><span class="50"><span lang="EN-US"><span>TreeNode.java</span></span></span><span><span>。目前，只要</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>leaf</span></span></span><span><span>三项就可以了。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>publ</strong></span></span><span lang="EN-US">ic class TreeNode {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String id;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String text;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>boolean leaf;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>是节点的唯一标记，知道了</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>就能知道是在触发哪个节点了。</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>是显示的标题，</span></span><span class="50"><span lang="EN-US"><span>leaf</span></span></span><span><span>比较重要，它用来标记这个节点是不是叶子。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>这里还是用异步树，</span></span><span class="50"><span lang="EN-US"><span>TreeNodeManager.java</span></span></span><span><span>里的</span></span><span><span class="50"><span lang="EN-US">getTree</span></span><span lang="EN-US">()</span></span><span><span>方法将获得一个节点的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span class="50"><span>作为</span></span><span><span>参数，然后返回这个节点下的所有子节点。我们这里没有限制生成的树形的深度，你可以根据自己的需要进行设置。</span></span><span class="50"><span lang="EN-US"><span>TreeNodeManager.java</span></span></span><span><span>的代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>publi</strong></span></span><span lang="EN-US">c List getTree(String id) {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>List list = new ArrayList</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String seed1 = id + 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String seed2 = id + 2;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String seed3 = id + 3;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>list.add(new TreeNode(seed1, "" + seed1, false));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>list.add(new TreeNode(seed2, "" + seed2, false));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>list.add(new TreeNode(seed3, "" + seed3, true));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>return list;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>上面的代码并不复杂，它实现的效果与在</span><span lang="EN-US"><span>Java</span></span><span>中使用</span></span><span class="50"><span lang="EN-US"><span>List</span></span></span><span><span>或数组是相同的，因为返回给前台的数据都是</span><span lang="EN-US"><span>JSON</span></span><span>格式的。前台使用</span><span lang="EN-US"><span>JavaScript</span></span><span>处理返回信息的部分更简单，先引入</span></span><span class="50"><span lang="EN-US"><span>DWRTree- Loader.js</span></span></span><span><span>，然后把</span></span><span class="50"><span lang="EN-US"><span>TreeLoader</span></span></span><span><span>替换成</span></span><span class="50"><span lang="EN-US"><span>DWRTreeLoder</span></span></span><span><span>即可，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span class="hl-keyword1"><span lang="EN-US"><span><strong>&nbsp;</strong></span></span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>var</strong></span></span><span lang="EN-US">&nbsp;tree = new Ext.tree.TreePanel('tree', {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>loader: new Ext.tree.DWRTreeLoader({dataUrl: treeNodeManager.getTree})</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>参数依然是</span></span><span class="50"><span lang="EN-US"><span>dataUrl</span></span></span><span><span>，它的值</span></span><span class="50"><span lang="EN-US"><span>treeNodeManager.getTree</span></span></span><span><span>代表的是一个</span><span lang="EN-US"><span>DWR</span></span><span>函数，我们不需要对它进行深入研究，它的内部会自动处理数据之间的对应关系。</span><span lang="EN-US"><span>DWR</span></span><span>有时真的很方便。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085940"></a><a name="_Toc205277889"></a><a name="ext-ch-10-01-04"></a><span><span><span><span>10.10.4</span></span></span><span><span><span>　</span></span></span><span><span><span>DWRProxy</span></span></span><span><span><span>和</span><span>ComboBox</span></span></span></span></p>
<p class="MsoNormal"><span><span class="50"><span lang="EN-US">DWRProxy</span></span><span>既然可以用在</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>中，那么它也可以为</span><span lang="EN-US"><span>ComboBox</span></span><span>服务，如代码清单</span><span lang="EN-US"><span>10-8</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span>代码清单</span><span lang="EN-US">10-8</span><span>　</span><span class="50"><span lang="EN-US">DWRProxy</span></span><span>与</span><span lang="EN-US"><span>ComboBox</span></span><span>整合</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>var</strong></span></span><span lang="EN-US">&nbsp;info = Ext.data.Record.create([</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name: 'id', type: 'int'},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name: 'name', type: 'string'}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>var store = new Ext.data.Store({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy: new Ext.data.DWRProxy(infoManager.getItems, true),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ListRangeReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty: 'totalSize',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>root: 'data',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>id: 'id'</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}, info)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>var combo = new Ext.form.ComboBox({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>store: store,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>displayField: 'name',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>valueField: 'id',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>triggerAction: 'all',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>typeAhead: true,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>mode: 'remote',</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>emptyText: '</span></span><span>请选择</span><span lang="EN-US"><span>',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>selectOnFocus: true</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="a1"><span lang="EN-US"><span>combo.render(<span class="hl-string1"><span><strong>'combo'</strong></span></span>);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>我们既可以用</span></span><span class="50"><span lang="EN-US"><span>mode:'remote'</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>triggerAction:'all'</span></span></span><span><span>在第一次选择时读取数据，也可以设置</span></span><span class="50"><span lang="EN-US"><span>mode:'local'</span></span></span><span><span>，然后手工操作</span></span><span><span class="50"><span lang="EN-US">store.load</span></span><span lang="EN-US">()</span></span><span><span>并读取数据。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>DWR</span></span><span>要比</span><span lang="EN-US"><span>Json-lib</span></span><span>方便得多，而且</span><span lang="EN-US"><span>DWR</span></span><span>返回的数据可以直接作为</span><span lang="EN-US"><span>JSON</span></span><span>使用，使用</span><span lang="EN-US"><span>Json-lib</span></span><span>时还要面对无休无止的循环引用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>这次的示例稍微复杂一些，因为包括依赖</span><span lang="EN-US"><span>jar</span></span><span>包、</span><span lang="EN-US"><span>class</span></span><span>、</span><span lang="EN-US"><span>XML</span></span><span>和</span><span lang="EN-US"><span>JSP</span></span><span>，所以示例单独放在</span><span lang="EN-US"><span>10.store/dwr2/</span></span><span>下，请将它们复制到</span><span lang="EN-US"><span>tomcat</span></span><span>的</span><span lang="EN-US"><span>webapps</span></span><span>下，然后再使用浏览器访问。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085941"></a><a name="_Toc205277890"></a><a name="ext-ch-10-02"></a><span><span><span><span lang="EN-US"><span>10.11</span></span></span></span><span><span><span>　</span><span lang="EN-US"><span>localXHR</span></span></span></span><span><span><span>支持本地使用</span></span><span lang="EN-US"><span>Ajax</span></span></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>Ajax</span></span><span>是不能在本地文件系统中使用的，必须把数据放到服务器上。无论是</span><span lang="EN-US"><span>IIS</span></span><span>、</span><span lang="EN-US"><span>Apache</span></span><span>、</span><span lang="EN-US"><span>&nbsp;Tomcat</span></span><span>，还是你熟悉的其他服务器，只要支持</span><span lang="EN-US"><span>HTTP</span></span><span>协议，就可以使用</span><span lang="EN-US"><span>EXT</span></span><span>中的</span><span lang="EN-US"><span>Ajax</span></span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>至于本地为何不能用</span><span lang="EN-US"><span>Ajax</span></span><span>，主要是因为</span><span lang="EN-US"><span>Ajax</span></span><span>要判断</span><span lang="EN-US"><span>HTTP</span></span><span>响应返回的状态，只有</span></span><span class="50"><span lang="EN-US"><span>status=200</span></span></span><span><span>时才认为这次请求是成功的。所以，</span><span lang="EN-US"><span>localXHR</span></span><span>做的就是强行修改响应状态，让</span><span lang="EN-US"><span>Ajax</span></span><span>可以继续下去。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>下面我们来分析一下</span><span lang="EN-US"><span>localXHR</span></span><span>的源代码。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>加入了一个</span></span><span class="50"><span lang="EN-US"><span>forceActiveX</span></span></span><span><span>属性，默认是</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>，它用来控制是否强制使用</span></span><span class="50"><span lang="EN-US"><span>activex</span></span></span><span><span>，</span></span><span class="50"><span lang="EN-US"><span>activex</span></span></span><span><span>是在</span><span lang="EN-US"><span>IE</span></span><span>下专用的。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>修改</span></span><span class="50"><span lang="EN-US"><span>createXhrObject</span></span></span><span><span>函数，只是在最开始处加了一条判断语句，如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span class="hl-keyword1"><span lang="EN-US"><strong><span>&nbsp;</span></strong></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>if</strong></span></span>(Ext.isIE7 &amp;&amp; !!<span class="hl-keyword1"><span><strong>this</strong></span></span>.forceActiveX){<span class="hl-keyword1"><span><strong>throw</strong></span></span>(<span class="hl-string1"><span><strong>"IE7forceActiveX"</strong></span></span>);}<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>增加了</span></span><span class="50"><span lang="EN-US"><span>getHttpStatus</span></span></span><span><span>函数，这是为了处理</span><span lang="EN-US"><span>HTTP</span></span><span>的响应状态，如代码清单</span><span lang="EN-US"><span>10-9</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-9</span></span><span>　处理</span><span lang="EN-US"><span>HTTP</span></span><span>响应状态</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span lang="EN-US"><span>getHttpStatus:&nbsp;<span class="hl-keyword1"><span><strong>function</strong></span></span>(reqObj){</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>var</strong></span></span>&nbsp;statObj = {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>status:0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>,statusText:<span class="hl-string1"><span><strong>''</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>,isError:<span class="hl-keyword1"><span><strong>false</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>,isLocal:<span class="hl-keyword1"><span><strong>false</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>,isOK:<span class="hl-keyword1"><span><strong>false</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>};</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>try</strong></span></span>&nbsp;{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>if</strong></span></span>(!reqObj)<span class="hl-keyword1"><span><strong>throw</strong></span></span>(<span class="hl-string1"><span><strong>'noobj'</strong></span></span>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.status = reqObj.status || 0;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.isLocal = !reqObj.status &amp;&amp; location.protocol ==&nbsp;<span class="hl-string1"><span><strong>"file:"</strong></span></span>&nbsp;||</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.isSafari &amp;&amp; reqObj.status == undefined;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.statusText = reqObj.statusText ||&nbsp;<span class="hl-string1"><span><strong>''</strong></span></span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.isOK = (statObj.isLocal ||</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>(statObj.status &gt; 199 &amp;&amp; statObj.status &lt; 300) ||</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.status == 304);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}&nbsp;<span class="hl-keyword1"><span><strong>catch</strong></span></span>(e){</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-comment1"><span><em>//status may not avail/valid yet.</em></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.isError =&nbsp;<span class="hl-keyword1"><span><strong>true</strong></span></span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>return</strong></span></span>&nbsp;statObj;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>},</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>它为状态增添了更多语义，</span></span><span class="50"><span lang="EN-US"><span>status</span></span></span><span><span>表示状态值，</span></span><span class="50"><span lang="EN-US"><span>statusText</span></span></span><span><span>表示状态描述，</span></span><span class="50"><span lang="EN-US"><span>isError</span></span></span><span><span>表示是否有错误，</span></span><span class="50"><span lang="EN-US"><span>isLocal</span></span></span><span><span>表示是否在本地进行</span><span lang="EN-US"><span>Ajax</span></span><span>访问，</span></span><span class="50"><span lang="EN-US"><span>isOK</span></span></span><span><span>表示操作是否成功。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>判断</span></span><span class="50"><span lang="EN-US"><span>isLocal</span></span></span><span><span>是否为本地的有两种方法：</span></span><span class="50"><span lang="EN-US"><span>reqObj</span></span></span><span><span>没有</span></span><span class="50"><span lang="EN-US"><span>status</span></span></span><span><span>，而且请求协议是</span></span><span class="50"><span lang="EN-US"><span>file:</span></span></span><span><span>；浏览器是</span><span lang="EN-US"><span>Safari</span></span><span>，而且</span></span><span class="50"><span lang="EN-US"><span>reqObj.status</span></span></span><span><span>没有定义。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>statObj</span></span></span><span><span>中的</span></span><span class="50"><span lang="EN-US"><span>isOK</span></span></span><span><span>属性用来判断此次请求是否成功。判断请求是否成功的条件很多，例如：</span></span><span class="50"><span lang="EN-US"><span>isLocal</span></span></span><span><span>的属性为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>、响应状态值在</span><span lang="EN-US"><span>199~300</span></span><span>之间、响应状态值是</span><span lang="EN-US"><span>304</span></span><span>等。如果处理过程中出现了异常，就会将</span></span><span class="50"><span lang="EN-US"><span>isError</span></span></span><span><span>属性设置为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>，最后会把配置好的</span></span><span class="50"><span lang="EN-US"><span>statObj</span></span></span><span><span>对象返回，等待下一个步骤的处理。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>localXHR.js</span></span><span>对</span></span><span class="50"><span lang="EN-US"><span>handleTransactionResponse</span></span></span><span><span>函数进行了简化。因为增加的</span></span><span class="50"><span lang="EN-US"><span>getHttpStatus</span></span></span><span><span>函数很好地封装了与请求相关的各种状态信息，所以在</span></span><span class="50"><span lang="EN-US"><span>handleTransactionResponse</span></span></span><span><span>函数中我们不会看到让人头晕目眩的响应状态代码。取而代之的是</span></span><span class="50"><span lang="EN-US"><span>isError</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>isOK</span></span></span><span><span>这些更容易理解的属性，</span></span><span class="50"><span lang="EN-US"><span>localXHR.js</span></span></span><span><span>直接使用这些属性来处理响应。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>createResponseObject</span></span></span><span><span>函数被大大强化了。其实前半部分都是一样的，</span></span><span class="50"><span lang="EN-US"><span>localXHR.js</span></span></span><span><span>中对</span></span><span class="50"><span lang="EN-US"><span>isLocal</span></span></span><span><span>做了大量的处理，响应中的</span></span><span class="50"><span lang="EN-US"><span>responseText</span></span></span><span><span>可以从连接中获得。如果需要</span><span lang="EN-US"><span>XML</span></span><span>，它就使用</span></span><span class="50"><span lang="EN-US"><span>ActiveXObject("Microsoft.XMLDOM")</span></span></span><span><span>或</span></span><span><span class="50"><span lang="EN-US">new DOMParser</span></span><span lang="EN-US">()</span></span><span><span>把</span></span><span class="50"><span lang="EN-US"><span>responseText</span></span></span><span><span>解析成</span><span lang="EN-US"><span>XML</span></span><span>放到</span></span><span class="50"><span lang="EN-US"><span>response</span></span></span><span><span>里，响应状态也是重新计算的，这样就能让</span><span lang="EN-US"><span>Ajax</span></span><span>正常调用了。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>最后处理的是</span></span><span class="50"><span lang="EN-US"><span>asyncRequest</span></span></span><span><span>函数，如果在异步请求时出现异常，就调用</span></span><span class="50"><span lang="EN-US"><span>handleTransac- tionResponse</span></span></span><span><span>返回响应，然后根据各种情况稍微修改</span></span><span class="50"><span lang="EN-US"><span>header</span></span></span><span><span>属性。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>我们来看看下面这行代码：</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>Ext.lib.Ajax.forceActiveX = (document.location.protocol ==&nbsp;<span class="hl-string1"><span><strong>'file:'</strong></span></span>);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果协议是</span></span><span class="50"><span lang="EN-US"><span>file:</span></span></span><span><span>，就强制使用</span></span><span class="50"><span lang="EN-US"><span>activex</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085942"><span lang="EN-US"><span>10.12</span></span></a><span><span><span>　本章小结</span></span></span></p>
<p class="MsoNormal"><span><span>本章系统地讨论了</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>包中的各个类的功能和使用方式，还涉及如何将</span><span lang="EN-US"><span>EXT</span></span><span>与</span><span lang="EN-US"><span>DWR</span></span><span>通过自定义的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>相结合的示例。我们介绍了如何使用</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>与后台进行数据交互，还专门介绍了它的子类</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>，并讨论了</span><span lang="EN-US"><span>EXT</span></span><span>中</span><span lang="EN-US"><span>Ajax</span></span><span>的应用以及在回调函数中使用</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>或</span></span><span><span class="50"><span lang="EN-US">createDelegate</span></span><span lang="EN-US">()</span></span><span><span>解决</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>的问题。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>接着详细介绍了类</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>的功能和使用方法，这两个类结合起来形成了</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>中的主体数据模型，很多组件（包括</span><span lang="EN-US"><span>Grid</span></span><span>和</span><span lang="EN-US"><span>ComboBox</span></span><span>）都是建立在它们之上的。除此之外，还讨论了常用的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>：</span></span><span class="50"><span lang="EN-US"><span>SimpleStore</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>JsonStore</span></span></span><span><span>，以及它们的应用场景。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>最后我们介绍了扩展插件</span><span lang="EN-US"><span>localXHR.js</span></span><span>，它可以解决</span><span lang="EN-US"><span>EXT</span></span><span>中</span><span lang="EN-US"><span>Ajax</span></span><span>无法访问本地文件的问题。</span><span lang="EN-GB"></span></span></p>
<p class="MsoNormal"><span lang="EN-GB"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span class="5"><span>本章内容</span></span><span class="5"><span lang="EN-US"></span></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>简介</span><span lang="EN-US"></span></span></p>
<p class="a2"><span class="50"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span></p>
<p class="a2"><span class="50"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span></p>
<p class="a2"><span class="50"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>常用</span></span><span><span class="50"><span lang="EN-US">proxy</span></span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>常用</span></span><span><span class="50"><span lang="EN-US">reader</span></span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>高级</span></span><span><span class="50"><span lang="EN-US">store</span></span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span lang="EN-US"><span>EXT</span></span><span>中的</span><span lang="EN-US"><span>Ajax</span></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>关于</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>和</span></span><span><span class="50"><span lang="EN-US">createDelegate()</span></span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span lang="EN-US"><span>DWR</span></span><span>与</span><span lang="EN-US"><span>EXT</span></span><span>整合</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085913"></a><a name="_Toc205277864"></a><a name="ext-ch-03-01"></a><span><span><span><span lang="EN-US"><span>10.1</span></span></span></span><span><span><span>　</span><span lang="EN-US"><span>Ext.data</span></span></span></span><span><span><span>简介</span></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>Ext.data</span></span><span>在命名空间中定义了一系列</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>。</span><span lang="EN-US"><span>Grid</span></span><span>和</span><span lang="EN-US"><span>ComboxBox</span></span><span>都是以</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>为媒介获取数据的，它包含异步加载、类型转换、分页等功能。</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>默认支持</span></span><span class="50"><span lang="EN-US"><span>Array</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>JSON</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>XML</span></span></span><span><span>等数据格式，可以通过</span><span lang="EN-US"><span>Memory</span></span><span>、</span><span lang="EN-US"><span>HTTP</span></span><span>、</span><span lang="EN-US"><span>ScriptTag</span></span><span>等方式获得这些格式的数据。如果要实现新的协议和新的数据结构，只需要扩展</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>即可。</span><span lang="EN-US"><span>DWRProxy</span></span><span>就实现了自身的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>，让</span><span lang="EN-US"><span>EXT</span></span><span>可以直接从</span><span lang="EN-US"><span>DWR</span></span><span>获得数据。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085914"></a><a name="_Toc205277865"><span><span lang="EN-US"><span>10.2</span></span></span></a><span><span><span><span>　</span></span></span><span><span><strong><span lang="EN-US">Ext.data.Connection</span></strong></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>是对</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>的封装，它提供了配置使用</span><span lang="EN-US"><span>Ajax</span></span><span>的通用方式，它在内部通过</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>实现与后台的异步调用。与底层的</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>相比，</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Connection</span></span></span><span><span>提供了更简洁的配置方式，使用起来更方便。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>主要用于在</span></span><span class="50"><span lang="EN-US"><span>Ext.data.HttpProxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>Ext.data.ScriptTagProxy</span></span></span><span><span>中执行与后台交互的任务，它会从指定的</span><span lang="EN-US"><span>URL</span></span><span>获得数据，并把后台返回的数据交给</span><span lang="EN-US"><span>HttpProxy</span></span><span>或</span><span lang="EN-US"><span>ScriptTagProxy</span></span><span>处理，</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>的使用方式如代码清单</span><span lang="EN-US"><span>10-1</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span></span><span class="5"><span lang="EN-US"><span>10-1</span></span></span><span>　使用</span></span></span><span><span><span class="50"><span lang="EN-US">Ext.data.Connection</span></span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var conn = new Ext.data.Connection({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>autoAbort: false,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>defaultHeaders: {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>referer: 'http://localhost:8080/'</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>disableCaching : false,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>extraParams : {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'name'</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>method : 'GET',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>timeout : 300,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>url : '01-01.txt'</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在使用</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>之前，都要像上面这样创建一个新的</span></span><span class="50"><span lang="EN-US"><span>Ext.Connection</span></span></span><span><span>实例。我们可以在构造方法里配置对应的参数，比如</span></span><span class="50"><span lang="EN-US"><span>autoAbort</span></span></span><span><span>表示链接是否会自动断开、</span></span><span class="50"><span lang="EN-US"><span>default- Headers</span></span></span><span><span>参数表示请求的默认首部信息、</span></span><span class="50"><span lang="EN-US"><span>disableCaching</span></span></span><span><span>参数表示请求是否会禁用缓存、</span></span><span class="50"><span lang="EN-US"><span>extraParams</span></span></span><span><span>参数代表请求的额外参数、</span></span><span class="50"><span lang="EN-US"><span>method</span></span></span><span><span>参数表示请求方法、</span></span><span class="50"><span lang="EN-US"><span>timeout</span></span></span><span><span>参数表示连接的超时时间、</span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>参数表示请求访问的网址等。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>在创建了</span></span><span class="50"><span lang="EN-US"><span>conn</span></span></span><span><span>之后，可以调用</span></span><span class="50"><span lang="EN-US"><span>request()</span></span></span><span><span>函数发送请求，处理返回的结果，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>conn.request({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>success: function(response) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('info', response.responseText);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>failure: function</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>&nbsp;{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('warn', 'failure');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Request()</span></span></span><span><span>函数中可以设置</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>failure</span></span></span><span><span>两个回调函数，分别在请求成功和请求失败时调用。请求成功时，</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>函数的参数就是后台返回的信息。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>我们再来看一下</span></span><span class="50"><span lang="EN-US"><span>request</span></span></span><span><span>函数中的其他参数。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>url:String</span></span></span><span><span>：请求</span><span lang="EN-US"><span>url</span></span><span>。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>params:Object/String/Function</span></span></span><span><span>：请求传递的参数。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>method:String</span></span></span><span><span>：请求方法，通常为</span></span><span class="50"><span lang="EN-US"><span>GET</span></span></span><span><span>或</span></span><span class="50"><span lang="EN-US"><span>POST</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>callback:Function</span></span></span><span><span>：请求完成后的回调函数，无论是成功还是失败，都会执行。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>success:Function</span></span></span><span><span>：请求成功时的回调函数。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>failure:Function</span></span></span><span><span>：请求失败时的回调函数</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>scope:Object</span></span></span><span><span>：回调函数的作用域。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>form:Object/String</span></span></span><span><span>：绑定的</span></span><span class="50"><span lang="EN-US"><span>form</span></span></span><span><span>表单。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>isUpload:Boolean</span></span></span><span><span>：是否执行文件上传。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>headers:Object</span></span></span><span><span>：请求首部信息。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>xmlData:Object</span></span></span><span><span>：</span><span lang="EN-US"><span>XML</span></span><span>文档对象，可以通过</span><span lang="EN-US"><span>URL</span></span><span>附加参数的方式发起请求。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>disableCaching:Boolean</span></span></span><span><span>：是否禁用缓存，默认为禁用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>还提供了</span></span><span class="50"><span lang="EN-US"><span>abort([Number transactionId])</span></span></span><span><span>函数，当同时有多个请求发生时，根据指定的事务</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>放弃其中的某一个请求。如果不指定事务</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>，就会放弃最后一个请求。</span></span><span class="50"><span lang="EN-US"><span>isLoading([Number transactionId])</span></span></span><span><span>函数的用法与</span></span><span class="50"><span lang="EN-US"><span>abort()</span></span></span><span><span>类似，可以根据事务</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>判断对应的请求是否完成。如果未指定事务</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>，就判断最后一个请求是否完成。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085915"></a><a name="_Toc205277866"><span><span lang="EN-US"><span>10.3</span></span></span></a><span><span><span><span>　</span></span></span><span><span><strong><span lang="EN-US">Ext.data.Record</span></strong></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>就是一个设定了内部数据类型的对象，它是</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>的最基本组成部分。如果把</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>看作是一张二维表，那么它的每一行就对应一个</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Record</span></span></span><span><span>实例。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>的主要功能是保存数据，并且在内部数据发生改变时记录修改的状态，它还可以保留修改之前的原始值。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>我们使用</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>时通常都是由</span></span><span class="50"><span lang="EN-US"><span>create()</span></span></span><span><span>函数开始，首先用</span></span><span class="50"><span lang="EN-US"><span>create()</span></span></span><span><span>函数创建一个自定义的</span></span><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>类型，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var PersonRecord = Ext.data.Record.create([</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name: 'name', type: 'string'},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name: 'sex', type: 'int'}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>]);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>PersonRecord</span></span></span><span><span>就是我们定义的新类型，包含字符串类型的</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>和整数类型的</span></span><span class="50"><span lang="EN-US"><span>sex</span></span></span><span><span>两个属性，然后我们使用</span></span><span class="50"><span lang="EN-US"><span>new</span></span></span><span><span>关键字创建</span></span><span class="50"><span lang="EN-US"><span>PersonRecord</span></span></span><span><span>的实例，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var boy = new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'boy',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>创建对象时，可以直接通过构造方法为对象赋予初始值，将</span></span><span class="50"><span lang="EN-US"><span>'boy'</span></span></span><span><span>赋值给</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>，</span></span><span class="50"><span lang="EN-US"><span>0</span></span></span><span><span>赋值给</span></span><span class="50"><span lang="EN-US"><span>sex</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>现在，我们得到了</span></span><span class="50"><span lang="EN-US"><span>PersonRecord</span></span></span><span><span>的实例</span></span><span class="50"><span lang="EN-US"><span>boy</span></span></span><span><span>，如何才能得到它的属性呢？以下三种方式都可以获得</span><span class="50"><span lang="EN-US">boy</span></span><span>中</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>属性的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(boy.data.name);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(boy.data['name']);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(boy.get('name'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这里涉及</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>属性，这是定义在</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>中的一个公共属性，用于保存当前</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>对象的所有数据。它是一个</span><span lang="EN-US"><span>JSON</span></span><span>对象，可以直接从它里面获得需要的数据。可以通过</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>get()</span></span></span><span><span>函数方便地从</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>属性中获得指定的属性值。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果我们需要修改</span></span><span class="50"><span lang="EN-US"><span>boy</span></span></span><span><span>中的数据，请不要使用以下方式直接操作</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>boy.data.name = 'boy name';</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>boy.data['name'] = 'boy name';</span></span></span></p>
<p class="MsoNormal"><span><span>而应该使用</span></span><span class="50"><span lang="EN-US"><span>set()</span></span></span><span><span>函数，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>boy.set('name', 'body name');</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>set()</span></span></span><span><span>函数会判断属性值是否发生了改变，如果改变了，就要将当前对象的</span></span><span class="50"><span lang="EN-US"><span>dirty</span></span></span><span><span>属性设置为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>，并将修改之前的原始值放入</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>对象中，供其他函数使用。如果直接操作</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>中的值，</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>就无法记录属性数据的修改情况。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>的属性数据被修改后，我们可以执行如下几种操作。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>commit()</span></span></span><span><span>（提交）：这个函数的效果是设置</span></span><span class="50"><span lang="EN-US"><span>dirty</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>，并删除</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>中保存的原始数据。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>reject()</span></span></span><span><span>（撤销）：这个函数的效果是将</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>中已经修改了的属性值都恢复成</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>中保存的原始数据，然后设置</span></span><span class="50"><span lang="EN-US"><span>dirty</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>，并删除保存原始数据的</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>对象。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>getChanges()</span></span></span><span><span>获得修改的部分：这个函数会把</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>中经过修改的属性和数据放在一个</span><span lang="EN-US"><span>JSON</span></span><span>对象里并返回。例如上例中，</span></span><span class="50"><span lang="EN-US"><span>getChanges()</span></span></span><span><span>返回的结果是</span></span><span class="50"><span lang="EN-US"><span>{name:&rsquo;body name&rsquo;}</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>我们还可以调用</span></span><span class="50"><span lang="EN-US"><span>isModified()</span></span></span><span><span>判断当前</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>中的数据是否被修改。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>还提供了用于复制</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>实例的函数</span></span><span class="50"><span lang="EN-US"><span>copy()</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;</span>var copyBoy = boy.copy</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这样我们就得到了</span></span><span class="50"><span lang="EN-US"><span>boy</span></span></span><span><span>的一个副本，它里面包含了</span></span><span class="50"><span lang="EN-US"><span>boy</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span class="50"><span>数据</span></span><span>，但</span></span><span class="50"><span lang="EN-US"><span>copy()</span></span></span><span><span>函数不会复制</span></span><span class="50"><span lang="EN-US"><span>dirty</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>modified</span></span></span><span><span>等额外的属性值。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>中其他的参数大多与</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>有关，请参考与</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>相关的讨论。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085916"></a><a name="_Toc205277867"><span><span lang="EN-US"><span>10.4</span></span></span></a><span><span><span><span>　</span></span></span><span><span><strong><span lang="EN-US">Ext.data.Store</span></strong></span></span><strong><span lang="EN-US"></span></strong><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><a name="ext-ch-08-04-01-01"></a><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>是</span><span lang="EN-US"><span>EXT</span></span><span>中用来进行数据交换和数据交互的标准中间件，无论是</span><span lang="EN-US"><span>Grid</span></span><span>还是</span><span lang="EN-US"><span>ComboBox</span></span><span>，都是通过它实现数据读取、类型转换、排序分页和搜索等操作的。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>中有一个</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>数组，所有数据都存放在这些</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Record</span></span></span><span><span>实例中，为后面的读取和修改操作做准备。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085917"></a><a name="_Toc205277868"></a><span><span><span><span><span>10.4.1</span></span></span></span><span><span><span>　</span></span></span><span><span><span>基本应用</span></span></span><span></span></span></p>
<p class="MsoNormal"><span><span>在使用之前，首先要创建一个</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>的实例，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var data = [</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>['boy', 0],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>['girl', 1]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>];</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var store = new Ext.data.Store({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy: new Ext.data.MemoryProxy(data),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ArrayReader({}, PersonRecord)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span>store.load</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>每个</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>最少需要两个组件的支持，分别是</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>，</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>用于从某个途径读取原始数据，</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>用于将原始数据转换成</span></span><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>实例。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>这里我们使用的是</span></span><span class="50"><span lang="EN-US"><span>Ext.data.MemoryProxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>Ext.data.ArrayReader</span></span></span><span><span>，将</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>数组中的数据转换成对应的几个</span></span><span class="50"><span lang="EN-US"><span>PersonRecord</span></span></span><span><span>实例，然后放入</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中。</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>创建完毕之后，执行</span></span><span class="50"><span lang="EN-US"><span>store.load()</span></span></span><span><span>实现这个转换过程。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>经过转换之后，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>里的数据就可以提供给</span><span lang="EN-US"><span>Grid</span></span><span>或</span><span lang="EN-US"><span>ComboBox</span></span><span>使用了，这就是</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Store</span></span></span><span><span>的最基本用法。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085918"></a><a name="_Toc205277869"></a><span><span><span><span><span>10.4.2</span></span></span></span><span><span><span>　</span></span></span><span><span><span>对数据进行排序</span></span></span><span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>提供了一系列属性和函数，利用它们对数据进行排序操作。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>可以在创建</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>时使用</span></span><span class="50"><span lang="EN-US"><span>sortInfo</span></span></span><span><span>参数指定排序的字段和排序方式，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var store = new Ext.data.Store({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy: new Ext.data.MemoryProxy(data),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ArrayReader({}, PersonRecord),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sortInfo: {field: 'name', direction: 'DESC'}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这样，在</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>加载数据之后，就会自动根据</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>字段进行降序排列。对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>使用</span></span><span class="50"><span lang="EN-US"><span>store.setDefaultSort('name','DESC');</span></span></span><span><span>也会达到同样效果。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>也可以在任何时候调用</span></span><span class="50"><span lang="EN-US"><span>sort()</span></span></span><span><span>函数，比如</span></span><span class="50"><span lang="EN-US"><span>store.sort('name', 'DESC');</span></span></span><span><span>，对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行排序。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果我们希望获得</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>的排序信息，可以调用</span></span><span class="50"><span lang="EN-US"><span>getSortState()</span></span></span><span><span>函数，返回的是类似</span></span><span class="50"><span lang="EN-US"><span>{field: "name", direction: " DESC"}</span></span></span><span><span>的</span><span lang="EN-US"><span>JSON</span></span><span>对象。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>与排序相关的参数还有</span></span><span class="50"><span lang="EN-US"><span>remoteSort</span></span></span><span><span>，这个参数是用来实现后台排序功能的。当设置为</span></span><span class="50"><span lang="EN-US"><span>remoteSort:true</span></span></span><span><span>时，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>会在向后台请求数据时自动加入</span></span><span class="50"><span lang="EN-US"><span>sort</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>dir</span></span></span><span><span>两个参数，分别对应排序的字段和排序的方式，由后台获取并处理这两个参数，在后台对所需数据进行排序操作。</span></span><span class="50"><span lang="EN-US"><span>remoteSort:true</span></span></span><span><span>也会导致每次执行</span></span><span class="50"><span lang="EN-US"><span>sort()</span></span></span><span><span>时都要去后台重新加载数据，而不能只对本地数据进行排序。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>详细的用法可以参考第</span><span lang="EN-US"><span>2</span></span><span>章。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085919"></a><a name="_Toc205277870"></a><span><span><span><span><span>10.4.3</span></span></span></span><span><span><span>　</span></span></span><span><span><span>从</span></span></span><span><span><strong><span>store</span></strong></span></span><span><span><span>中获取数据</span></span></span><span></span></span></p>
<p class="MsoNormal"><span><span>从</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中获取数据有很多种途径，可以依据不同的要求选择不同的函数。最直接的方法是根据</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>在</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的行号获得对应的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，得到了</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>就可以使用</span></span><span class="50"><span lang="EN-US"><span>get()</span></span></span><span><span>函数获得里面的数据了，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.getAt(0).get('name')</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>通过这种方式，我们可以遍历</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中所有的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，依次得到它们的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>for (var i = 0; i &lt; store.getCount</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>; i++) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>var record = store.getAt(i);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>alert(record.get('name'));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Store.getCount()</span></span></span><span><span>返回的是</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的所有数据记录，然后使用</span></span><span class="50"><span lang="EN-US"><span>for</span></span></span><span><span>循环遍历整个</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>，从而得到每条记录。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>除了使用</span></span><span class="50"><span lang="EN-US"><span>getCount()</span></span></span><span><span>的方法外，还可以使用</span></span><span class="50"><span lang="EN-US"><span>each()</span></span></span><span><span>函数，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.each(function(record) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>alert(record.get('name'));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Each()</span></span></span><span><span>可以接受一个函数作为参数，遍历内部</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，并将每个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>作为参数传递给</span></span><span class="50"><span lang="EN-US"><span>function()</span></span></span><span><span>处理。如果希望停止遍历，可以让</span></span><span class="50"><span lang="EN-US"><span>function()</span></span></span><span><span>返回</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>也可以使用</span></span><span class="50"><span lang="EN-US"><span>getRange()</span></span></span><span><span>函数连续获得多个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，只需要指定开始和结束位置的索引值，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var records = store.getRange(0, 1);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>for (var i = 0; i &lt; records.length; i++) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>var record = records[i];</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>alert(record.get('name'));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果确实不知道</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>，也可以根据</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>本身的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>从</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中获得对应的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.getById(1001).get('name')</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>EXT</span></span><span>还提供了函数</span></span><span class="50"><span lang="EN-US"><span>find()</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>，可以利用它们对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行搜索，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>find( String property, String/RegExp value, [Number startIndex], [Boolean anyMatch],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>[Boolean caseSensitive] )</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在这</span><span lang="EN-US"><span>5</span></span><span>个参数中，只有前两个是必须的。第一个参数</span></span><span class="50"><span lang="EN-US"><span>property</span></span></span><span><span>代表搜索的字段名；第二个参数</span></span><span class="50"><span lang="EN-US"><span>value</span></span></span><span><span>是匹配用字符串或正则表达式；第三个参数</span></span><span class="50"><span lang="EN-US"><span>startIndex</span></span></span><span><span>表示从第几行开始搜索，第四个参数</span></span><span class="50"><span lang="EN-US"><span>anyMatch</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，不必从头开始匹配；第五个参数</span></span><span class="50"><span lang="EN-US"><span>caseSensitive</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，会区分大小写。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如下面的代码所示：</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>var index = store.find('name','g');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.getAt(index).get('name'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>与</span></span><span class="50"><span lang="EN-US"><span>find()</span></span></span><span><span>函数对应的</span></span><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>函数的定义格式如下：</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>findBy( Function fn, [Object scope], [Number startIndex] ) : Number</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>函数允许用户使用自定义函数对内部数据进行搜索。</span></span><span class="50"><span lang="EN-US"><span>fn</span></span></span><span><span>返回</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，表示查找成功，于是停止遍历并返回行号。</span></span><span class="50"><span lang="EN-US"><span>fn</span></span></span><span><span>返回</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>时，表示查找失败（即未找到），继续遍历，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>index = store.findBy(function(record, id) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>return record.get('name') == 'girl' &amp;&amp; record.get('sex') == 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.getAt(index).get('name'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>通过</span></span><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>函数，我们可以同时判断</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>中的多个字段，在函数中实现复杂逻辑。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>我们还可以使用</span></span><span class="50"><span lang="EN-US"><span>query</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>queryBy</span></span></span><span><span>函数对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行查询。与</span></span><span class="50"><span lang="EN-US"><span>find</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>findBy</span></span></span><span><span>不同的是，</span></span><span class="50"><span lang="EN-US"><span>query</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>queryBy</span></span></span><span><span>返回的是一个</span></span><span class="50"><span lang="EN-US"><span>MixCollection</span></span></span><span><span>对象，里面包含了搜索得到的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.query('name', 'boy'));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>alert(store.queryBy(function(record) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>return record.get('name') == 'girl' &amp;&amp; record.get('sex') == 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}));</span></span></span></p>
<p class="111"><a name="_Toc216085920"></a><a name="_Toc205277871"></a><span><span><span><span lang="EN-US"><span>10.4.4</span></span></span></span><span><span><span>　</span></span></span><span><span><span>更新</span></span></span><span><span><strong><span lang="EN-US">store</span></strong></span></span><span><span><span>中的数据</span></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>可以使用</span></span><span class="50"><span lang="EN-US"><span>add(Ext.data.Record[] records)</span></span></span><span><span>向</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>末尾添加一个或多个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，使用的参数可以是一个</span><span lang="EN-US"><span>record</span></span><span>实例，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.add(new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Add()</span></span></span><span><span>的也可以添加一个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>数组，如下面的代码所示：</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.add([new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other1',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}), new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other2',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>})]);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Add()</span></span></span><span><span>函数每次都会将新数据添加到</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>的末尾，这就有可能破坏</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>原有的排序方式。如果希望根据</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>原来的排序方式将新数据插入到对应的位置，可以使用</span></span><span class="50"><span lang="EN-US"><span>addSorted()</span></span></span><span><span>函数。它会在添加新数据之后立即对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>进行排序，这样就可以保证</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据有序地显示，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.addSorted(new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'lili',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 1</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>会根据排序信息查找这条</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>应该插入的索引位置，然后根据得到的索引位置插入数据，从而实现对整体进行排序。这个函数需要预先为</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>设置本地排序，否则会不起作用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果希望自己指定数据插入的索引位置，可以使用</span></span><span class="50"><span lang="EN-US"><span>insert()</span></span></span><span><span>函数。它的第一个参数表示插入数据的索引位置，可以使用</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>实例或</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>实例的数组作为参数，插入之后，后面的数据自动后移，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.insert(3, new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.insert(3, [new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other1',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}), new PersonRecord({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>name: 'other2',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>sex: 0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>})]);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>删除操作可以使用</span></span><span class="50"><span lang="EN-US"><span>remove()</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>removeAll()</span></span></span><span><span>函数，它们分别可以删除指定的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>和清空整个</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.remove(store.getAt(0));</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span>store.removeAll</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中没有专门提供修改某一行</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>的操作，我们需要先从</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中获取一个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>。对这个</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>内部数据的修改会直接反映到</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>上，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.getAt(0).set('name', 'xxxx');</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>修改</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>的内部数据之后有两种选择：执行</span></span><span class="50"><span lang="EN-US"><span>rejectChanges()</span></span></span><span><span>撤销所有修改，将修改过的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>恢复到原来的状态；执行</span></span><span class="50"><span lang="EN-US"><span>commitChanges()</span></span></span><span><span>提交数据修改。在执行撤销和提交操作之前，可以使用</span></span><span class="50"><span lang="EN-US"><span>getModifiedRecords()</span></span></span><span><span>获得</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中修改过的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>数组。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>与修改数据相关的参数是</span></span><span class="50"><span lang="EN-US"><span>pruneModifiedRecords</span></span></span><span><span>，如果将它设置为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>，当每次执行删除或</span></span><span class="50"><span lang="EN-US"><span>reload</span></span></span><span><span>操作时，都会清空所有修改。这样，在每次执行删除或</span></span><span class="50"><span lang="EN-US"><span>reload</span></span></span><span><span>操作之后，</span></span><span class="50"><span lang="EN-US"><span>getModifiedRecords()</span></span></span><span><span>返回的就是一个空数组，否则仍然会得到上次修改过的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>记录。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085921"></a><a name="_Toc205277872"></a><span><span><span><span><span>10.4.5</span></span></span></span><span><span><span>　</span></span></span><span><span><span>加载及显示数据</span></span></span><span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>创建好后，需要调用</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>函数加载数据，加载成功后才能对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行操作。</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>调用的完整过程如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.load({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>params: {start:0,limit:20},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>callback: function(records, options, success){</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('info', '</span></span><span>加载完毕</span><span lang="EN-US"><span>');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>scope: store,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>add: true</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>是在</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>加载时发送的附加参数。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>是加载完毕时执行的回调函数，它包含</span><span lang="EN-US"><span>3</span></span><span>个参数：</span></span><span class="50"><span lang="EN-US"><span>records</span></span></span><span><span>参数表示获得的数据，</span></span><span class="50"><span lang="EN-US"><span>options</span></span></span><span><span>表示执行</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>时传递的参数，</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>表示是否加载成功。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Scope</span></span></span><span><span>用来指定回调函数执行时的作用域。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Add</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>得到的数据会添加在原来的</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>数据的末尾，否则会先清除之前的数据，再将得到的数据添加到</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>一般来说，为了对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行初始化，</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>函数只需要执行一次。如果用</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>参数指定了需要使用的参数，以后再次执行</span></span><span class="50"><span lang="EN-US"><span>reload()</span></span></span><span><span>重新加载数据时，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>会自动使用上次</span></span><span class="50"><span lang="EN-US"><span>load()</span></span></span><span><span>中包含的</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>参数内容。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果有一些需要固定传递的参数，也可以使用</span></span><span class="50"><span lang="EN-US"><span>baseParams</span></span></span><span><span>参数执行，它是一个</span><span lang="EN-US"><span>JSON</span></span><span>对象，里面的数据会作为参数发送给后台处理，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.baseParams.start = 0;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.baseParams.limit = 20;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>为</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>加载数据之后，有时不需要把所有数据都显示出来，这时可以使用函数</span></span><span class="50"><span lang="EN-US"><span>filter</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>filterBy</span></span></span><span><span>对</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>中的数据进行过滤，只显示符合条件的部分，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>filter( String field, String/RegExp value, [Boolean anyMatch],&nbsp;<br />[Boolean caseSensitive] ) : void</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>filter()</span></span></span><span><span>函数的用法与之前谈到的</span></span><span class="50"><span lang="EN-US"><span>find()</span></span></span><span><span>相似，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.filter('name', 'boy');</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>对应的</span></span><span class="50"><span lang="EN-US"><span>filterBy()</span></span></span><span><span>与</span></span><span class="50"><span lang="EN-US"><span>findBy()</span></span></span><span><span>类似，也可以在自定义的函数中实现各种复杂判断，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.filterBy(function(record) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>return record.get('name') == 'girl' &amp;&amp; record.get('sex') == 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果想取消过滤并显示所有数据，那么可以调用</span></span><span class="50"><span lang="EN-US"><span>clearFilter()</span></span></span><span><span>函数，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>store.clearFilter</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果想知道</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>上是否设置了过滤器，可以通过</span></span><span class="50"><span lang="EN-US"><span>isFiltered()</span></span></span><span><span>函数进行判断。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085922"></a><a name="_Toc205277873"></a><span><span><span><span lang="EN-US"><span>10.4.6</span></span></span></span><span><span><span>　</span></span></span><span><span><span>其他功能</span></span></span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>除了上面提到的数据获取、排序、更新、显示等功能外，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>还提供了其他一些功能函数。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>collect( String dataIndex, [Boolean allowNull], [Boolean bypassFilter] ) : Array</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>collect</span></span></span><span><span>函数获得指定的</span></span><span class="50"><span lang="EN-US"><span>dataIndex</span></span></span><span><span>对应的那一列的数据，当</span></span><span class="50"><span lang="EN-US"><span>allowNull</span></span></span><span><span>参数为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，返回的结果中可能会包含</span></span><span class="50"><span lang="EN-US"><span>null</span></span></span><span class="50"><span><span>、</span></span></span><span class="50"><span lang="EN-US"><span>undefined</span></span></span><span><span>或空字符串，否则</span></span><span class="50"><span lang="EN-US"><span>collect</span></span></span><span><span>函数会自动将这些空数据过滤掉。当</span></span><span class="50"><span lang="EN-US"><span>bypassFilter</span></span></span><span><span>参数为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，</span></span><span class="50"><span lang="EN-US"><span>collect</span></span></span><span><span>的结果不会受查询条件的影响，无论查询条件是什么都会忽略掉，返回的信息是所有的数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.collect('name'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这样会获得所有</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>列的值，示例中返回的是包含了</span></span><span class="50"><span lang="EN-US"><span>'boy'</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>'girl'</span></span></span><span><span>的数组。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span class="50"><span lang="EN-US">getTotalCount</span></span><span lang="EN-US">()</span></span><span><span>用于在翻页时获得后台传递过来的数据总数。如果没有设置翻页，</span></span><span><span class="50"><span lang="EN-US">get- TotalCount</span></span><span lang="EN-US">()</span></span><span><span>的结果与</span></span><span><span class="50"><span lang="EN-US">getCount</span></span><span lang="EN-US">()</span></span><span><span>相同，都是返回当前的数据总数，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>alert(store.getTotalCount</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>indexOf(Ext.data.Record record)</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>indexOfId(String id)</span></span></span><span><span>函数根据</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>或</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>获得</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>对应的行号，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.indexOf(store.getAt(1)));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.indexOfId(1001));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>loadData(object data, [Boolean append])</span></span></span><span><span>从本地</span><span lang="EN-US"><span>JavaScript</span></span><span>变量中读取数据，</span></span><span class="50"><span lang="EN-US"><span>append</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>时，将读取的数据附加到原数据后，否则执行整体更新，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>store.loadData(data, true);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Sum(String property, Number start, Number end):Number</span></span></span><span><span>用于计算某一个列从</span><span lang="EN-US"><span>start</span></span><span>到</span><span lang="EN-US"><span>end</span></span><span>的总和，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>alert(store.sum('sex'));</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果省略参数</span></span><span class="50"><span lang="EN-US"><span>start</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>end</span></span></span><span><span>，就计算全部数据的总和。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>还提供了一系列事件（见表</span><span lang="EN-US"><span>10-1</span></span><span>），让我们可以为对应操作设定操作函数。</span><span lang="EN-US"></span></span></p>
<p align="center" class="MsoNormal"><span>表</span><span lang="EN-US">10-1</span><span>　</span><strong><span lang="EN-US">store</span></strong><span>提供的事件</span><span lang="EN-US"></span></p>
<div>
<table width="556" cellpadding="0" cellspacing="0" border="1" class="MsoNormalTable">
<tbody>
<tr>
<td valign="top" width="115">
<p align="center" class="MsoNormal"><span>事件名</span><span lang="EN-US"></span></p>
</td>
<td valign="top" width="453">
<p align="center" class="MsoNormal"><span>参　　数</span><span lang="EN-US"></span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">add</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Ext.data.Record[] records, Number index )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">beforelaod</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Object options )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">clear</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">datachanged</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">load</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Ext.data.Record[] records, Object options )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">loadexception</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">()</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">metachange</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Object meta. )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">remove</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Ext.data.Record record, Number index )</span></p>
</td>
</tr>
<tr>
<td valign="top" width="115">
<p class="MsoNormal"><span lang="EN-US">update</span></p>
</td>
<td valign="top" width="453">
<p class="MsoNormal"><span lang="EN-US">( Store this, Ext.data.Record record, String operation )</span></p>
</td>
</tr>
</tbody>
</table>
</div>
<p class="MsoNormal"><span><span>至此，</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>等组件已经讲解完毕，下面我们主要讨论一下常用的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>组件。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085923"></a><a name="_Toc205277874"><span><span lang="EN-US"><span>10.5</span></span></span></a><span><span><span><span>　常用</span></span></span><span><span><strong><span lang="EN-US">proxy</span></strong></span></span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085924"></a><a name="_Toc205277875"></a><span><span><span><span><span>10.5.1</span></span></span></span><span><span><span>　</span></span></span><span><span><strong><span>MemoryProxy</span></strong></span></span><span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>MemoryProxy</span></span></span><span><span>只能从</span><span lang="EN-US"><span>JavaScript</span></span><span>对象获得数据，可以直接把数组，或</span><span lang="EN-US"><span>JSON</span></span><span>和</span><span lang="EN-US"><span>XML</span></span><span>格式的数据交给它处理，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;proxy =&nbsp;<strong>new</strong>&nbsp;Ext.data.MemoryProxy([</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>[<strong>'id1'</strong>,<strong>'name1'</strong>,<strong>'descn1'</strong>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>[<strong>'id2'</strong>,<strong>'name2'</strong>,<strong>'descn2'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>]);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="111"><a name="_Toc216085925"></a><a name="_Toc205277876"></a><a name="ext-ch-08-04-01-02"></a><span><span><span><span>10.5.2</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>HttpProxy</span></strong></span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>使用</span><span lang="EN-US"><span>HTTP</span></span><span>协议，通过</span><span lang="EN-US"><span>Ajax</span></span><span>去后台取数据，构造它时需要设置</span></span><span class="50"><span lang="EN-US"><span>url:'xxx.jsp'</span></span></span><span><span>参数。这里的</span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>可以替换成任何一个合法的网址，这样</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>才知道去哪里获取数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;proxy =&nbsp;<strong>new</strong>&nbsp;Ext.data.HttpProxy({url:<strong>'xxx.jsp'</strong>});<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>后台需要返回</span><span lang="EN-US"><span>EXT</span></span><span>所需要的</span><span lang="EN-US"><span>JSON</span></span><span>格式的数据，下面的内容就是后台使用</span><span lang="EN-US"><span>JSP</span></span><span>的一个范例，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>response.setContentType(<strong>"application/x-json"</strong>);</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>Writer out = response.getWriter</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>out.print(<strong>"["</strong>&nbsp;+</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"['id1','name1','descn1']"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"['id2','name2','descn2']"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"]"</strong>);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>请注意，这里的</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>不支持跨域，它只能从同一域中获得数据。如果想跨域，请参考下面的</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085926"></a><a name="_Toc205277877"></a><a name="ext-ch-08-04-01-03"></a><span><span><span><span>10.5.3</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>ScriptTagProxy</span></strong></span></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>的用法几乎和</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>一样，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;proxy =&nbsp;<strong>new</strong>&nbsp;Ext.data.ScriptTagProxy({url:<strong>'xxx.jsp'</strong>});<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>从这里也看不出来它是如何支持跨域的，我们还需要在后台进行相应的处理，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>String cb = request.getParameter(<strong>"callback"</strong>);</span></span></p>
<p class="a1"><span lang="EN-US"><span>response.setContentType(<strong>"text/javascript"</strong>);</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>Writer out = response.getWriter</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>out.write(cb +&nbsp;<strong>"("</strong>);</span></span></p>
<p class="a1"><span lang="EN-US"><span>out.print(<strong>"["</strong>&nbsp;+</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"['id1','name1','descn1']"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"['id2','name2','descn2']"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"]"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>out.write(<strong>");"</strong>);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>其中的关键就在于从请求中获得的</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>参数，这个参数叫做回调函数。</span></span><span class="50"><span lang="EN-US"><span>ScriptTag- Proxy</span></span></span><span><span>会在当前的</span><span lang="EN-US"><span>HTML</span></span><span>页面里添加一个</span></span><span class="50"><span lang="EN-US"><span>&lt;script type="text/javascript"src="xxx.jsp"&gt; &lt;/script&gt;</span></span></span><span><span>标签，然后把后台返回的内容添加到这个标签中，这样就可以解决跨域访问数据的问题。为了让后台返回的内容可以在动态生成的标签中运行，</span><span lang="EN-US"><span>EXT</span></span><span>会生成一个名为</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>的回调函数，并把回调函数的名称传递给后台，由后台生成</span></span><span class="50"><span lang="EN-US"><span>callback(data)</span></span></span><span><span>形式的响应内容，然后返回给前台自动运行。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>虽然上述处理过程比较难理解，但是我们只需要了解</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>的用法就足够了。如果还想进一步了解</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>的运行过程，可以使用</span></span><span class="50"><span lang="EN-US"><span>Firebug</span></span></span><span><span>查看动态生成的</span></span><span class="50"><span lang="EN-US"><span>HTML</span></span></span><span><span>以及响应的</span><span lang="EN-US"><span>JSON</span></span><span>内容。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>最后我们来分析一下</span><span lang="EN-US"><span>EXT</span></span><span>的</span><span lang="EN-US"><span>API</span></span><span>文档中提供的示例，这段后台代码会自动判断请求的类型，返回支持</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>或</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>的数据，如代码清单</span><span lang="EN-US"><span>10-2</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-2</span></span><span>　在后台同时支持</span></span></span><span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>和</span></span><span><span class="50"><span lang="EN-US">ScriptTagProxy</span></span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">boolean</span></strong><span lang="EN-US">&nbsp;scriptTag = false;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>String cb = request.getParameter(<strong>"callback"</strong>);</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">if</span></strong><span lang="EN-US">&nbsp;(cb != null) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>scriptTag = true;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>response.setContentType(<strong>"text/javascript"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}&nbsp;<strong>else</strong>&nbsp;{</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>response.setContentType(<strong>"application/x-json"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>Writer out = response.getWriter</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">if</span></strong><span lang="EN-US">&nbsp;(scriptTag) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>out.write(cb +&nbsp;<strong>"("</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>out.print(dataBlock.toJsonString</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">if</span></strong><span lang="EN-US">&nbsp;(scriptTag) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>out.write(<strong>");"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>代码中通过判断请求中是否包含</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>参数来决定返回何种数据类型。如果包含，就返回</span></span><span class="50"><span lang="EN-US"><span>ScriptTagProxy</span></span></span><span><span>需要的数据；否则，就当作</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>处理。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085927"></a><a name="_Toc205277878"></a><a name="ext-ch-08-04-02"></a><a name="ext-ch-08-04-02-01"></a><span><span><span><span lang="EN-US"><span>10.6</span></span></span></span><span><span><span>　常用</span></span></span><span><span><strong><span lang="EN-US">Reader</span></strong></span></span></span></p>
<p class="111"><a name="_Toc216085928"></a><a name="_Toc205277879"></a><span><span><span><span>10.6.1</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>A</span></strong></span></span><span><span><strong><span>rrayReader</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>从</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>中读取的数据需要进行解析，这些数据转换成</span></span><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>数组后才能提供给</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Store</span></span></span><span><span>使用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>ArrayReader</span></span></span><span><span>的作用是从二维数组里依次读取数据，然后生成对应的</span></span><span class="50"><span lang="EN-US"><span>Record</span></span></span><span><span>。默认情况下是按列顺序读取数组中的数据，不过你也可以考虑用</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>指定</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>与原始数组对应的列号。</span></span><span class="50"><span lang="EN-US"><span>ArrayReader</span></span></span><span><span>的用法很简单，但缺点是不支持分页。使用二维数组的方式如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;data = [</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>[<strong>'id1'</strong>,<strong>'name1'</strong>,<strong>'descn1'</strong>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>[<strong>'id2'</strong>,<strong>'name2'</strong>,<strong>'descn2'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>];</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>对应的</span></span><span class="50"><span lang="EN-US"><span>ArrayReader</span></span></span><span><span>如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.ArrayReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:1</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>},[</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'name'</strong>,mapping:1},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'descn'</strong>,mapping:2},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'id'</strong>,mapping:0},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>我们演示的是字段顺序不一致的情况，如果字段顺序和列顺序一致，就不用额外配置</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085929"></a><a name="_Toc205277880"></a><a name="ext-ch-08-04-02-02"></a><span><span><span><span>10.6.2</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>JsonReader</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>在</span><span lang="EN-US"><span>JavaScript</span></span><span>中，</span><span lang="EN-US"><span>JSON</span></span><span>是一种非常重要的数据格式，</span></span><span class="50"><span lang="EN-US"><span>key:value</span></span></span><span><span>的形式比</span><span lang="EN-US"><span>XML</span></span><span>那种复杂的标签结构更容易理解，代码量也更小，很多人倾向于使用它作为</span><span lang="EN-US"><span>EXT</span></span><span>的数据交换格式。为</span></span><span class="50"><span lang="EN-US"><span>Json- Reader</span></span></span><span><span>准备的</span><span lang="EN-US"><span>JSON</span></span><span>数据如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;data = {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:0,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty:2,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>successProperty:<strong>true</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:[</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{id:<strong>'id1'</strong>,name:<strong>'name1'</strong>,descn:<strong>'descn1'</strong>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{id:<strong>'id2'</strong>,name:<strong>'name2'</strong>,descn:<strong>'descn2'</strong>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>};</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>与数组相比，</span><span lang="EN-US"><span>JSON</span></span><span>的最大优点就是支持分页，我们可以使用</span></span><span class="50"><span lang="EN-US"><span>totalProperty</span></span></span><span><span>参数表示数据的总量。</span></span><span class="50"><span lang="EN-US"><span>successProperty</span></span></span><span><span>参数是可选的，可以用它判断当前请求是否执行成功，进而判断是否进行数据加载。在不希望</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>处理响应数据时，可以把</span></span><span class="50"><span lang="EN-US"><span>successProperty</span></span></span><span><span>设置成</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>现在来讨论一下</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>，看看它是如何与上面的</span><span lang="EN-US"><span>JSON</span></span><span>数据对应的，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.JsonReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>successProperty:&nbsp;<strong>"successproperty"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty:&nbsp;<strong>"totalProperty"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:&nbsp;<strong>"root"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:&nbsp;<strong>"id"</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}, [</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'id'</strong>,mapping:<strong>'id'</strong>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'name'</strong>,mapping:<strong>'name'</strong>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'descn'</strong>,mapping:<strong>'descn'</strong>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>上例中的对应方式不够简洁，因为</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>部分的内容是相同的，其实这里的</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>可以省略，默认会用</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>参数从</span><span lang="EN-US"><span>JSON</span></span><span>中获得对应的数据。如果不想与</span><span lang="EN-US"><span>JSON</span></span><span>里的名字一样，也可以使用</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>修改。不过，</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>在这里还有其他用途，如代码清单</span><span lang="EN-US"><span>10-3</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-3</span></span><span>　为</span></span></span><span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>设置</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>进行数据映射</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;data = {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:0,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty:2,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>successProperty:<strong>true</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:[</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{id:<strong>'id1'</strong>,name:<strong>'name1'</strong>,descn:<strong>'descn1'</strong>,person:{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>id:1,name:<strong>'man'</strong>,sex:<strong>'male'</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>}},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{id:<strong>'id2'</strong>,name:<strong>'name2'</strong>,descn:<strong>'descn2'</strong>,person:{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>id:2,name:<strong>'woman'</strong>,sex:<strong>'female'</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>}}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>};</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.JsonReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>successProperty:&nbsp;<strong>"successproperty"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty:&nbsp;<strong>"totalProperty"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:&nbsp;<strong>"root"</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id:&nbsp;<strong>"id"</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}, [</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>'id'</strong>,<strong>'name'</strong>,<strong>'descn'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'person_name'</strong>,mapping:<strong>'person.name'</strong>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name:<strong>'person_sex'</strong>,mapping:<strong>'person.sex'</strong>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在上面的代码中，我们使用</span><span lang="EN-US"><span>JSON</span></span><span>支持更复杂的嵌套结构，其中的</span></span><span class="50"><span lang="EN-US"><span>person</span></span></span><span><span>对象自身就拥有</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>、</span><span><span>&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>sex</span></span></span><span><span>等属性。在</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>中可以用</span></span><span class="50"><span lang="EN-US"><span>mapping</span></span></span><span><span>把这些嵌套的内部属性映射出来，赋予对应的</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>，而其他字段都不变。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085930"></a><a name="_Toc205277881"></a><a name="ext-ch-08-04-02-03"></a><span><span><span><span>10.6.3</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>XmlReader</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>XML</span></span><span>是非常通用的数据传输格式，</span></span><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>使用的</span><span lang="EN-US"><span>XML</span></span><span>格式的数据如代码清单</span><span lang="EN-US"><span>10-4</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-4</span></span><span>　</span></span></span><span><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>使用的</span><span lang="EN-US"><span>XML</span></span></span><span><span>格式的数据</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><strong><span lang="EN-US"><span><span>&lt;?xml version="1.0" encoding="utf-8"?&gt;</span></span></span></strong></p>
<p class="a1"><strong><span lang="EN-US"><span><span>&lt;dataset&gt;</span></span></span></strong></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>id</strong>&gt;1&lt;/<strong>id</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>totalRecords</strong>&gt;2&lt;/<strong>totalRecords</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>success</strong>&gt;true&lt;/<strong>success</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>record</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>id</strong>&gt;1&lt;/<strong>id</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>name</strong>&gt;name1&lt;/<strong>name</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>descn</strong>&gt;descn1&lt;/<strong>descn</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;/<strong>record</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>record</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>id</strong>&gt;2&lt;/<strong>id</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>name</strong>&gt;name2&lt;/<strong>name</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;<strong>descn</strong>&gt;descn2&lt;/<strong>descn</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>&lt;/<strong>record</strong>&gt;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&lt;/<strong>dataset</strong>&gt;</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这里一定要用</span></span><span class="50"><span lang="EN-US"><span>dataset</span></span></span><span><span>作为</span><span lang="EN-US"><span>XML</span></span><span>根元素。再让我们看一下如何对</span></span><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>进行配置，从而读取上面示例中的</span><span lang="EN-US"><span>XML</span></span><span>数据，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.XmlReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span>totalRecords:&nbsp;<strong>'totalRecords'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span>success:&nbsp;<strong>'success'</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span>record:&nbsp;<strong>'record'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span>id:&nbsp;<strong>"id"</strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>}, [<strong>'id'</strong>,<strong>'name'</strong>,<strong>'descn'</strong>]);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>使用的参数与之前介绍的</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>有些不同，我们可以看到这里用到了</span></span><span class="50"><span lang="EN-US"><span>totalRecords</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>两个参数，其中</span></span><span class="50"><span lang="EN-US"><span>totalRecords</span></span></span><span><span>用来指定从</span></span><span class="50"><span lang="EN-US"><span>&rsquo;totalRecords&rsquo;</span></span></span><span><span>标签里获得后台数据总数，</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>则表示</span><span lang="EN-US"><span>XML</span></span><span>中放在</span></span><span class="50"><span lang="EN-US"><span>record</span></span></span><span><span>标签里的数据是我们需要显示的结果数据。其他两个参数</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>的含义和</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>中对应的参数相似，分别用来判断操是否成功和这次返回的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>。因为</span><span lang="EN-US"><span>XML</span></span><span>中的标签和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>里需要的名字是相同的，所以简化了配置，将</span></span><span class="50"><span lang="EN-US"><span>[{name:&rsquo;id&rsquo;},{name:&rsquo;name&rsquo;},{name:&rsquo;descn&rsquo;}]</span></span></span><span><span>直接写成了</span></span><span class="50"><span lang="EN-US"><span>[&lsquo;id&rsquo;,&rsquo;name&rsquo;,&rsquo;descn&rsquo;]</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>因为</span></span><span class="50"><span lang="EN-US"><span>XmlReader</span></span></span><span><span>不能将</span><span lang="EN-US"><span>JavaScript</span></span><span>中的字符串自动解析成</span><span lang="EN-US"><span>XML</span></span><span>格式的数据，因此我们需要利用其他方法进行演示。参考</span></span><span class="50"><span lang="EN-US"><span>localXHR.js</span></span></span><span><span>中构造</span><span lang="EN-US"><span>XML</span></span><span>的方式，我们有了下面的解决方案，如代码清单</span><span lang="EN-US"><span>10-5</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-5</span></span><span>　通过本地字符串构造</span><span lang="EN-US"><span>XML</span></span><span>对象</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;data = "<strong>&lt;?xml version='1.0' encoding='utf-8'?&gt;</strong>" +</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>"&lt;<strong>dataset</strong>&gt;" +</span></span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US"><span>&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>"&lt;id&gt;1&lt;/id&gt;"&nbsp;</span></strong><span lang="EN-US">+<strong></strong></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;totalRecords&gt;2&lt;/totalRecords&gt;"&nbsp;</strong>+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;success&gt;true&lt;/success&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;record&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;id&gt;1&lt;/id&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;name&gt;name1&lt;/name&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;descn&gt;descn1&lt;/descn&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;/record&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;record&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;id&gt;2&lt;/id&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>"<strong>&lt;name&gt;name2&lt;/name&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;descn&gt;descn2&lt;/descn&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;/record&gt;"</strong>&nbsp;+</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>"&lt;/dataset&gt;"</strong>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;xdoc;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">if</span></strong><span lang="EN-US">(<strong>typeof</strong>(DOMParser) ==&nbsp;<strong>'undefined'</strong>){</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>xdoc =&nbsp;<strong>new</strong>&nbsp;ActiveXObject(<strong>"Microsoft.XMLDOM"</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>xdoc.async="<strong>false</strong>";</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>xdoc.loadXML(data);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}<strong>else</strong>{</span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><strong>var</strong>&nbsp;domParser =&nbsp;<strong>new</strong>&nbsp;DOMParser</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>xdoc = domParser.parseFromString(data,&nbsp;<strong>'application/xml'</strong>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>domParser =&nbsp;<strong>null</strong>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;proxy =&nbsp;<strong>new</strong>&nbsp;Ext.data.MemoryProxy(xdoc);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;reader =&nbsp;<strong>new</strong>&nbsp;Ext.data.XmlReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>totalRecords:&nbsp;<strong>'totalRecords'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>success:&nbsp;<strong>'success'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>record:&nbsp;<strong>'record'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>id: "<strong>id</strong>"</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}, [<strong>'id','name','descn'</strong>]);</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><strong><span lang="EN-US">var</span></strong><span lang="EN-US">&nbsp;ds =&nbsp;<strong>new</strong>&nbsp;Ext.data.Store({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy: proxy,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: reader</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="11"><a name="_Toc216085931"></a><a name="_Toc205277882"></a><a name="ext-ch-08-04-03"></a><span><span><span><span lang="EN-US"><span>10.7</span></span></span></span><span><span><span>　高级</span></span></span><span><span><strong><span lang="EN-US">store</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>实际开发时，并不需要每次都对</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>这三个对象进行配置，</span><span lang="EN-US"><span>EXT</span></span><span>为我们提供了几种可选择的整合方案。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>SimpleStore</span></span></span><span lang="EN-US"><span>&nbsp;=&nbsp;</span></span><span class="50"><span lang="EN-US"><span>Store</span></span></span><span lang="EN-US"><span>&nbsp;+&nbsp;</span></span><span class="50"><span lang="EN-US"><span>MemoryProxy</span></span></span><span lang="EN-US"><span>&nbsp;+&nbsp;</span></span><span><span class="50"><span lang="EN-US">ArrayReader</span></span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><strong>var</strong>&nbsp;ds = Ext.data.SimpleStore({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>data: [</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span>&nbsp;&nbsp;</span>[<strong>'id1'</strong>,<strong>'name1'</strong>,<strong>'descn1'</strong>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span>&nbsp;&nbsp;</span>[<strong>'id2'</strong>,<strong>'name2'</strong>,<strong>'descn2'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>fields: [<strong>'id'</strong>,<strong>'name'</strong>,<strong>'descn'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>SimpleStore</span></span></span><span><span>是专为简化读取本地数组而设计的，设置上</span></span><span class="50"><span lang="EN-US"><span>MemoryProxy</span></span></span><span><span>需要的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>ArrayReader</span></span></span><span><span>需要的</span></span><span class="50"><span lang="EN-US"><span>fields</span></span></span><span><span>就可以使用了。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>JsonStore</span></span></span><span lang="EN-US"><span>&nbsp;=&nbsp;</span></span><span class="50"><span lang="EN-US"><span>Store</span></span></span><span lang="EN-US"><span>&nbsp;+&nbsp;</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span lang="EN-US"><span>&nbsp;+&nbsp;</span></span><span><span class="50"><span lang="EN-US">JsonReader</span></span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><strong>var</strong>&nbsp;ds = Ext.data.JsonStore({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>url:&nbsp;<strong>'xxx.jsp'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>root:&nbsp;<strong>'root'</strong>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>fields: [<strong>'id'</strong>,<strong>'name'</strong>,<strong>'descn'</strong>]</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>JsonStore</span></span></span><span><span>将</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>HttpProxy</span></span></span><span><span>整合在一起，提供了一种从后台读取</span><span lang="EN-US"><span>JSON</span></span><span>信息的简便方法，大多数情况下可以考虑直接使用它从后台读取数据。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>Ext.data.GroupingStore</span></span></span><span><span>对数据进行分组</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.data.GroupingStore</span></span></span><span><span>继承自</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>，它的主要功能是可以对内部的数据进行分组，我们可以在创建</span></span><span class="50"><span lang="EN-US"><span>Ext.data.GroupingStore</span></span></span><span><span>时指定根据某个字段进行分组，也可以在创建实例后调用它的</span></span><span class="50"><span lang="EN-US"><span>groupBy()</span></span></span><span><span>函数对内部数据重新分组，如下面的代码所示。</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>var ds = new Ext.data.GroupingStore({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>data: [</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id1','name1','female','descn1'],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id2','name2','male','descn2'],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id3','name3','female','descn3'],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id4','name4','male','descn4'],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>['id5','name5','female','descn5']</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>],</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ArrayReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>fields: ['id','name','sex','descn']</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>}),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>groupField: 'sex',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>groupOnSort: true</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>});</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>上例中，我们使用</span></span><span class="50"><span lang="EN-US"><span>groupField</span></span></span><span><span class="50"><span>作为</span></span><span>参数，为</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Grouping</span></span></span><span><span>设置了分组字段，另外还设置了</span></span><span class="50"><span lang="EN-US"><span>groupOnSort</span></span></span><span><span>参数，这个参数可以保证只有在进行分组时才会对</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Grouping- Store</span></span></span><span><span>内部的数据进行排序。如果采用默认值，就需要手工指定</span></span><span class="50"><span lang="EN-US"><span>sortInfo</span></span></span><span><span>参数，从而指定默认的排序字段和排序方式，否则就会出现错误。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>创建</span></span><span class="50"><span lang="EN-US"><span>Ext.data.GroupingStore</span></span></span><span><span>的实例之后，我们还可以调用</span></span><span class="50"><span lang="EN-US"><span>groupBy()</span></span></span><span><span>函数重新对数据进行分组。因为我们设置了</span></span><span class="50"><span lang="EN-US"><span>groupOnSort:true</span></span></span><span><span>，所以在重新分组时，</span><span lang="EN-US"><span>EXT</span></span><span>会使用分组的字段对内部数据进行排序。如果不希望对数据进行分组，也可以调用</span></span><span class="50"><span lang="EN-US"><span>clearGrouping()</span></span></span><span><span>函数清除分组信息，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>ds.groupBy('id');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>ds.clearGrouping();<span></span></span></span></span></p>
<p class="11"><a name="_Toc216085932"></a><a name="_Toc205277883"></a><a name="ext-ch-08-05"></a><a name="ext-ch-08-06"></a><span><span><span><span lang="EN-US"><span>10.8</span></span></span></span><span><span><span>　</span><span lang="EN-US"><span>EXT</span></span></span></span><span><span><span>中的</span><span lang="EN-US"><span>Ajax</span></span></span></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>EXT</span></span><span>与后台交换数据时，很大程度上依赖于底层实现的</span><span lang="EN-US"><span>Ajax</span></span><span>。所谓底层实现，就是说很可能就是我们之前提到的</span><span><span>&nbsp;<span lang="EN-US">Prototype</span></span></span><span>、</span><span lang="EN-US"><span>jQuery</span></span><span>或</span><span lang="EN-US"><span>YUI</span></span><span>中提供的</span><span lang="EN-US"><span>Ajax</span></span><span>功能。为了统一接口，</span><span lang="EN-US"><span>EXT</span></span><span>在它们的基础上进行了封装，让我们可以用同一种写法&ldquo;游走&rdquo;于各种不同的底层实现之间。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085933"></a><span><span><span>10.8.1</span></span><span><span>　</span></span><span><span>最容易看到的</span></span><span><strong><span>Ext.Ajax</span></strong></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>的基本用法如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>Ext.Ajax.request({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>url: '07-01.txt',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>success: function(response) {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('</span></span><span>成功</span><span lang="EN-US"><span>', response.responseText);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>failure: function(response) {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('</span></span><span>失败</span><span lang="EN-US"><span>', response.responseText);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>params: { name: 'value' }</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>这里调用的是</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>的</span></span><span class="50"><span lang="EN-US"><span>request</span></span></span><span><span>函数，它的参数是一个</span><span lang="EN-US"><span>JSON</span></span><span>对象，具体如下所示。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>参数表示将要访问的后台网址。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>参数表示响应成功后的回调函数。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>上例中我们直接从</span></span><span class="50"><span lang="EN-US"><span>response</span></span></span><span><span>取得返回的字符串，用</span></span><span class="50"><span lang="EN-US"><span>Ext.Msg.alert</span></span></span><span><span>显示出来。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>failure</span></span></span><span><span>参数表示响应失败后的回调函数。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>注意，这里的响应失败并不是指数据库操作之类的业务性失败，而是指</span><span lang="EN-US"><span>HTTP</span></span><span>返回</span><span lang="EN-US"><span>404</span></span><span>或</span><span lang="EN-US"><span>500</span></span><span>错误，请不要把</span><span lang="EN-US"><span>HTTP</span></span><span>响应错误与业务错误混淆在一起。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>参数表示请求时发送到后台的参数，既可以使用</span><span lang="EN-US"><span>JSON</span></span><span>对象，也可以直接使用</span></span><span class="50"><span lang="EN-US"><span>"name=value"</span></span></span><span><span>形式的字符串。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>上面的示例可以在</span><span lang="EN-US"><span>10.store/07-01.html</span></span><span>中找到。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>直接继承自</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>，不同的是，它是一个单例，不需要用</span></span><span class="50"><span lang="EN-US"><span>new</span></span></span><span><span>创建实例，可以直接使用。在使用</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>前需要先创建实例，因为</span></span><span class="50"><span lang="EN-US"><span>Ext.data. Connection</span></span></span><span><span>是为了给</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>中的各种</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>提供</span></span><span class="50"><span lang="EN-US"><span>Ajax</span></span></span><span><span>功能，分配不同的实例更有利于分别管理。</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>为用户提供了一个简易的调用接口，实际使用时，可以根据自己的需要进行选择。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085934"></a><span><span><span>10.8.2</span></span><span><span>　</span></span><span><span>Ext.lib.Ajax</span></span><span><span>是更底层的封装</span></span></span></p>
<p class="MsoNormal"><span><span>其实</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>的内部功能实现都是依靠</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>来完成的，在</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>下面就是各种底层库的</span><span lang="EN-US"><span>Ajax</span></span><span>了。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果使用</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>实现以上的功能，就需要写成下面的形式，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>Ext.lib.Ajax.request(</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>'POST',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>'07-01txt',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{success: function(response){</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('</span></span><span>成功</span><span lang="EN-US"><span>', response.responseText);</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>},failure: function</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>{</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.Msg.alert('</span></span><span>失败</span><span lang="EN-US"><span>', response.responseText);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>'data=' + encodeURIComponent(Ext.encode({name:'value'}))</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>我们可以看到，使用</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>时需要传递</span><span lang="EN-US"><span>4</span></span><span>个参数，分别为</span></span><span class="50"><span lang="EN-US"><span>method</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>。它们的含义与</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>中的参数都是一一对应的，唯一没有提到过的</span></span><span class="50"><span lang="EN-US"><span>method</span></span></span><span><span>参数表示请求</span><span lang="EN-US"><span>HTTP</span></span><span>的方法，它也可以在</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>中使用</span></span><span class="50"><span lang="EN-US"><span>method:'POST'</span></span></span><span><span>的方式设置。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>相对于</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>来说，</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>有如下几个缺点。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>参数的顺序被定死了，第一个参数是</span></span><span class="50"><span lang="EN-US"><span>method</span></span></span><span><span>，第二个参数是</span></span><span class="50"><span lang="EN-US"><span>url</span></span></span><span><span>，第三个参数是回调函数</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>，第四个参数是</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>。这样既不容易记忆，也无法省略其中某个不需要的参数。</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>中用</span><span lang="EN-US"><span>JSON</span></span><span>对象来定义参数，使用起来更灵活。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>在</span></span><span class="50"><span lang="EN-US"><span>params</span></span></span><span><span>部分，</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>必须使用字符串形式，显得有些笨重。</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>则可以在</span><span lang="EN-US"><span>JSON</span></span><span>对象和字符串之间随意选择，非常灵活。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>比与</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>相比，</span></span><span class="50"><span lang="EN-US"><span>Ext.lib.Ajax</span></span></span><span><span>的唯一优势就是它可以在</span><span lang="EN-US"><span>EXT 1.x</span></span><span>中使用。如果你使用的是</span><span lang="EN-US"><span>EXT 2.0</span></span><span>或更高的版本，那么就放心大胆地使用</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>吧，它会带给你更多的惊喜。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>该示例在</span><span lang="EN-US"><span>10.store/07-02.html</span></span><span>中。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085935"></a><a name="_Toc205277884"><span><span lang="EN-US"><span>10.9</span></span></span></a><span><span><span><span>　关于</span></span></span><span><span><strong><span lang="EN-US">scope</span></strong></span></span><span><span><span>和</span></span></span><span><span><strong><span lang="EN-US">createDelegate()</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>关于</span><span lang="EN-US"><span>JavaScript</span></span><span>中</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>的使用，这是一个由来已久的问题了。我们这里就不介绍它的发展历史了，只结合具体的例子，告诉大家可能会遇到什么问题，在遇到这些问题时</span><span lang="EN-US"><span>EXT</span></span><span>是如何解决的。在使用</span><span lang="EN-US"><span>EXT</span></span><span>时，最常碰到的就是使用</span><span lang="EN-US"><span>Ajax</span></span><span>回调函数时出现的问题，如下面的代码所示。</span><span lang="EN-US"><span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span lang="EN-US">&lt;<strong><em>input</em></strong>&nbsp;<span class="hl-attribute"><span>type</span></span>=<span class="hl-value"><span>"text"</span></span>&nbsp;<span class="hl-attribute"><span>name</span></span>=<span class="hl-value"><span>"text"</span></span>&nbsp;<span class="hl-attribute"><span>id</span></span>=<span class="hl-value"><span>"text"</span></span>&gt;</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&lt;input type="button" name="button" id="button" value="button"&gt;</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>现在的</span><span lang="EN-US"><span>HTML&nbsp;</span></span><span>页面中有一个</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>输入框和一个按钮。我们希望按下这个按钮之后，能用</span><span lang="EN-US"><span>Ajax</span></span><span>去后台读取数据，然后把后台响应的数据放到</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>中，实现过程如代码清单</span><span><span lang="EN-US">1</span><span lang="EN-GB">0</span><span lang="EN-US">-6</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-6</span></span><span>　</span><span lang="EN-US"><span>Ajax</span></span></span><span><span>中使用回调函数</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><span><strong><span lang="EN-US">functio</span>n</strong></span><span lang="EN-US">&nbsp;doSuccess(response) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>text.dom.value = response.responseText;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>Ext.onReady(function</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>{</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.get('button').on('click', function</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>var text = Ext.get('text');</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.lib.Ajax.request(</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>'POST',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>'08.txt',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>{success:doSuccess},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>'param=' + encodeURIComponent(text.dom.value)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>});</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在上面的代码中，</span><span lang="EN-US"><span>Ajax</span></span><span>已经用</span></span><span class="50"><span lang="EN-US"><span>Ext.get('text')</span></span></span><span><span>获得了</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>，以为后面可以直接使用，没想到回调函数</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>不会按照你写的顺序去执行。当然，也不会像你所想的那样使用局部变量</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>。实际上，如果什么都不做，仅仅只是使用回</span><span>调函数，你不得不再次使用</span></span><span class="50"><span lang="EN-US"><span>Ext.get('text')</span></span></span><span><span>重新获得元素，否则浏览器就会报</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>未定义的错误。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>在此使用</span></span><span class="50"><span lang="EN-US"><span>Ext.get('text')</span></span></span><span><span>重新获取对象还比较简单，在有些情况下不容易获得需要处理的对象，我们要在发送</span><span lang="EN-US"><span>Ajax</span></span><span>请求之前获取回调函数中需要操作的对象，有两种方法可供选择：</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>createDelegate</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>为</span><span lang="EN-US"><span>Ajax</span></span><span>设置</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>。</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>function</strong></span></span>&nbsp;doSuccess(response) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>this</strong></span></span>.dom.value = response.responseText;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>Ext.lib.Ajax.request(</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'POST'</strong></span></span>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'08.txt'</strong></span></span>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{success:doSuccess,scope:text},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'param='</strong></span></span>&nbsp;+ encodeURIComponent(text.dom.value)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>在</span><span lang="EN-US"><span>Ajax</span></span><span>的</span></span><span class="50"><span lang="EN-US"><span>callback</span></span></span><span><span>参数部分添加一个</span></span><span class="50"><span lang="EN-US"><span>scope:text</span></span></span><span><span>，把回调函数的</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>指向</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>，它的作用就是把</span></span><span class="50"><span lang="EN-US"><span>doSuccess</span></span></span><span><span>函数里的</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>指向</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>对象。然后再把</span></span><span class="50"><span lang="EN-US"><span>doSuccess</span></span></span><span><span>里改成</span></span><span class="50"><span lang="EN-US"><span>this.dom. value</span></span></span><span><span>，这样就可以了。如果想再次在回调函数里用某个对象，必须配上</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>，这样就能在回调函数中使用</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>对它进行操作了。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>为</span></span><span class="50"><span lang="EN-US"><span>success</span></span></span><span><span>添加</span></span><span class="50"><span lang="EN-US"><span>createDelegate()</span></span></span><span><span>。</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>function</strong></span></span>&nbsp;doSuccess(response) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>this</strong></span></span>.dom.value = response.responseText;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span>&nbsp;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>Ext.lib.Ajax.request(</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'POST'</strong></span></span>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'08.txt'</strong></span></span>,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{success:doSuccess.createDelegate(text)},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-string1"><span><strong>'param='</strong></span></span>&nbsp;+ encodeURIComponent(text.dom.value)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span>);</span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>createDelegate</span></span></span><span><span>只能在</span></span><span class="50"><span lang="EN-US"><span>function</span></span></span><span><span>上调用，它把函数里的</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>强行指向我们需要的对象，然后我们就可以在回调函数</span></span><span class="50"><span lang="EN-US"><span>doSuccess</span></span></span><span><span>里直接通过</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>来引用</span></span><span class="50"><span lang="EN-US"><span>createDelegate()</span></span></span><span><span>中指定的这个对象了。它可以作为解决</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>问题的一个备选方案。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>如果让我选择，我会尽量选择</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>，因为</span></span><span class="50"><span lang="EN-US"><span>createDelegate</span></span></span><span><span>是要对原来的函数进行封装，重新生成</span></span><span class="50"><span lang="EN-US"><span>function</span></span></span><span><span>对象。简单环境下，</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>就够用了，倒是</span></span><span class="50"><span lang="EN-US"><span>createDelegate</span></span></span><span><span>还有其他功能，比如修改调用参数等。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>示例在</span><span lang="EN-US"><span>10.store/08.html</span></span><span>中。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085936"></a><a name="_Toc205277885"></a><a name="ext-ch-10-01"></a><span><span><span><span lang="EN-US"><span>10.10</span></span></span></span><span><span><span>　</span><span lang="EN-US"><span>DWR</span></span></span></span><span><span><span>与</span><span lang="EN-US"><span>EXT</span></span></span></span><span><span><span>整合</span></span></span></span></p>
<p class="MsoNormal"><span><span>据不完全统计，从事</span><span lang="EN-US"><span>Ajax</span></span><span>开发的</span><span lang="EN-US"><span>Java</span></span><span>程序员有一大半都使用</span><span lang="EN-US"><span>DWR</span></span><span>。我们下面来介绍一下如何在</span><span lang="EN-US"><span>EXT</span></span><span>中使用</span><span lang="EN-US"><span>DWR</span></span><span>与后台交互。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085937"></a><a name="_Toc205277886"></a><a name="ext-ch-10-01-01"></a><span><span><span><span>10.10.1</span></span></span><span><span><span>　</span></span></span><span><span><span>在</span><span>EXT</span></span></span><span><span><span>中直接使用</span><span>DWR</span></span></span></span></p>
<p class="MsoNormal"><span><span>因为</span><span lang="EN-US"><span>DWR</span></span><span>在前台的表现形式和普通的</span><span lang="EN-US"><span>JavaScript</span></span><span>完全一样，所以我们不需要特地去做些什么，直接使用</span><span lang="EN-US"><span>EXT</span></span><span>调用</span><span lang="EN-US"><span>DWR</span></span><span>生成的</span><span lang="EN-US"><span>JavaScript</span></span><span>函数即可。以</span><span lang="EN-US"><span>Grid</span></span><span>为例，比如现在我们要显示一个通讯录的信息，后台记录的数据有：</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>name</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>sex</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>email</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>tel</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>addTime</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>descn</span></span></span><span><span>。编写对应的</span><span lang="EN-US"><span>POJO</span></span><span>，代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>public</strong></span></span><span lang="EN-US">&nbsp;<span class="hl-keyword1"><span><strong>cla</strong></span></span>ss Info {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>long id;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String name;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int sex;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String email;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String tel;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>Date addTime;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String descn;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>然后编写操作</span><span lang="EN-US"><span>POJO</span></span><span>的</span></span><span class="50"><span lang="EN-US"><span>manager</span></span></span><span><span>类，代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>public</strong></span></span><span lang="EN-US">&nbsp;<span class="hl-keyword1"><span><strong>class</strong></span></span>&nbsp;InfoManager {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>private List infoList = new ArrayList</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>public List getResult</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>&nbsp;{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>return infoList;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>代码部分有些删减，我们只保留了其中的关键部分，就这样把这两个类配置到</span><span lang="EN-US"><span>dwr.xml</span></span><span>中，让前台可以对这些类进行调用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>下面是</span><span lang="EN-US"><span>EXT</span></span><span>与</span><span lang="EN-US"><span>DWR</span></span><span>交互的关键部分，我们要对</span><span lang="EN-US"><span>JavaScript</span></span><span>部分做如下修改，如代码清单</span><span lang="EN-US"><span>10-7</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-7</span></span><span>　使用</span><span lang="EN-US"><span>EXT</span></span><span>调用</span></span><span lang="EN-US"><span><span>DWR</span></span></span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>var</strong></span></span><span lang="EN-US">&nbsp;cm =&nbsp;<span class="hl-keyword1"><span><strong>new</strong></span></span>&nbsp;Ext.grid.ColumnModel([</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>编号</span><span lang="EN-US"><span>',dataIndex:'id'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>名称</span><span lang="EN-US"><span>',dataIndex:'name'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>性别</span><span lang="EN-US"><span>',dataIndex:'sex'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>邮箱</span><span lang="EN-US"><span>',dataIndex:'email'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>电话</span><span lang="EN-US"><span>',dataIndex:'tel'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>添加时间</span><span lang="EN-US"><span>',dataIndex:'addTime'},</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{header:'</span></span><span>备注</span><span lang="EN-US"><span>',dataIndex:'descn'}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>var store = new Ext.data.JsonStore({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>fields: ["id","name","sex",'email','tel','addTime','descn']</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span lang="EN-US"><span>//&nbsp;</span></span><span>调用</span><span lang="EN-US"><span>DWR</span></span><span>取得数据</span></span></p>
<p class="a1"><span lang="EN-US"><span>infoManager.getResult(function(data) {</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>store.loadData(data);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>var grid = new Ext.grid.GridPanel({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>renderTo: 'grid',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>store: store,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>cm: cm</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>注意，执行</span></span><span class="50"><span lang="EN-US"><span>infoManager.getResult()</span></span></span><span><span>函数时，</span><span lang="EN-US"><span>DWR</span></span><span>就会使用</span><span lang="EN-US"><span>Ajax</span></span><span>去后台取数据了，操作成功后调用我们定义的匿名回调函数。在这里我们只做一件事，那就是将返回的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>直接注入到</span></span><span class="50"><span lang="EN-US"><span>ds</span></span></span><span><span>中。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>DWR</span></span><span>返回的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>可以被</span></span><span class="50"><span lang="EN-US"><span>JsonStore</span></span></span><span><span>直接读取，我们需要设置对应的</span></span><span class="50"><span lang="EN-US"><span>fields</span></span></span><span><span>参数，以告诉</span></span><span class="50"><span lang="EN-US"><span>JsonReader</span></span></span><span><span>需要哪些属性。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>在这里，</span><span lang="EN-US"><span>EXT</span></span><span>和</span><span lang="EN-US"><span>DWR</span></span><span>两者之间没有任何关系，将它们任何一方替换掉都可以。实际上它们只是在一起运行，并没有整合。我们给出的这个示例也是说明了一种松耦合的可能性，实际操作中完全可以使用这种方式。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085938"></a><a name="_Toc205277887"></a><a name="ext-ch-10-01-02"></a><span><span><span><span>10.10.2</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>DWRProxy</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>要结合使用</span><span lang="EN-US"><span>EXT</span></span><span>和</span><span lang="EN-US"><span>DWR</span></span><span>，不需要对后台程序进行任何修改，可以直接让前后台数据进行交互。不过还要考虑很多细节，比如</span><span lang="EN-US"><span>Grid</span></span><span>分页、刷新、排序、搜索等常见的操作。</span><span lang="EN-US"><span>EXT</span></span><span>的官方网站上已经有人放上了</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>，借助它可以让</span><span lang="EN-US"><span>DWR</span></span><span>和</span><span lang="EN-US"><span>EXT</span></span><span>连接得更加紧密。不过，需要在后台添加</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>所需要的</span><span lang="EN-US"><span>Java</span></span><span>类，这可能不是最好的解决方案。但我们相信，通过对它的内在实现的讨论，我们可以有更多的选择和想象空间。</span><span lang="EN-US"></span></span></p>
<div>
<p class="055205505"><span><span class="5"><span>注意</span></span><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span><span>这个</span><span><span>DWRProxy.js</span></span><span>一定要放在</span><span><span>ext-base.js</span></span><span>和</span><span><span>ext-all.js</span></span><span>后面，否则会出错。</span><span></span></span></p>
</div>
<p class="MsoNormal"><span><span>我们现在就用</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>来实现一个分页的示例。除了准备好插件</span><span lang="EN-US"><span>DWRProxy.js</span></span><span>外，还要在后台准备一个专门用于分页的封装类。因为不仅要告诉前台显示哪些数据，还要告诉前台一共有多少条数据。现在我们来重点看一下</span></span><span class="50"><span lang="EN-US"><span>ListRange.java</span></span></span><span><span>，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>public class ListRange {</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>Object[] data;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int totalSize;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>其实</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>非常简单，只有两个属性：提供数据的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>和提供数据总量的</span></span><span class="50"><span lang="EN-US"><span>totalSize</span></span></span><span><span>。再看一下</span></span><span class="50"><span lang="EN-US"><span>InfoManager.java</span></span></span><span><span>，为了实现分页，我们专门编写了一个</span></span><span class="50"><span lang="EN-US"><span>getItems</span></span></span><span><span>方法，代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>pub</strong></span></span><span lang="EN-US">lic ListRange getItems(Map conditions) {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int start = 0;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int pageSize = 10;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>int pageNo = (start / pageSize) + 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>try {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>start = Integer.parseInt(conditions.get("start").toString</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>pageSize = Integer.parseInt(conditions.get("limit").toString</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>pageNo = (start / pageSize) + 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>} catch (Exception ex) {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>ex.printStackTrace</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>List list = infoList.subList(start, start + pageSize);</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>return new ListRange(list.toArray</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>, infoList.size</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>getItems()</span></span></span><span><span>的参数是</span></span><span class="50"><span lang="EN-US"><span>Map</span></span></span><span><span>，我们从中获得需要的参数，比如</span></span><span class="50"><span lang="EN-US"><span>start</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>limit</span></span></span><span><span>。不过</span><span lang="EN-US"><span>HTTP</span></span><span>里的参数都是字符串，而我们需要的是数字，所以要对类型进行相应的转换。根据</span></span><span class="50"><span lang="EN-US"><span>start</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>limit</span></span></span><span><span>两个属性从全部数据中截取一部分，放进新建的</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>中，然后把生成的</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>返回给前台，于是一切都解决了。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>重头戏要上演了，我们就要使用传说中的</span></span><span class="50"><span lang="EN-US"><span>Ext.data.DWRProxy</span></span></span><span><span>了，还有</span></span><span class="50"><span lang="EN-US"><span>Ext.data.List- RangeReader</span></span></span><span><span>。通过这两个扩展，</span><span lang="EN-US"><span>EXT</span></span><span>完全可以支持</span><span lang="EN-US"><span>DWR</span></span><span>的数据传输协议。实际上，这正是</span><span lang="EN-US"><span>EXT</span></span><span>要把数据和显示分离设计的原因，这样你只需要添加自定义的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>，不需要修改</span><span lang="EN-US"><span>EXT</span></span><span>的其他部分，就可以实现从特定途径获取数据的功能。后台还是</span><span lang="EN-US"><span>DWR</span></span><span>，所以至少在</span><span lang="EN-US"><span>Grid</span></span><span>部分，我们可以很好地使用它们的结合，主要代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>var</strong></span></span><span lang="EN-US">&nbsp;store =&nbsp;<span class="hl-keyword1"><span><strong>new</strong></span></span>&nbsp;Ext.data.Store({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy:&nbsp;<span class="hl-keyword1"><span><strong>new</strong></span></span>&nbsp;Ext.data.DWRProxy(infoManager.getItems,&nbsp;<span class="hl-keyword1"><span><strong>true</strong></span></span>),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ListRangeReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty: 'totalSize',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>root: 'data',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>id: 'id<span class="hl-string1"><span><strong>'</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}, info),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>remoteSort: true</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>与我们上面说的一样，我们修改了</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>，也修改了</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>，其他地方都不需要进行修改，</span><span lang="EN-US"><span>Grid</span></span><span>已经可以正常运行了。需要提醒的是</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>的用法，其中包括两个参数：第一个是</span></span><span class="50"><span lang="EN-US"><span>dwr- Call</span></span></span><span><span>，它把一个</span><span lang="EN-US"><span>DWR</span></span><span>函数放进去，它对应的是后台的</span></span><span class="50"><span lang="EN-US"><span>getItems</span></span></span><span><span>方法；第二个参数是</span></span><span class="50"><span lang="EN-US"><span>paging- AndSort</span></span></span><span><span>，这个参数控制</span><span lang="EN-US"><span>DWR</span></span><span>是否需要分页和排序。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>ListRangeReader</span></span></span><span><span>部分与后台的</span></span><span class="50"><span lang="EN-US"><span>ListRange.java</span></span></span><span><span>对应。</span></span><span class="50"><span lang="EN-US"><span>totalProperty</span></span></span><span><span>表示后台数据总数，我们通过它指定从</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>中读取</span></span><span class="50"><span lang="EN-US"><span>totalSize</span></span></span><span><span>属性的值来作为后台数据总数。还需要指定</span></span><span class="50"><span lang="EN-US"><span>root</span></span></span><span><span>参数，以告诉它在</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>中的数据变量的名称为</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>，随后</span></span><span class="50"><span lang="EN-US"><span>DWRProxy</span></span></span><span><span>会从</span></span><span class="50"><span lang="EN-US"><span>ListRange</span></span></span><span><span>中的</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>属性中获取数据并显示到页面上。如果不想使用我们提供的</span></span><span class="50"><span lang="EN-US"><span>ListRange.java</span></span></span><span><span class="50"><span>类</span></span><span>，也可以自己创建一个类，只要把</span></span><span class="50"><span lang="EN-US"><span>totalProperty</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>data</span></span></span><span><span>两个属性与之对应即可。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085939"></a><a name="_Toc205277888"></a><a name="ext-ch-10-01-03"></a><span><span><span><span>10.10.3</span></span></span><span><span><span>　</span></span></span><span><span><strong><span>DWRTreeLoader</span></strong></span></span></span></p>
<p class="MsoNormal"><span><span>我们现在来尝试一下让树形也支持</span><span lang="EN-US"><span>DWR</span></span><span>。有了前面的基础，整合</span><span lang="EN-US"><span>DWR</span></span><span>和</span><span lang="EN-US"><span>tree</span></span><span>就更简单了。在后台，我们需要树形节点对应的</span></span><span class="50"><span lang="EN-US"><span>TreeNode.java</span></span></span><span><span>。目前，只要</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>leaf</span></span></span><span><span>三项就可以了。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>publ</strong></span></span><span lang="EN-US">ic class TreeNode {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String id;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String text;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>boolean leaf;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>是节点的唯一标记，知道了</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span><span>就能知道是在触发哪个节点了。</span></span><span class="50"><span lang="EN-US"><span>text</span></span></span><span><span>是显示的标题，</span></span><span class="50"><span lang="EN-US"><span>leaf</span></span></span><span><span>比较重要，它用来标记这个节点是不是叶子。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>这里还是用异步树，</span></span><span class="50"><span lang="EN-US"><span>TreeNodeManager.java</span></span></span><span><span>里的</span></span><span><span class="50"><span lang="EN-US">getTree</span></span><span lang="EN-US">()</span></span><span><span>方法将获得一个节点的</span></span><span class="50"><span lang="EN-US"><span>id</span></span></span><span class="50"><span>作为</span></span><span><span>参数，然后返回这个节点下的所有子节点。我们这里没有限制生成的树形的深度，你可以根据自己的需要进行设置。</span></span><span class="50"><span lang="EN-US"><span>TreeNodeManager.java</span></span></span><span><span>的代码如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>publi</strong></span></span><span lang="EN-US">c List getTree(String id) {</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>List list = new ArrayList</span></span><span lang="EN-US">()</span><span lang="EN-US"><span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String seed1 = id + 1;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String seed2 = id + 2;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>String seed3 = id + 3;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>list.add(new TreeNode(seed1, "" + seed1, false));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>list.add(new TreeNode(seed2, "" + seed2, false));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>list.add(new TreeNode(seed3, "" + seed3, true));</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>return list;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>}</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>上面的代码并不复杂，它实现的效果与在</span><span lang="EN-US"><span>Java</span></span><span>中使用</span></span><span class="50"><span lang="EN-US"><span>List</span></span></span><span><span>或数组是相同的，因为返回给前台的数据都是</span><span lang="EN-US"><span>JSON</span></span><span>格式的。前台使用</span><span lang="EN-US"><span>JavaScript</span></span><span>处理返回信息的部分更简单，先引入</span></span><span class="50"><span lang="EN-US"><span>DWRTree- Loader.js</span></span></span><span><span>，然后把</span></span><span class="50"><span lang="EN-US"><span>TreeLoader</span></span></span><span><span>替换成</span></span><span class="50"><span lang="EN-US"><span>DWRTreeLoder</span></span></span><span><span>即可，如下面的代码所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span class="hl-keyword1"><span lang="EN-US"><span><strong>&nbsp;</strong></span></span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>var</strong></span></span><span lang="EN-US">&nbsp;tree = new Ext.tree.TreePanel('tree', {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>loader: new Ext.tree.DWRTreeLoader({dataUrl: treeNodeManager.getTree})</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>参数依然是</span></span><span class="50"><span lang="EN-US"><span>dataUrl</span></span></span><span><span>，它的值</span></span><span class="50"><span lang="EN-US"><span>treeNodeManager.getTree</span></span></span><span><span>代表的是一个</span><span lang="EN-US"><span>DWR</span></span><span>函数，我们不需要对它进行深入研究，它的内部会自动处理数据之间的对应关系。</span><span lang="EN-US"><span>DWR</span></span><span>有时真的很方便。</span><span lang="EN-US"></span></span></p>
<p class="111"><a name="_Toc216085940"></a><a name="_Toc205277889"></a><a name="ext-ch-10-01-04"></a><span><span><span><span>10.10.4</span></span></span><span><span><span>　</span></span></span><span><span><span>DWRProxy</span></span></span><span><span><span>和</span><span>ComboBox</span></span></span></span></p>
<p class="MsoNormal"><span><span class="50"><span lang="EN-US">DWRProxy</span></span><span>既然可以用在</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>中，那么它也可以为</span><span lang="EN-US"><span>ComboBox</span></span><span>服务，如代码清单</span><span lang="EN-US"><span>10-8</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span>代码清单</span><span lang="EN-US">10-8</span><span>　</span><span class="50"><span lang="EN-US">DWRProxy</span></span><span>与</span><span lang="EN-US"><span>ComboBox</span></span><span>整合</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span><span><span class="hl-keyword1"><span lang="EN-US"><strong>var</strong></span></span><span lang="EN-US">&nbsp;info = Ext.data.Record.create([</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name: 'id', type: 'int'},</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>{name: 'name', type: 'string'}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>]);</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>var store = new Ext.data.Store({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>proxy: new Ext.data.DWRProxy(infoManager.getItems, true),</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>reader: new Ext.data.ListRangeReader({</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>totalProperty: 'totalSize',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>root: 'data',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>id: 'id'</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}, info)</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span>var combo = new Ext.form.ComboBox({</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>store: store,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>displayField: 'name',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>valueField: 'id',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>triggerAction: 'all',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>typeAhead: true,</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>mode: 'remote',</span></span></span></p>
<p class="a1"><span><span lang="EN-US"><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>emptyText: '</span></span><span>请选择</span><span lang="EN-US"><span>',</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>selectOnFocus: true</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>});</span></span></p>
<p class="a1"><span lang="EN-US"><span>combo.render(<span class="hl-string1"><span><strong>'combo'</strong></span></span>);</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>我们既可以用</span></span><span class="50"><span lang="EN-US"><span>mode:'remote'</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>triggerAction:'all'</span></span></span><span><span>在第一次选择时读取数据，也可以设置</span></span><span class="50"><span lang="EN-US"><span>mode:'local'</span></span></span><span><span>，然后手工操作</span></span><span><span class="50"><span lang="EN-US">store.load</span></span><span lang="EN-US">()</span></span><span><span>并读取数据。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>DWR</span></span><span>要比</span><span lang="EN-US"><span>Json-lib</span></span><span>方便得多，而且</span><span lang="EN-US"><span>DWR</span></span><span>返回的数据可以直接作为</span><span lang="EN-US"><span>JSON</span></span><span>使用，使用</span><span lang="EN-US"><span>Json-lib</span></span><span>时还要面对无休无止的循环引用。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>这次的示例稍微复杂一些，因为包括依赖</span><span lang="EN-US"><span>jar</span></span><span>包、</span><span lang="EN-US"><span>class</span></span><span>、</span><span lang="EN-US"><span>XML</span></span><span>和</span><span lang="EN-US"><span>JSP</span></span><span>，所以示例单独放在</span><span lang="EN-US"><span>10.store/dwr2/</span></span><span>下，请将它们复制到</span><span lang="EN-US"><span>tomcat</span></span><span>的</span><span lang="EN-US"><span>webapps</span></span><span>下，然后再使用浏览器访问。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085941"></a><a name="_Toc205277890"></a><a name="ext-ch-10-02"></a><span><span><span><span lang="EN-US"><span>10.11</span></span></span></span><span><span><span>　</span><span lang="EN-US"><span>localXHR</span></span></span></span><span><span><span>支持本地使用</span></span><span lang="EN-US"><span>Ajax</span></span></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>Ajax</span></span><span>是不能在本地文件系统中使用的，必须把数据放到服务器上。无论是</span><span lang="EN-US"><span>IIS</span></span><span>、</span><span lang="EN-US"><span>Apache</span></span><span>、</span><span lang="EN-US"><span>&nbsp;Tomcat</span></span><span>，还是你熟悉的其他服务器，只要支持</span><span lang="EN-US"><span>HTTP</span></span><span>协议，就可以使用</span><span lang="EN-US"><span>EXT</span></span><span>中的</span><span lang="EN-US"><span>Ajax</span></span><span>。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>至于本地为何不能用</span><span lang="EN-US"><span>Ajax</span></span><span>，主要是因为</span><span lang="EN-US"><span>Ajax</span></span><span>要判断</span><span lang="EN-US"><span>HTTP</span></span><span>响应返回的状态，只有</span></span><span class="50"><span lang="EN-US"><span>status=200</span></span></span><span><span>时才认为这次请求是成功的。所以，</span><span lang="EN-US"><span>localXHR</span></span><span>做的就是强行修改响应状态，让</span><span lang="EN-US"><span>Ajax</span></span><span>可以继续下去。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>下面我们来分析一下</span><span lang="EN-US"><span>localXHR</span></span><span>的源代码。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>加入了一个</span></span><span class="50"><span lang="EN-US"><span>forceActiveX</span></span></span><span><span>属性，默认是</span></span><span class="50"><span lang="EN-US"><span>false</span></span></span><span><span>，它用来控制是否强制使用</span></span><span class="50"><span lang="EN-US"><span>activex</span></span></span><span><span>，</span></span><span class="50"><span lang="EN-US"><span>activex</span></span></span><span><span>是在</span><span lang="EN-US"><span>IE</span></span><span>下专用的。</span><span lang="EN-US"></span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>修改</span></span><span class="50"><span lang="EN-US"><span>createXhrObject</span></span></span><span><span>函数，只是在最开始处加了一条判断语句，如下所示。</span><span lang="EN-US"></span></span></p>
<p class="af4"><span class="hl-keyword1"><span lang="EN-US"><strong><span>&nbsp;</span></strong></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>if</strong></span></span>(Ext.isIE7 &amp;&amp; !!<span class="hl-keyword1"><span><strong>this</strong></span></span>.forceActiveX){<span class="hl-keyword1"><span><strong>throw</strong></span></span>(<span class="hl-string1"><span><strong>"IE7forceActiveX"</strong></span></span>);}<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a2"><span lang="EN-US"><span>q<span>&nbsp;&nbsp;&nbsp;</span></span></span><span><span>增加了</span></span><span class="50"><span lang="EN-US"><span>getHttpStatus</span></span></span><span><span>函数，这是为了处理</span><span lang="EN-US"><span>HTTP</span></span><span>的响应状态，如代码清单</span><span lang="EN-US"><span>10-9</span></span><span>所示。</span><span lang="EN-US"></span></span></p>
<p class="ae"><span><span><span class="5"><span>代码清单</span><span>10-9</span></span><span>　处理</span><span lang="EN-US"><span>HTTP</span></span><span>响应状态</span><span lang="EN-US"></span></span></span></p>
<p class="a1"><span lang="EN-US"><span>getHttpStatus:&nbsp;<span class="hl-keyword1"><span><strong>function</strong></span></span>(reqObj){</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>var</strong></span></span>&nbsp;statObj = {</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>status:0</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>,statusText:<span class="hl-string1"><span><strong>''</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>,isError:<span class="hl-keyword1"><span><strong>false</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>,isLocal:<span class="hl-keyword1"><span><strong>false</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>,isOK:<span class="hl-keyword1"><span><strong>false</strong></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>};</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>try</strong></span></span>&nbsp;{</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>if</strong></span></span>(!reqObj)<span class="hl-keyword1"><span><strong>throw</strong></span></span>(<span class="hl-string1"><span><strong>'noobj'</strong></span></span>);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.status = reqObj.status || 0;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.isLocal = !reqObj.status &amp;&amp; location.protocol ==&nbsp;<span class="hl-string1"><span><strong>"file:"</strong></span></span>&nbsp;||</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Ext.isSafari &amp;&amp; reqObj.status == undefined;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.statusText = reqObj.statusText ||&nbsp;<span class="hl-string1"><span><strong>''</strong></span></span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.isOK = (statObj.isLocal ||</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>(statObj.status &gt; 199 &amp;&amp; statObj.status &lt; 300) ||</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.status == 304);</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}&nbsp;<span class="hl-keyword1"><span><strong>catch</strong></span></span>(e){</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-comment1"><span><em>//status may not avail/valid yet.</em></span></span></span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>statObj.isError =&nbsp;<span class="hl-keyword1"><span><strong>true</strong></span></span>;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span>}</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span><span>&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="hl-keyword1"><span><strong>return</strong></span></span>&nbsp;statObj;</span></span></span></p>
<p class="a1"><span lang="EN-US"><span>},</span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>它为状态增添了更多语义，</span></span><span class="50"><span lang="EN-US"><span>status</span></span></span><span><span>表示状态值，</span></span><span class="50"><span lang="EN-US"><span>statusText</span></span></span><span><span>表示状态描述，</span></span><span class="50"><span lang="EN-US"><span>isError</span></span></span><span><span>表示是否有错误，</span></span><span class="50"><span lang="EN-US"><span>isLocal</span></span></span><span><span>表示是否在本地进行</span><span lang="EN-US"><span>Ajax</span></span><span>访问，</span></span><span class="50"><span lang="EN-US"><span>isOK</span></span></span><span><span>表示操作是否成功。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>判断</span></span><span class="50"><span lang="EN-US"><span>isLocal</span></span></span><span><span>是否为本地的有两种方法：</span></span><span class="50"><span lang="EN-US"><span>reqObj</span></span></span><span><span>没有</span></span><span class="50"><span lang="EN-US"><span>status</span></span></span><span><span>，而且请求协议是</span></span><span class="50"><span lang="EN-US"><span>file:</span></span></span><span><span>；浏览器是</span><span lang="EN-US"><span>Safari</span></span><span>，而且</span></span><span class="50"><span lang="EN-US"><span>reqObj.status</span></span></span><span><span>没有定义。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>statObj</span></span></span><span><span>中的</span></span><span class="50"><span lang="EN-US"><span>isOK</span></span></span><span><span>属性用来判断此次请求是否成功。判断请求是否成功的条件很多，例如：</span></span><span class="50"><span lang="EN-US"><span>isLocal</span></span></span><span><span>的属性为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>、响应状态值在</span><span lang="EN-US"><span>199~300</span></span><span>之间、响应状态值是</span><span lang="EN-US"><span>304</span></span><span>等。如果处理过程中出现了异常，就会将</span></span><span class="50"><span lang="EN-US"><span>isError</span></span></span><span><span>属性设置为</span></span><span class="50"><span lang="EN-US"><span>true</span></span></span><span><span>，最后会把配置好的</span></span><span class="50"><span lang="EN-US"><span>statObj</span></span></span><span><span>对象返回，等待下一个步骤的处理。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span lang="EN-US"><span>localXHR.js</span></span><span>对</span></span><span class="50"><span lang="EN-US"><span>handleTransactionResponse</span></span></span><span><span>函数进行了简化。因为增加的</span></span><span class="50"><span lang="EN-US"><span>getHttpStatus</span></span></span><span><span>函数很好地封装了与请求相关的各种状态信息，所以在</span></span><span class="50"><span lang="EN-US"><span>handleTransactionResponse</span></span></span><span><span>函数中我们不会看到让人头晕目眩的响应状态代码。取而代之的是</span></span><span class="50"><span lang="EN-US"><span>isError</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>isOK</span></span></span><span><span>这些更容易理解的属性，</span></span><span class="50"><span lang="EN-US"><span>localXHR.js</span></span></span><span><span>直接使用这些属性来处理响应。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span class="50"><span lang="EN-US"><span>createResponseObject</span></span></span><span><span>函数被大大强化了。其实前半部分都是一样的，</span></span><span class="50"><span lang="EN-US"><span>localXHR.js</span></span></span><span><span>中对</span></span><span class="50"><span lang="EN-US"><span>isLocal</span></span></span><span><span>做了大量的处理，响应中的</span></span><span class="50"><span lang="EN-US"><span>responseText</span></span></span><span><span>可以从连接中获得。如果需要</span><span lang="EN-US"><span>XML</span></span><span>，它就使用</span></span><span class="50"><span lang="EN-US"><span>ActiveXObject("Microsoft.XMLDOM")</span></span></span><span><span>或</span></span><span><span class="50"><span lang="EN-US">new DOMParser</span></span><span lang="EN-US">()</span></span><span><span>把</span></span><span class="50"><span lang="EN-US"><span>responseText</span></span></span><span><span>解析成</span><span lang="EN-US"><span>XML</span></span><span>放到</span></span><span class="50"><span lang="EN-US"><span>response</span></span></span><span><span>里，响应状态也是重新计算的，这样就能让</span><span lang="EN-US"><span>Ajax</span></span><span>正常调用了。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>最后处理的是</span></span><span class="50"><span lang="EN-US"><span>asyncRequest</span></span></span><span><span>函数，如果在异步请求时出现异常，就调用</span></span><span class="50"><span lang="EN-US"><span>handleTransac- tionResponse</span></span></span><span><span>返回响应，然后根据各种情况稍微修改</span></span><span class="50"><span lang="EN-US"><span>header</span></span></span><span><span>属性。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>我们来看看下面这行代码：</span><span lang="EN-US"></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="a1"><span lang="EN-US"><span><span>Ext.lib.Ajax.forceActiveX = (document.location.protocol ==&nbsp;<span class="hl-string1"><span><strong>'file:'</strong></span></span>);<span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span></span></span></span></p>
<p class="af4"><span lang="EN-US"><span>&nbsp;</span></span></p>
<p class="MsoNormal"><span><span>如果协议是</span></span><span class="50"><span lang="EN-US"><span>file:</span></span></span><span><span>，就强制使用</span></span><span class="50"><span lang="EN-US"><span>activex</span></span></span><span><span>。</span><span lang="EN-US"></span></span></p>
<p class="11"><a name="_Toc216085942"><span lang="EN-US"><span>10.12</span></span></a><span><span><span>　本章小结</span></span></span></p>
<p class="MsoNormal"><span><span>本章系统地讨论了</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>包中的各个类的功能和使用方式，还涉及如何将</span><span lang="EN-US"><span>EXT</span></span><span>与</span><span lang="EN-US"><span>DWR</span></span><span>通过自定义的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>相结合的示例。我们介绍了如何使用</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Connection</span></span></span><span><span>与后台进行数据交互，还专门介绍了它的子类</span></span><span class="50"><span lang="EN-US"><span>Ext.Ajax</span></span></span><span><span>，并讨论了</span><span lang="EN-US"><span>EXT</span></span><span>中</span><span lang="EN-US"><span>Ajax</span></span><span>的应用以及在回调函数中使用</span></span><span class="50"><span lang="EN-US"><span>scope</span></span></span><span><span>或</span></span><span><span class="50"><span lang="EN-US">createDelegate</span></span><span lang="EN-US">()</span></span><span><span>解决</span></span><span class="50"><span lang="EN-US"><span>this</span></span></span><span><span>的问题。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>接着详细介绍了类</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Record</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>Ext.data.Store</span></span></span><span><span>的功能和使用方法，这两个类结合起来形成了</span></span><span class="50"><span lang="EN-US"><span>Ext.data</span></span></span><span><span>中的主体数据模型，很多组件（包括</span><span lang="EN-US"><span>Grid</span></span><span>和</span><span lang="EN-US"><span>ComboBox</span></span><span>）都是建立在它们之上的。除此之外，还讨论了常用的</span></span><span class="50"><span lang="EN-US"><span>proxy</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>reader</span></span></span><span><span>、</span></span><span class="50"><span lang="EN-US"><span>store</span></span></span><span><span>：</span></span><span class="50"><span lang="EN-US"><span>SimpleStore</span></span></span><span><span>和</span></span><span class="50"><span lang="EN-US"><span>JsonStore</span></span></span><span><span>，以及它们的应用场景。</span><span lang="EN-US"></span></span></p>
<p class="MsoNormal"><span><span>最后我们介绍了扩展插件</span><span lang="EN-US"><span>localXHR.js</span></span><span>，它可以解决</span><span lang="EN-US"><span>EXT</span></span><span>中</span><span lang="EN-US"><span>Ajax</span></span><span>无法访问本地文件的问题。</span><span lang="EN-GB"></span></span></p>
<p class="MsoNormal"><span lang="EN-GB"><span>&nbsp;</span></span></p>
</p><img src="http://www.cnblogs.com/meetrice/aggbug/1604780.html?type=1" width="1" height="1" alt=""/><p>评论: 1　<a href="http://www.cnblogs.com/meetrice/archive/2009/11/17/1604780.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2009/11/17/1604780.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item><item><title>三款Json查看小工具</title><link>http://www.cnblogs.com/meetrice/archive/2009/10/28/1591277.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Wed, 28 Oct 2009 05:33:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2009/10/28/1591277.html</guid><description><![CDATA[<p>阅读: 323 评论: 0 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2009-10-28 13:33 <a href="http://www.cnblogs.com/meetrice/archive/2009/10/28/1591277.html" target="_blank">原文链接</a></p><p>&nbsp;&nbsp; &nbsp;&nbsp;JSON(JavaScript Object Notation) 是一种轻量级的数据交换格式。易于人阅读和编写。同时也易于机器解析和生成。它基于JavaScript Programming Language, Standard ECMA-262 3rd Edition &ndash; December 1999的一个子集。 JSON采用完全独立于语言的文本格式，但是也使用了类似于C语言家族的习惯（包括C, C++, C#, Java, JavaScript, Perl, Python等）。这些特性使JSON成为理想的数据交换语言。</p>
<div>&nbsp;&nbsp; &nbsp;在使用struts2 json plugin的把相关的数据对象转化为json数据传送给前台页面的时候，往往会因为数据量过多而排查错误过于困难，所以，需要几个查看json数据的工具来帮忙形成Tree而方便浏览数据。</div>
<div><a target="_blank" href="http://www.codeplex.com/JsonViewer"><big><strong>Json Viewe</strong></big></a></div>
<div>&nbsp;&nbsp; &nbsp;这款工具提供了3种选择：</div>
<div>&nbsp;&nbsp; &nbsp;1：是独立的exe文件，可以点击直接查看json对象；</div>
<div>&nbsp;&nbsp; &nbsp;2：Fiddler【一款免费的记录主机HTTP（S）通信的代理（proxy）】 的插件http://www.infoq.com/cn/news/2009/03/fiddler&nbsp;</div>
<div>&nbsp;&nbsp; &nbsp;3：Visual Studio 2005 的插件。</div>
<div>&nbsp;&nbsp; &nbsp;<a target="_blank" href="http://farm4.static.flickr.com/3402/3506539426_7e75e99fe7.jpg?v=0"><img src="http://farm4.static.flickr.com/3402/3506539426_7e75e99fe7.jpg?v=0" /></a></div>
<div><big><strong>Eclipse 的json插件：</strong></big><a target="_blank" href="http://sureshkrishna.wordpress.com/2007/09/24/json2xml-treeviewer-plugin-for-eclipse/"><big><strong>JSON2XML TreeViewer plugin for Eclipse</strong></big></a></div>
<div>&nbsp;&nbsp; &nbsp;这款插件主要功能是把json的数据转换为Json Tree和Xml Tree，在使用eclipse测试代码的时候，把生成的数据直接复制粘贴到这个工具中，免去了打开一个新软件的痛苦，岂不是操作很方便？点击这里<a target="_blank" href="http://sureshkrishna.wordpress.com/2007/09/24/json2xml-treeviewer-plugin-for-eclipse/">下载</a></div>
<div>&nbsp;&nbsp; &nbsp;直接把jar包放到elipse的plugin中就可以了，重启elipse &gt; 点击左下角的show view &gt; 找到 Json analyzer,双击添加 。</div>
<div><a href="javascript:void(0);/*1241580173882*/"><img src="http://farm4.static.flickr.com/3391/3506539418_c8e97ef958.jpg?v=0" /></a></div>
<div><a target="_blank" href="https://addons.mozilla.org/zh-CN/firefox/addon/10869"><big><strong>Firefox的json插件</strong></big></a></div>
<div>&nbsp;&nbsp; &nbsp;有了这个工具，你可以在FF浏览器中像XML文件一样查看JSON，具有代码自动高亮,自动缩进,自动折叠功能.甚至JSON文件中有错误，JSONView仍然可以显示原始代码.</div>
<div>&nbsp;&nbsp; &nbsp;安装了JSONView后，请到http://brh.numbera.com/software/jsonview/example.json查看扩展是否起作用了!如果可以看到折叠树，就代表可以了。</div>
<div>&nbsp;</div>
<div>&nbsp;&nbsp; &nbsp;以上三个工具您可以按需选择，基本可以满足日常的json数据查看了，如果您有更好的工具，请推荐给我！</div><img src="http://www.cnblogs.com/meetrice/aggbug/1591277.html?type=1" width="1" height="1" alt=""/><p>评论: 0　<a href="http://www.cnblogs.com/meetrice/archive/2009/10/28/1591277.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2009/10/28/1591277.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item><item><title>使用Eink显示屏的智能手机</title><link>http://www.cnblogs.com/meetrice/archive/2009/10/23/1588668.html</link><dc:creator>meetrice</dc:creator><author>meetrice</author><pubDate>Fri, 23 Oct 2009 06:42:00 GMT</pubDate><guid>http://www.cnblogs.com/meetrice/archive/2009/10/23/1588668.html</guid><description><![CDATA[<p>阅读: 56 评论: 0 作者: <a href="http://www.cnblogs.com/meetrice/" target="_blank">meetrice</a> 发表于 2009-10-23 14:42 <a href="http://www.cnblogs.com/meetrice/archive/2009/10/23/1588668.html" target="_blank">原文链接</a></p>我非常期待，希望手机制造商尽快推出这样的产品，我会第一个购买！<img src="http://www.cnblogs.com/meetrice/aggbug/1588668.html?type=1" width="1" height="1" alt=""/><p>评论: 0　<a href="http://www.cnblogs.com/meetrice/archive/2009/10/23/1588668.html#pagedcomment" target="_blank">查看评论</a>　<a href="http://www.cnblogs.com/meetrice/archive/2009/10/23/1588668.html#commentform" target="_blank">发表评论</a></p><p><a href="http://job.cnblogs.com/" target="_blank">找优秀程序员，就在博客园</a></p><hr/><p>最新新闻：<br/>· <a href="http://news.cnblogs.com/n/59262/" target="_blank">甲骨文将关闭OpenSSO</a><span style="color:gray">(2010-03-20 23:54)</span><br/>· <a href="http://news.cnblogs.com/n/59261/" target="_blank">专访陈晓薇：九城已重建、我还没想好去哪</a><span style="color:gray">(2010-03-20 22:07)</span><br/>· <a href="http://news.cnblogs.com/n/59260/" target="_blank">[视频]社交媒体不仅仅是一时狂热</a><span style="color:gray">(2010-03-20 21:58)</span><br/>· <a href="http://news.cnblogs.com/n/59259/" target="_blank">Google开出首个1337美刀的Chrome bug奖励支票</a><span style="color:gray">(2010-03-20 21:47)</span><br/>· <a href="http://news.cnblogs.com/n/59258/" target="_blank">著名图像讨论网站4chan创始人披露4chan诞生历史</a><span style="color:gray">(2010-03-20 21:42)</span><br/></p><p>编辑推荐：<a href="http://news.cnblogs.com/n/59093/" target="_blank">[视频]想做你的Code</a><br/></p><p>网站导航：<a href="http://www.cnblogs.com" target="_blank">博客园首页</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/" target="_blank">个人主页</a>&nbsp;&nbsp;<a href="http://news.cnblogs.com" target="_blank">新闻</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/ing/" target="_blank">闪存</a>&nbsp;&nbsp;<a href="http://home.cnblogs.com/group/" target="_blank">小组</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com/q/" target="_blank">博问</a>&nbsp;&nbsp;<a href="http://space.cnblogs.com" target="_blank">社区</a>&nbsp;&nbsp;<a href="http://kb.cnblogs.com" target="_blank">知识库</a></p>]]></description></item></channel></rss>