如何提高Visual FoPro的性能

時間:2022-10-08 04:08:00

導語:如何提高Visual FoPro的性能一文來源于網友上傳,不代表本站觀點,若需要原創文章可咨詢客服老師,歡迎參考。

如何提高Visual FoPro的性能

摘要:本文介紹一些實用技巧和技術。如果我們能正確地應用這些技術,就可以大大改進VisualFoxPro的性能,提高數據的訪問速度。

關鍵詞:VisualFoxPro;性能;技術

高性能是MicrosoftFoxPro數據庫管理系統(特別是它的數據庫引擎)的最大特點。Visual

FoxPro關系型數據庫引進了對象模型,提高了引擎的存取速度并增強了客戶/服務器特性,因此整個管理系統的功能變得更加強大。但是,這些強大功能的代價是使管理系統變得更加復雜。因此,一方面,很容易開發出性能穩定、面向對象、使用遠程數據的應用程序,另一方面,也很難避免出現低性能的應用程序。

本文從改善、提高VisualFoxPro性能的目標出發,介紹一些實用技巧和技術。

一、改善本地數據訪問的性能

1.使用索引

Visual

FoxPro中的索引是基于樹的數據結構,因此查詢經過索引的表是很快的。但當表中有較多的索引時,更新表和向表中輸入數據就會變得慢一些,因為

VisualFoxPro需要更新每個索引。通常,只需在用于篩選和聯接的數據上建立索引。

應該避免以FOR<條件>或NOT<條件>這樣的形式建立索引表達式,因為這些表達式無法優化。例如:INDEXONDELETED

()TAGDEL是可以進行Rushmore優化的,但是,INDEXONNOTDELETED()TAG

NOTDEL則不能。在特殊情況下,我們不想包含被刪除的記錄,可以先設置SETDELETEDON,再創建索引,這樣可以加速操作。

此外,注意不要在那些只有少數離散數據中取值的字段(例如邏輯型字段)上建立索引。

2.優化查詢的條件

VisualFoxPro通過查找與篩選表達式左邊相匹配的索引表達式來優化篩選條件。我們經常試圖將索引的標識名與一個篩選表達式相匹配,而

VisualFoxPro無法通過這種方式優化查詢。下面使用的索引是錯誤的:

USECUSTOMERS

INDEXONUPPER(cu_name)TAGname

SELECT*FROMcustomers;

WHEREcu_name="BILL"&&notoptimized.Noindexon"cu_name"

在一個篩選的查詢中正確使用索引的方法是∶

SELECT*FROMcustomersWHEREUPPER(cu_name)="BILL"&&Optimized!

3.使用SYS(3051)函數

SYS(3051)S函數控制從一個記錄(表、索引或備注文件)的鎖定失敗到再次嘗試鎖定它之間的時間間隔,以毫秒為單位,默認值為333

毫秒。

如果在我們的系統中存在大量的鎖定競爭,可以將這個值調大(最大值為

1000),以提高我們應用程序的性能,因為應用程序不會因徒勞鎖定記錄而浪費時間。但是,如果鎖定競爭不多,應將該值調小(最小值為

100),以加速記錄鎖定的嘗試。

4.注音標記和機器排序序列

在VisualFoxPro

中,已經改進了查詢包含國際化字符(帶有區分標記的字符)數據的優化方式。但如果我們的索引表達式的結果包含的字符都不帶注音標記(例如B或

M),則查詢還能更快。

非機器排序序列(例如“通用”排序序列)比機器排序序列慢,有下列幾個原因:非機器索引關鍵字的大小是機器索引關鍵字的兩倍,因為必須為每個字符記錄注音信息;為了返回正確的結果,非機器排序序列要使用很多特定的規則來斷定索引的順序。因為機器排序序列更快,所以它通常用于聯接和查找,而其他排序序列用于排序記錄。

5.使事務安排緊湊

