microsoftvisualfoxpro的性能调整技巧.docx
《microsoftvisualfoxpro的性能调整技巧.docx》由会员分享,可在线阅读,更多相关《microsoftvisualfoxpro的性能调整技巧.docx(9页珍藏版)》请在冰豆网上搜索。
![microsoftvisualfoxpro的性能调整技巧.docx](https://file1.bdocx.com/fileroot1/2023-2/13/1786a01c-d029-4eb9-b81b-139cc8588966/1786a01c-d029-4eb9-b81b-139cc85889661.gif)
microsoftvisualfoxpro的性能调整技巧
MicrosoftVisualFoxPro的性能调整技巧
MicrosoftVisualFoxPro的性能调整技巧
简介
性能总是Microsoft®FoxPro®数据库管理系统的主要特点之一,尤其是在数据库引擎方面。
在介绍了MicrosoftVisualFoxPro™有关的数据库开发系统以及它相关的对象模型,加强引擎,还有客户端/服务器特性之后,你就会发现整个产品的功能变得越来越强大了。
然而强大的另一面就是产品也变得越来越复杂了。
因此,当开发越来越强劲时,面向对象的应用程序使用远程数据存储器中的数据变得越来越容易了,同时,应用程序也变得更加慢了。
本文要为你介绍一些实践技巧和技术,帮助你改善你的应用程序的性能。
只要你在应用程序中正确的使用了这些技术,你就能够明显改善你的用户界面和数据访问性能。
尽管应用起来只有部分技巧结果比较明显,我们还是希望我们所介绍的能够给你提供有用的信息,帮助你全面改善应用程序的性能。
同时,我们希望你能够把你的意见或经验反馈给我们,这样今后使用VisualFoxPro的开发者要提高应用程序的性能时就能获得更多的帮助,这正如你的前人所做的一样。
硬件配置
在这一部分我们将介绍调整操作系统的技巧,经过调整之后操作系统将会与VisualFoxPro一起工作得更加和谐。
在某些情况下你需要改变硬盘缓存器的值以达到优化性能,从而满足应用程序需要的目的。
MicrosoftWindows95和WindowsNT
在大多数情况下MicrosoftWindows®95和WindowsNT®操作系统与VisualFoxPro一起工作得非常好。
唯一的例外就是在WindowsNTServer上运行VisualFoxPro。
因为WindowsNTServer需要的内存比VisualFoxPro想象的还多,所以VisualFoxPro只能够为自己超支分配内存使用。
为了解决这种情况,你可以用SYS(3050)系统函数来调整VisualFoxPro的内存缓冲区,把它近似调整为它的缺省值的三分之一(详情见内存管理)。
例如,你可以把下面这一行代码添加到启动编码或者是CONFIG.FPW文件中去:
=SYS(3050,VAL(SYS(3050,1,0))/3)
本地数据性能
Rushmore和索引
在MSDNLibrary的VisualFoxProDeveloper‘sGuide中,第十五章“优化应用程序”一文详细地讨论了Rushmore™技术。
下面再补充说明一些技巧。
使用索引
使用索引能够提高数据查询的性能,这是很明显的。
在VisualFoxPro中,索引是树形的数据结构,所以在索引中查询非常快。
VisualFoxPro最独特的方面之一就是支持在索引中使用公式。
大多数数据库管理系统(DBMSs)允许使用一个或更多个字段进行查询,而VisualFoxPro允许在索引中使用任何公式,甚至是用户自定义的函数。
不过你要注意的是,当你往表格中添加了很多的索引时,更新和插入速度会比较慢,因为此时VisualFoxPro要更新每一个索引。
通常,你只需要为那些在过滤器和汇合指令中使用的数据建立索引。
你要避免使用FOR<条件>或者NOT<条件>形式的索引公式,因为这些公式对于索引来说是不可优化的。
例如:
INDEXONDELETED()TAGDEL
是Rushmore可优化的,但是
INDEXONNOTDELETED()TAGNOTDEL
不是。
作为一个查询的特殊情况,当你不想删掉记录时,如果你已经SETDELETEDON,那么使用第一个例子中的索引公式会帮助你加快操作速度。
如果你在公式中使用了一个FOR的句子,VisualFoxPro不会使用索引来达到最优化。
例如
INDEXONORDNUMFORDISCOUNT>10TAGORDDISC
最后,注意不要使用那些只能用离散值的索引(如逻辑字段等)。
何时进行查询Rushmore优化?
什么时候对VisualFoxPro表格进行的查询或者过滤要用Rushmore优化,以及什么时候只是需要部分地进行优化,这些问题都很重要。
VisualFoxPro用Rushmore技术来优化过滤条件,它会找寻符合过滤器左边表达式的索引关键表达式。
通常,开发者们会错误地试图把一个索引的标记名与一个过滤器的表达式的相匹配,这样只会发现VisualFoxPro不能够用这种方法进行优化。
以下是一个错误地使用了索引的例子:
USECUSTOMER
INDEXONUPPER(contact)TAGname
SELECT*FROMcustomer;
WHEREcontact="BILL"&¬optimized.Noindexon"contact"
以下是在过滤查询中正确利用索引的方法:
SELECT*FROMcustomerWHEREUPPER(contact)="BILL"&&Optimized!
你还可以用SYS(3054)函数来决定Rushmore查询优化的等级。
SYS(3054)可以显示也可以不显示查询的Rushmore优化等级。
SYS(3054,1)表示显示Rushmore优化的等级,而SYS(3054,0)则表示不显示Rushmore优化的等级。
数据库引擎性能特性
主索引和侯选的索引
在FoxPro2.x中,用唯一的ID号来增加记录的典型技术就是在你的关键字段中建立一个索引,要增加记录时就运行一个搜索程序来查看这个ID号是否已经被使用了。
虽然这个方法已经比较快了,但是它还不是最理想的。
用Primary和Candidate关键字插入(或者更新)VisualFoxPro表格中,这种方法是由数据库引擎验证的唯一方法,它用于比较低的级别中,速度非常快。
用可区别的标记来提高性能
在VisualFoxPro中,我们改进了查找具有通用特征(指那些有可区别标记的特征)的数据的方法。
如果你的索引表达式的结果不支持可区别的标记(如B或M),查找会快一些。
Non-Machine比较顺序
non-Machine比较顺序(如General)比Machine比较顺序慢的原因有两点:
Non-Machine的索引关键字比Machine的索引关键字长一倍,因为它们要包含可区别的信息。
Non-Machine比较用了许多特别的规则来为特征值建立索引,这样它才能返回正确的结果。
因为Machine比较顺序相对来说要快一些,所以它通常用于连接和查找,而其他的比较顺序通常用来为记录排序。
注意:
VisualFoxPro利用的索引仅仅是用SETCOLLATE当前的设置来建立的。
因此,典型的解决方法是在主要的搜索和分类字段中有两个索引:
SETCOLLATETO"GENERAL"
INDEXONlastnameTAGlastname&&sortindex
SETCOLLATETO"MACHINE"
INDEXONlastnameTAG_lastname&&seek/selectindex
如果你想要用相对来说比较快的Machine索引来对字段进行查找,选择或者连接,请在进行之前使用SETCOLLATETO"MACHINE"。
Rushmore会使用在Machine比较顺序中建立的索引,查找和选择/连接都非常快。
用SQLSELECT
如果在Machine比较顺序中完成了一个SQLSELECT,那么任何ORDERBY或者GROUPBY都可以用Machine比较顺序。
如果你要用non-Machine比较顺序为结果记录排序,你可以在这个比较顺序中完成SELECT,当然这样做比较慢,也可以分两步把它完成:
第一步:
用"Machine"比较顺序来选择记录。
SETCOLLATETO"MACHINE"&&useonly‘machine‘indexes
SELECT*FROMtableINTOCURSORtemp1WHERElastname="Müller"
第二步:
用"General"比较顺序为记录排序。
SETCOLLATETO"GENERAL"&&useonly‘general‘indexes
SELECT*FROMtemp1INTOTABLEoutputORDERBYlastname
新数据类型
我们在VisualFoxPro中引进了几个新的数据类型:
DateTime,Integer,Double,和Currency。
所有这些类型的数据在硬盘上将存为二进制数据(其中Integer是一个四个字节的二进制值,其他的是八个字节的二进制值)。
这样做有两个优点。
第一个优点是,因为存储在硬盘上的数据量比较小(一个八位的数作为Numeric来存储要占八个字节,而作为Integer来存储则只要四个字节),所以从硬盘往内存里调数据和索引时,一次能够调更多的数据到内存页中去,这样速度就会比较快一些。
第二个优点是,无须进行数据的传送。
在内部,如果VisualFoxPro把整数看作四个字节的二进制值,那么需要把它转换为数字才能以ASCII码数据的形式存储在硬盘中。
因而,每一次读取数据都必须先从ASCII码转换成为二进制,然后再转换回去。
有了Integers,Doubles,DateTimes,和Currency几种数据类型,这种转换就不必要了,对数据的访问自然就快了很多。
在新的数据类型中,Integer对速度的影响最大。
因此,只要有可能,尽量地把主要的和外来的关键值设置为Integer。
好处就是:
.DBF文件更小了,索引更小了,而连接就更快了(这也许才是最重要的)。
缓冲和事务处理
事务处理必须简短。
看看下面这个例子:
BEGINTRANSACTION
DOFORMBIGFORMTOnResult
IFnResult=IDCOMMIT
ENDTRANSACTION
ELSE
ROLLBACK
ENDIF
上面这个例子说明了什么?
如果你认为这是一个操作的恰当的事务处理的封装,的确如此。
但是,事务处理仅仅用于限制数据的更新。
如果你做的不仅仅是这些(如涉及用户界面甚至编程的概念像CASE,WHILE,或IF语句等),那么在实际的数据更新过程中效率就会变得很低。
很明显,这是因为在VisualFoxPro中如果要使用事务处理就要求锁住记录。
在事务处理和记录更新的过程中,记录被锁住,一直要等到事务处理被委托或者是反转才能够解开。
即使你在UNLOCK之后说明了要RLOCK()或者FLOCK(),记录也一直被锁死着,直到ENDTRANSACTION或者ROLLBACK出现才会改变。
进一步说,把记录悬挂起来也要求VisualFoxPro要把头文件锁住,直到事务处理完成之后才能够解锁。
(被委托或者是反转)。
因此,在一个大的,多用户的系统中,减少记录被锁死的持续时间是很关键的。
所以在上面这个例子中一个更加适当的应用程序是:
*SavemethodfromthecmdSavecommandbutton.
BEGINTRANSACTION
UPDATEPRODUCTSSETreorder_amt=0;
WHEREdiscontinued=.T.
ENDTRANSACTION
使用SYS(3051)
这个SYS函数控制时间的数量,精度达到毫秒级,经过一次不成功的锁定尝试之后,VisualFoxPro在再次试图锁定一个记录,表格,索引,或备忘录之前会一直等待。
缺省值是333毫秒。
如果在你的数据库文件中有许多锁定竞争,你只要把这个值调大(最大是1000),就能够改善你的应用程序的性能。
这样你的应用程序就不会把时间浪费在快速通过网络进行锁定上了。
不过,如果不希望锁定竞争太高,你就要把这个值调低(最小值是100),这样锁定操作就会更快一些。
远程数据性能
从任何后端数据库中检索获得数据都是很耗费时间的。
为了从一个服务器数据库中检索数据,以下几个步骤是必须的:
客户端向后端服务器数据库提出查询。
服务器分析并且编辑查询条件。
生成结果集。
服务器通报客户端结果已经完成。
客户端通过网络从服务器上获得数据。
为了加快数据的检索(或更新)过程要用到许多技术。
只检索你需要的数据
一般来说,应用程序中的一个函数单元(在大部分情况下是一个表单或者报表)要访问表格中所有的数据只是特殊情况。
建立一个远程视图,仅仅获取(或者更新)你所需要的字段和行,这样通过线路所传送大量数据的情况就会大大改善。
例如,如果你已经建立了一个远程视图,它与一个表单的四个控件绑定在一起(如客户表格中的客户标识号,公司名,联系方式,地址等),用这样一个SELECT语句来执行视图,如:
SELECT*FROMcustomers
效率会很低,因为你检索了大量不做要求的字段。
如果用下面这个SELECT语句来执行视图,效果会好一些。
SELECTcustomer_id,company,contact,addressFROMcustomers
使用WHERE子句
为了限制检索(或者更新)的数据量,适当地使用WHERE子句是有必要的。
我们用同样的例子来进行说明,如果你想知道西北地区的客户情况,使用下面这个SELECT语句:
SELECTcustomer_id,company,contact,addressFROMcustomers
WHEREregion=‘NORTHWEST‘
WHERE子句中的参数
VisualFoxPro中灵活的视图和SQLPassThrough技术能够让你在SQLSELECT,SQLUPDATE,以及SQLDELETE语句的WHERE子句中使用运行时参数。
例如,你能够从任何区中检索信息。
SELECTcustomer_id,company,contact,addressFROMcustomers
WHEREregion=?
pcRegion
这里pcRegion是参数的名字。
如果视图只是用于检索或者再查询必需的信息,这个参数应该有(但不是必须有)。
使用正确的更新准则
ViewDesigner中的UpdateCriteria标签使你能够明确你想要如何把视图中的数据进行更新,插入和删除。
标签中标有“SQLWHEREclauseincludes”的部分能够让你控制UPDATE和DELETE操作中WHERE子句的内容。
这对于控制后端的数据冲突以及性能都十分重要。
考虑到上面所提到的视图并且假设关键字段是customer_id。
假设你想要更新除了关键字段之外的所有字段(这种情况不会经常出现,因为改变关键字段就意味着做一次删除再加上一次插入)—也就是“公司名”,“联系方式”,以及“地址”。
基于你在"SQLWHEREclauseincludes"选项组中的选择,你的WHERE子句可以是表1中的任何形式。
Table1.PossibleWHEREClausesforUpdatesandDeletions
表1。
更新和删除的WHERE子句的可能情况设置
WHERE子句仅仅是关键字段
WHEREOLDVAL(customer_id)=CURVAL(customer_id)关键字段和经过修改的字段(缺省设置)
WHEREOLDVAL(customer_id)=CURVAL(customer_id)AND
OLDVAL(<first_modified_field>)=CURVAL(<first_modified_field>)AND
OLDVAL(<next_modified_field>)=CURVAL(<next_modified_field>)AND
[andsoon.]关键和可更新的字段
WHEREOLDVAL(customer_id)=CURVAL(customer_id)AND
OLDVAL(company)=CURVAL(company)AND
OLDVAL(contact)=CURVAL(contact)AND
OLDVAL(address)=CURVAL(address)关键字和时间标记
WHEREOLDVAL(customer_id)=CURVAL(customer_id)AND
OLDVAL(timestamp)=CURVAL(timestamp)