事務應該只包含更新數據操作,在事務中包含其他任何操作(如使用我們界面,使用編程結構的CASE、WHILE或IF

語句)都會降低更新數據的效率。

這對于VisualFoxPro

是很重要的,因為使用事務需要鎖定記錄。在事務中以及更新記錄時會鎖定記錄,并且在提交或回滾事務之前不會釋放這些鎖定的記錄。即使我們使用了RLOCK

()或FLOCK(),然后執行UNLOCK,記錄在ENDTRANSACTION或ROLLBACK

語句之前也一直保持鎖定。另外,在追加記錄時需要VisualFoxPro

鎖定標頭(即其他我們可以修改,但不能添加或刪除),并且在事務結束(提交或回滾)之前一直鎖定標頭。因此,在一個高容量多我們的系統中,減少鎖定記錄的時間就變得很關鍵。

6.使用新的數據類型

在VisualFoxPro

中引入了四種新數據類型∶日期時間型、整型、雙精度型和貨幣型。所有這些類型的數據都以二進制數據的形式保存在磁盤上(整型是四字節的二進制數據,其他數據類型是八字節的二進制數據)。

使用這些數據類型有兩個優點:首先,由于在磁盤上保存數據時所占的空間更小(一個八位數的數據若用數值型保存將占用八個字節,而保存為整形只需要四個字節),這樣,從磁盤向內存加載數據和索引時,一次可以加載更多的有用數據,從而提高應用程序的性能。第二個優點是不需要任何的數據轉換。Visual

FoxPro內部將整型數據表示為四字節的二進制值,而數值型數據在磁盤上保存為ASCII碼形式,因此,在每次讀數據時,都必須將ASCII

碼轉換為二進制值,存盤時再轉換回去。由于整型和雙精度型數據(以及日期型和貨幣型數據)不需要這種轉換,所以數據訪問就更快。

在新數據類型中,整型數據對速度的影響最大。要盡量使用整型數據作為主關鍵字和外部關鍵字的值。這樣可以得到更小的DBF

文件,更小的索引,更快的連接。

二、提高遠程數據訪問的性能

在任何后端數據庫中檢索數據是很費時的。為了加快數據的下載(或更新),可使用下面的方法。

1.只下載需要的數據

在一個應用程序的功能單元(比如,表單或報表)中,很少需要訪問表中的所有數據。通過創建遠程視圖,只得到(或更新)我們需要的字段和記錄,就可以減少通過網絡的數據數量。例如,在我們的表單上有四個控件,分別綁定了遠程視圖的字段(客戶標識號、公司名、聯系人和來自客戶表的地址),可使用SELECT

customer_id,company,contact,addressFROMcustomersSELECT則會好得多。

2.使用一個WHERE子句

為了進一步限制下載(或更新)的數據數量,可以使用WHERE子句。對于上面的示例,如果我們只需要西南部的客戶記錄,我們視圖的SELECT

語句可以是:

SELECTcustomer_id,company,contact,addressFROMcustomers

WHEREregion=''''NORTHWEST''''

VisualFoxPro提供的視圖靈活性以及SQLPassThrough技術使我們可以在SELECT、UPDATE和

DELETE等SQL語句的WHERE子句中使用參數。例如,對于上例,我們可以使用參數在運行時刻下載任何地區的信息:

SELECTcustomer_id,company,contact,addressFROMcustomers

WHEREregion=?pcRegion

式中,“pcRegion”是參數的名稱。

3.使用正確的更新條件

視圖設計器中的“更新條件”選項卡允許我們指定視圖中的數據如何被更新(插入和刪除)。在選項卡中的“SQLWHERE

子句包括”部分,我們可以控制UPDATE和DELETE操作中WHERE

子句的內容。這對于在后端控制數據沖突是很關鍵的,對于改善性能也是很重要的。

因為我們向后端更新的字段總是可更新字段的子集(并且一定是視圖中字段總數的子集),在大多數情況下都使用“關鍵字和已修改字段”選項。對于支持時間戳的服務器數據庫,建議使用“關鍵字和時間戳”設置,這種更新方式比用“關鍵字和已修改字段”更快。

4.使用BatchUpdateCount屬性

有些服務器(例如MicrosoftSQLServerServer)允許我們在一個單獨的數據包中發送一批SQL

語句,這個技術加速更新、刪除和插入,因為通過網絡傳送的網絡包的絕對數量減少了,而且服務器數據庫可以成批編譯多個語句而不是單獨編譯。

我們應該對于這個屬性和PacketSize

屬性用不同的值來試驗,以優化我們的更新。可以在“查詢”菜單的“高級選項”對話框中設置該屬性,或者通過DBSETPROP()或

CURSORSETPROP()函數來設置。注意若要使用這個屬性,必須通過調用DBSETPROP()或SQLSETPROP()

函數設置“Transactions”屬性來啟動人工事務。

5.使用PacketSize屬性

PacketSize屬性控制向數據庫服務器傳送和下載的網絡包的大小(按照字節)。它實際上是由ODBC

設置的,并且可以是任何非零值。不同的網絡對該屬性有不同的處理,因此我們應該參閱網絡服務文檔。該屬性的默認值是4096

字節。如果我們的網絡支持更大的數據包,我們可以在每次請求(SELECT、INSERT、UPDATE、DELETE)

時將該屬性值增加以加大網絡吞吐量。

6.使用FetchMemo屬性

FetchMemo屬性控制當從后端取得一個記錄時是否也取得備注和二進制(通用字段)數據。請將該屬性設置為

.F.,這樣,直到真正需要時,才從網絡傳遞數據,從而提高我們的查詢取得數據的速度。

7.在本地機上保存查閱表

在很多情況下,我們的應用程序經常訪問只讀數據。例如,我們的應用程序可能會經常使用一個包括各個公司人員的檔案表,將這些數據保存在本地機上(也就是,不把這些表裝在服務器上),查詢會更快。對于從不更改或很少更改的數據,這個技術會很有用。

8.使用本地規則

幾乎很少有人知道,VisualFoxPro

在本地和遠程視圖中也支持字段級和記錄級規則。這些規則是為了防止與數據或商業規則不符的數據進入數據庫。可以將這些規則放在視圖中,而不僅僅放在后端表中,這樣作的好處是:在無效數據通過網絡傳送之前就可捕獲它。缺點是:這些規則并不自動與后端服務器表上的規則相匹配。因此,如果后端表規則更改了定義,必須人工更改本地定義的視圖中的規則。但是,如果規則很簡單,這也不是一個很大的負擔。另外,規則定義并不經常改變,因此我們也不必擔心會經常更新本地的規則。

三、改造表單對象性能

1.使用數據環境

在“表單設計器”或“報表設計器”中使用數據環境,則打開表和在表間建立關系的速度會比在表單的Load事件中使用USE、SETORDER

和SETRELATION命令快得多。這是因為VisualFoxPro使用底層的系統調用來打開表并建立索引和關系。

2.限制表單集中表單的數目

只有在必須讓一組表單共享一個私有數據工作期時才使用表單集。當我們運行一個表單集時,即使只顯示了表單集的第一個表單,VisualFoxPro

也會創建表單集中所有表單和所有表單中的所有控件,這樣很費時間。如果表單不必共享一個私有數據工作期,這樣做是不必要的。我們應該建立獨立的表單并在需要它們時執行

DOFORM命令。

當然,如果使用了表單集,在訪問表單集中的表單時也會得到些好處。因為所有表單已被加載到內存中了,只是沒有顯示,所以顯示表單會比較快。

3.向頁框中動態加載頁面控件

與表單集類似,當加載頁框時,也加載了每個頁面上的所有控件,從而降低了性能。我們可以創建頁框中每個頁面上控件的類來解決這個問題。使用這個技術,由于直到訪問時才加載頁框中第二及其他頁面上的控件,所以可以加速表單的加載。

4.動態綁定控件與數據

對于一個包含很多與數據綁定的控件的表單,如果我們將綁定的時間延遲到需要的時候,也可以極大地提高表單的性能。

我們可以將表單使用的表和視圖放在數據環境中,這樣當加載表單時表和視圖就打開了。然后,當一個控件(例如組合框)獲得焦點時,我們可以將控件與數據值綁定。

5.使用LockScreen屬性

任何對表單上控件的更改,這個屬性允許我們延遲屏幕刷新。例如,使控件可見或不可見,更改控件顏色,或者在綁定型控件中移動記錄,都可以用這個屬性將它們延遲到所有更改都結束時再刷新,這樣系統的效率會更高。

6.在視圖中使用NoDataOnLoad屬性

視圖的數據環境臨時表對象的NoDataOnLoad屬性與視圖的USE命令的NODATA

子句的作用相同。它打開視圖,但是視圖不取得任何數據。對于本地和遠程視圖都是如此。例如,我們有一個有關客戶信息的表單,它使用一個包含客戶信息的視圖,該視圖使用參數代替

customer_id的具體值。我們可以輸入一個有效的customer_id,然后按下“搜索”按鈕。

這樣做的優點是表單的加載時間大大減少了,因為視圖不給我們帶來任何數據,但是與視圖字段綁定的控件仍是綁定的,因為存在一個打開的工作區(只是其中沒有數據)。

四、完善OLE的性能

在訪問OLE數據之前先運行OLE服務程序。如果與通用字段數據類型相應的服務器(例如MicrosoftExcel或

Word)在客戶機的計算機上已經運行了,則與通用字段綁定的控件通常會獲得更好的性能。

1.自動化的性能

在某些情況下,即使已經運行了一個實例,OLE服務器(例如Microsoft

Excel)仍然經常啟動另一個新的實例。要想改變這種情況(并提高性能),請使用GetObject函數而不要使用CreateObject

函數。例如,下面的調用:x=GetObject(,"excel.Application")總是使用一個已存在的實例,但是,x=

CreateObject("excel.Application")將創建一個新的實例。

如果我們調用了GetObject()函數,而服務器還沒有運行,系統會返回一個錯誤。我們可以俘獲這個錯誤并在錯誤處理程序中調用

CreateObject()函數。

2.不使用MEMLIMIT

VisualFoxPro不能識別MEMLIMIT。在FoxPro中,MEMLIMIT是一個配置設置,指定FoxPro

分配供自己使用的最大內存數。不要使用這個配置設置來限制VisualFoxPro使用的內存數量。如果必要,請使用SYS(3050)函數。

3.“作為圖標”插入對象

當我們將一個OLE對象插入到字段中時,將它作為一個圖標,而不要作為整個的對象。這樣可以減少所需的存儲空間,因為如果Visual

FoxPro同對象一起保存了一個“代表”映象,會占用大量的存儲空間。另外,如使用圖標,繪制該對象的性能也會提高,因為只需重畫圖標。

4.盡量使用人工鏈接和圖象控件

使用人工鏈接對象更快,因為自動鏈接需要的通知時間較長,而且人工鏈接不需要啟動OLE

服務器來繪制對象。如果不需要經常更新一個對象,請使用人工鏈接。

如果在一個應用程序中使用單獨的位圖(如,公司徽標),則圖象控件要比OLE綁定型控件快得多。

5.使用SYS(3050)

這個SYS函數允許我們優化用于數據緩沖的前臺和后臺的內存大小。前臺內存是指當VisualFoxPro

是前臺(活動)應用程序時可用的內存。后臺內存是指當VisualFoxPro是后臺應用程序時可用的內存。

我們可以實際操作這些值,觀察VisualFoxPro為它的數據緩沖占用多少內存,以優化我們的應用程序。

參考文獻:

①胡維華主編《VisualFoxPro程序設計教程》,浙江科學技術出版社,杭州,2000。

②陳華生主編《VisualFoxPro教程》,蘇州大學出版社