VFP的數據策略:基礎篇html
做者:Doug Hennig 翻譯:老瓷前端
在VFP應用程序中,有不少方法能夠訪問非VFP數據(如SQL Server):
遠程視圖、SQL Passthrough(SPT--譯者著)、ADO、XML……本文件將探討不一樣機制的利弊,並討論什麼時候適合使用特定策略。咱們還將研究VFP中一種使人興奮的新技術CursorAdapter,它將使訪問遠程數據比早期版本更容易。sql
愈來愈多的VFP開發人員將數據存儲在VFP表之外的其餘地方,如SQL Server或Oracle。這有不少緣由,包括VFP表的脆弱性(感知上和實際上)、安全性、數據庫大小和公司標準。微軟在每個版本中都使非VFP數據的訪問變得更加容易,甚至還鼓勵它在VFP7 CD中加入MSDE(微軟數據引擎,一個免費的、精簡版的SQL Server)。
然而,訪問後端數據庫從未像使用VFP表那樣容易。此外,還可以使用多種機制來執行此操做:數據庫
你應該選擇哪一種機制?答案(正如大多數VFP問題的答案)是「取決於」。它取決於許多因素,包括開發團隊的經驗和專業知識、基礎設施、應用程序的需求、預期的將來需求等等。
讓咱們來看看這些機制中的每一種,包括它們的優勢和缺點,須要注意的一些技術,以及我對每一種機制在總體方案中的位置的見解。咱們還將瞭解我認爲VFP 8中最大的新特性之一CursorAdapter類,以及它如何使經過ODBC、ADO或XML進行遠程數據訪問變得更加容易和一致。編程
與本地視圖同樣,遠程視圖只是在數據庫容器中定義的預約義SQL SELECT語句。不一樣之處在於,遠程視圖經過ODBC(即便它訪問的數據是VFP)而不是本機訪問數據。
可使用create SQL view命令以編程方式建立遠程視圖,也可使用視圖設計器以可視化方式建立遠程視圖。在這兩種狀況下,都須要指定要使用的ODBC鏈接。鏈接能夠是在系統上設置的ODBC數據源(DSN),也能夠是已在同一數據庫中定義的鏈接對象。下面是一個示例,它建立了SQL Server附帶的示例Northwind數據庫的Customers表的遠程視圖(咱們將在示例中普遍使用該數據庫)。這是從GENDBC生成的代碼中摘錄的;實際上還有不少代碼能夠設置鏈接、視圖和字段的各類屬性。後端
CREATE CONNECTION NORTHWINDCONNECTION ; CONNSTRING "DSN=Northwind SQL; UID=sa; PWD=testdb; " + ; "DATABASE=Northwind; TRUSTED_CONNECTION=No" CREATE SQL VIEW "CUSTOMERSVIEW" ; REMOTE CONNECT "NorthwindConnection" ; AS SELECT * FROM dbo.Customers Customers DBSetProp('CUSTOMERSVIEW', 'View', 'UpdateType', 1) DBSetProp('CUSTOMERSVIEW', 'View', 'WhereType', 3) DBSetProp('CUSTOMERSVIEW', 'View', 'FetchMemo', .T.) DBSetProp('CUSTOMERSVIEW', 'View', 'SendUpdates', .T.) DBSetProp('CUSTOMERSVIEW', 'View', 'Tables', 'dbo.Customers') DBSetProp('CUSTOMERSVIEW.customerid', 'Field', 'KeyField', .T.) DBSetProp('CUSTOMERSVIEW.customerid', 'Field', 'Updatable', .F.) DBSetProp('CUSTOMERSVIEW.customerid', 'Field', 'UpdateName', ; 'dbo.Customers.CustomerID') DBSetProp('CUSTOMERSVIEW.companyname', 'Field', 'Updatable', .T.) DBSetProp('CUSTOMERSVIEW.companyname', 'Field', 'UpdateName', ; 'dbo.Customers.CompanyName')
能夠升遷現有應用程序的最簡單方法之一是使用升遷嚮導建立VFP表的SQL Server版本,而後建立新數據庫(例如REMOTE.DBC),並在該數據庫中建立與它們所基於的表同名的遠程視圖。這樣,打開遠程視圖的代碼將與打開本地表的代碼徹底相同,只是您將首先打開其餘數據庫。例如:安全
if oApp.lUseLocalData open database Local else open database Remote endif use CUSTOMERS
若是在窗體和報表的數據環境中使用遊標對象,則須要作一些額外的工做,由於這些對象引用了將視圖拖放到數據環境中時選擇的特定數據庫。要處理此問題,請將相似於如下內容的代碼放入DataEnvironment的BeforeOpenTables方法中:服務器
local loObject for each loObject in This.Objects if upper(loObject.BaseClass) = 'CURSOR' and not empty(loObject.Database) loObject.Database = iif(oApp.lUseLocalData, 'local.dbc', 'remote.dbc') endif upper(loObject.BaseClass) = 'CURSOR' .. next loObject
須要注意的一點是:當您打開一個視圖時,VFP會嘗試在DBC中鎖定該視圖的記錄,即便它只是短暫的。這可能會在繁忙的應用程序中引發爭用,在這些應用程序中,多個用戶可能會嘗試同時打開窗體。儘管有一些解決方法(將DBC複製到本地工做站並使用該方法,或者在VFP 7和更高版本中,使用SET reproces SYSTEM來增長鎖爭用的超時),但這是須要計劃的。
關於偏僻的景色是否是一件好事,有很大的爭議。若是您有興趣閱讀有關論點各方面的內容,請查看如下連接:
http://fox.wikis.com/wc.dll?Wiki~RemoteViews~VFP
http://fox.wikis.com/wc.dll?Wiki~MoreOnRemoteViews~VFP
http://fox.wikis.com/wc.dll?Wiki~Client/ServerDataAccessTechniques~VFP
http://fox.wikis.com/wc.dll?Wiki~Client/ServerTechniquesPerformance~VFP框架
遠程視圖的優勢是:less
遠程視圖的缺點是:
基本上,這歸結爲一個控制問題:遠程視圖使處理後端數據變得容易,但代價是限制了對它們的控制。
遠程視圖實際上只適用於客戶機-服務器、直接鏈接到數據的兩層應用程序。我相信,從長遠來看,若是使用n層設計開發,大多數應用程序將更加靈活、健壯,而且具備更長的保質期,所以,遠程視圖最適合於這樣的狀況:您正在對現有應用程序進行升遷,而不想從新設計/從新開發它,或者您的開發團隊對其餘技術沒有太多經驗。
VFP提供了許多函數,有時稱爲SQL passthrough(或SPT)函數,這些函數容許您訪問後端數據庫。SQLCONNECT()和SQLSTRINGCONNECT()鏈接到後端數據庫引擎;這兩個函數的區別在於,SQLCONNECT()須要現有的ODBC數據源(DSN)在用戶系統上定義,而SQLSTRINGCONNECT()只是將必要的信息直接傳遞給ODBC,即無DSNless鏈接。如您所料,SQLDISCONNECT()從後端斷開鏈接。SQLEXEC()向數據庫引擎發送一個命令(如SQL SELECT語句),一般(但不必定,取決於命令)將返回的結果放入VFP遊標中。
下面是一個打開到Northwind數據庫的鏈接的示例(假設有一個名爲「Northwind」的DSN定義瞭如何鏈接到此數據庫),檢索單個客戶記錄並將其顯示在瀏覽窗口中,而後關閉鏈接。
lnHandle = sqlconnect('Northwind') if lnHandle > 0 sqlexec(lnHandle, "select * from customers where customerid = 'ALFKI'") browse sqldisconnect(lnHandle) else aerror(laErrors) messagebox('Could not connect: ' + laErrors[2]) endif lnHandle > 0
要改用無DSN鏈接,請將SQLCONNECT()語句替換爲如下內容(將服務器名稱、用戶ID和密碼替換爲適當的值):
lnHandle = sqlstringconnect('Driver=SQL Server;Server=(local);' + ; Database=Northwind;uid=sa;pwd=whatever')
DispLogin SQL設置控制ODBC是否顯示登陸對話框。儘管您可能認爲讓ODBC擔憂用戶名和密碼很方便,但您沒法控制對話框的外觀,也沒法控制若是用戶輸入不正確的值會發生什麼。相反,您最好在本身的VFP對話框中向用戶請求適當的信息,而後將該信息傳遞給ODBC。如SQLCONNECT()函數的VFP幫助中所述,應該使用SQLSETPROP()將DispLogin設置爲3。
與其讓每一個須要訪問遠程數據的組件管理本身的ODBC鏈接,不如使用一個對象,該對象的惟一職責是管理鏈接和訪問數據。基於Custom的SFConnectionMgr就是一個例子。它有幾個自定義屬性,其中一些屬性必須先設置,而後才能使用它鏈接到遠程數據源。
屬性 | 描述 | ||
cDatabase | 要鏈接到的數據庫;若是填寫了cDSN,則能夠留空。 | ||
cDriver | 要使用的ODBC驅動程序或OLE DB提供程序;若是填寫了cDSN,則能夠留空。 | ||
cDSN | 要鏈接到的ODBC DSN;留空則使用無DSN鏈接。 | ||
cErrorMessage | 發生任何錯誤的消息。 | ||
cPassword | 數據源的密碼;若是使用受信任的鏈接,則能夠留空。 | ||
cServer | 數據庫所在的服務器;若是填寫了cDSN,則能夠留空。 | ||
cUserName | 數據源的用戶名;若是使用受信任的鏈接,則能夠留空。 | ||
lConnected | 若是已鏈接到數據源則爲.T. 。 |
它有幾個自定義方法:
方法 | 描述 |
Connect | 鏈接到數據源。 |
Disconnect | 斷開數據源鏈接(Destroy調用,也可手動調用)。 |
Execute | 對數據源執行語句。 |
GetConnection | 返回鏈接句柄或ADO鏈接對象。 |
GetConnectionString | 從各類鏈接屬性(受保護)返回鏈接字符串。 |
HandleError | 當發生錯誤時設置cErrorMessage屬性(受保護)。 |
SFConnectionMgr不打算直接使用,但它是SFConnectionMgr ODBC和SFConnectionMgr ADO的子類,分別針對ODBC和ADO。這些子類重寫大多數方法以提供所需的特定行爲。讓咱們看看SFConnectionMgrODBC。
Init方法將當前的dislogin設置保存爲自定義的ndislogin屬性,並將其設置爲3,這樣就永遠不會顯示登陸對話框。
This.nDispLogin = sqlgetprop(0, 'DispLogin') sqlsetprop(0, 'DispLogin', 3) dodefault()
Connect方法檢查咱們是否已經鏈接,而後若是在cDSN屬性中指定了DSN,則使用SQLCONNECT()或生成鏈接字符串並使用SQLSTRINGCONNECT()函數。無論怎樣,若是鏈接成功,nHandle屬性都包含鏈接句柄,而lConnected是.T。若是鏈接失敗,nHandle是0,lConnected是.F,而cErrorMessage包含有關出錯的信息(在HandleError方法中設置,咱們不會查看)。
* 若是還沒有鏈接,請使用無DSN鏈接鏈接到指定的DSN或數據源。 local lcConnString with This if not .lConnected if empty(.cDSN) lcConnString = .GetConnectionString() .nHandle = sqlstringconnect(lcConnString) else .nHandle = sqlconnect(.cDSN, .cUserName, .cPassword) endif empty(.cDSN) * 若是成功鏈接,則設置lConnected標誌,不然獲取錯誤信息。 .lConnected = .nHandle > 0 if not .lConnected .nHandle = 0 .HandleError() endif not .lConnected endif not .lConnected endwith return This.lConnected
GetConnectionString從鏈接屬性的值返回鏈接字符串。
local lcSpecifier, ; lcConnString with This lcSpecifier = iif(upper(.cDriver) = 'SQL SERVER', 'database=', ; 'dbq=') lcConnString = 'driver=' + .cDriver + ';' + ; iif(empty(.cServer), '', 'server=' + .cServer + ';') + ; iif(empty(.cUserName), '', 'uid=' + .cUserName + ';') + ; iif(empty(.cPassword), '', 'pwd=' + .cPassword + ';') + ; iif(empty(.cDatabase), '', lcSpecifier + .cDatabase + ';') + ; 'trusted_connection=' + iif(empty(.cUserName), 'yes', 'no') endwith return lcConnString
Execute方法對數據源執行一個語句(如SQL SELECT命令)。它首先調用Connect以確保咱們有一個鏈接,而後使用SQLEXEC()函數將語句傳遞給數據源。
lparameters tcStatement, ; tcCursor local lcCursor, ; llReturn with This .Connect() if .lConnected lcCursor = iif(vartype(tcCursor) = 'C' and not empty(tcCursor), ; tcCursor, sys(2015)) llReturn = sqlexec(.nHandle, tcStatement, lcCursor) >= 0 if not llReturn .HandleError() endif not llReturn endif .lConnected endwith return llReturn
Disconnect方法斷開與數據源的鏈接,並將nHandle設置爲0,將lConnected設置爲.F。
with This if .lConnected sqldisconnect(.nHandle) .nHandle = 0 .lConnected = .F. endif .lConnected endwith
Destroy只需斷開鏈接並恢復保存的discogin設置。
This.Disconnect() sqlsetprop(0, 'DispLogin', This.nDispLogin) dodefault()
下面是一個示例(取自TestConnMgr.prg),它顯示瞭如何使用SFConnectionMgrODBC。它首先鏈接到SQL Server Northwind數據庫並獲取全部客戶記錄,而後鏈接到Access Northwind數據庫並再次檢索全部客戶記錄。固然,本例使用硬編碼鏈接信息;實際應用程序可能會將此信息存儲在本地表、INI文件或Windows註冊表中,以使其更加靈活。
loConnMgr = newobject('SFConnectionMgrODBC', 'SFRemote') with loConnMgr * 鏈接到SQL Server Northwind數據庫並獲取客戶記錄。 .cDriver = 'SQL Server' .cServer = '(local)' .cDatabase = 'Northwind' .cUserName = 'sa' .cPassword = '' do case case not .Connect() messagebox(.cErrorMessage) case .Execute('select * from customers') browse use otherwise messagebox(.cErrorMessage) endcase * 如今鏈接到Access Northwind數據庫並獲取客戶記錄。 .Disconnect() .cDriver = 'Microsoft Access Driver (*.mdb)' .cServer = '' .cDatabase = 'd:\Program Files\Microsoft Visual Studio\VB98\Nwind.mdb' .cUserName = '' .cPassword = '' do case case not .Connect() messagebox(.cErrorMessage) case .Execute('select * from customers') browse use otherwise messagebox(.cErrorMessage) endcase endwith
使用SPT的優勢是:
使用SPT的缺點是:
與遠程視圖同樣,SPT最適合於與數據直接鏈接的客戶機-服務器兩層應用程序。因爲將現有應用程序轉換爲SPT要比遠程視圖或遊標適配器(稍後咱們將看到)作得更多,SPT最適合於實用程序、簡單應用程序或窄焦點狀況。
OLE DB和ADO是微軟通用數據訪問策略的一部分,在這種策略中,任何類型的數據均可以以任何格式存儲在任何地方,而不只僅是存儲在本地服務器上的關係數據庫中,能夠供任何須要它的應用程序使用。OLE DB提供程序相似於ODBC驅動程序:它們提供了一種標準的、一致的訪問數據源的方法。各類OLE DB提供程序可用於特定的DBMS(SQL Server、Oracle、Access/Jet等),而Microsoft爲ODBC數據源提供OLE DB提供程序。
下面是一個示例(ADOExample.prg),它從Northwind數據庫獲取全部巴西客戶,並顯示客戶ID和公司名稱。注意,鏈接對象處理鏈接(記錄集的ActiveConnection屬性設置爲鏈接對象),而記錄集處理數據。
local loConn as ADODB.Connection, ; loRS as ADODB.Recordset loConn = createobject('ADODB.Connection') loConn.ConnectionString = 'provider=SQLOLEDB.1;data source=(local);' + ; 'initial catalog=Northwind;uid=sa;pwd=' loConn.Open() loRS = createobject('ADODB.Recordset') loRS.ActiveConnection = loConn loRS.LockType = 3 && adLockOptimistic loRS.CursorLocation = 3 && adUseClient loRS.CursorType = 3 && adOpenStatic loRS.Open("select * from customers where country='Brazil'") lcCustomers = '' do while not loRS.EOF lcCustomers = lcCustomers + loRS.Fields('customerid').Value + chr(9) + ; loRS.Fields('companyname').Value + chr(13) loRS.MoveNext() enddo while not loRS.EOF messagebox(lcCustomers) loRS.Close() loConn.Close()
因爲其面向對象的特性和功能,ADO一直是n層開發的首選數據訪問機制(儘管隨着XML變得愈來愈流行,這種狀況正在迅速改變)。與ODBC不一樣,您沒必要直接鏈接到數據源。
有關ADO和在VFP中使用ADO的詳細信息,請參閱John Petersen的「ADO Jumpstart For Visual FoxPro Developers」白皮書,該白皮書可從VFP主頁(http://msdn.microsoft.com/vfoxpro;按照「技術資源」、「技術文章」和「com和ActiveX開發」連接訪問文檔)。
使用ADO的優勢是:
ADO的缺點是:
在其餘組件之間來回傳遞數據時,ADO很容易使用。例如,VFP COM對象的方法能夠很容易地將ADO記錄集返回到Excel VBA代碼,而後該代碼能夠處理和顯示結果。
若是您正在使用n層體系結構設計應用程序,那麼ADO多是一個不錯的選擇,若是您已經熟悉它或者已經爲它準備好了基礎設施。然而,XML正迅速成爲n層應用程序的首選機制,所以我但願ADO在這方面的應用愈來愈少。
XML(可擴展標記語言)並非一種真正的數據訪問機制;它其實是一種傳輸技術。數據被打包成具備結構化格式的文本,而後運到某個地方。然而,因爲XML只是文本,因此它比其餘技術有不少優點(咱們稍後將討論)。
幾年前,微軟「發現」了XML,並從那時起在幾乎全部地方都實現了它。內置在.NET框架ADO.NET中的數據訪問技術以XML爲基礎(事實上,一個簡單的觀點是ADO.NET實際上只是一組包裝類,經過OOP接口公開XML數據)。基於SOAP(簡單對象訪問協議)的Web服務使用XML做爲通訊和數據傳輸的基礎。XML甚至正迅速成爲n層應用程序的首選數據傳輸機制,長期以來,n層應用程序更青睞ADO。
VFP 7添加了幾個與XML一塊兒工做的函數:XMLTOCURSOR(),它將XML轉換爲遊標;CURSORTOXML(),它將執行相反的操做;XMLUPDATEGRAM(),它將updategram(以特定格式表示對數據的更改的XML)從對遊標的更改中生成。下面是一些VFP代碼(取自XMLExample1.prg),展現了VFP如何處理XML:
* 獲取ALFKI客戶的信息並顯示原始XML。 close databases all lcXML = GetCustomerByID('ALFKI') strtofile(lcXML, 'ALFKI.XML') modify file ALFKI.XML erase ALFKI.XML *將其放入遊標中,瀏覽並進行更改,而後查看updategram。 xmltocursor(lcXML, 'CUSTOMERS') set multilocks on cursorsetprop('Buffering', 5) browse lcUpdate = xmlupdategram() strtofile(lcUpdate, 'UPDATE.XML') modify file UPDATE.XML * 經過設置KeyFieldList屬性,updategram將只包含key和changed字段。 cursorsetprop('KeyFieldList', 'cust_id') lcUpdate = xmlupdategram() strtofile(lcUpdate, 'UPDATE.XML') modify file UPDATE.XML erase UPDATE.XML close databases all * 此函數將指定的客戶記錄返回爲XML。 function GetCustomerByID(tcCustomerID) local lcXML open database (_samples + 'data\testdata') select * from customer where cust_id = tcCustomerID into cursor Temp cursortoxml('Temp', 'lcXML', 1, 8, 0, '1') use in Temp use in Customer return lcXML
注意,在版本8以前,雖然VFP能夠建立一個XML updategram,但它沒有一個簡單的方法來使用它(即,更新VFP表)。Visual FoxPro MVP Alex Feldstein爲此編寫了一個例程(http://fox.wikis.com/wc.dll?Wiki~XMLUpdateGramParse),但在VFP 8中,可使用新的XMLAdapter類的實例來完成此操做(咱們將在「VFP:Advanced中的數據策略」文檔中查看該類)。
下面是一個示例(XMLExample2.prg),它使用SQLXML經過Web服務器從SQL Server獲取客戶記錄(咱們將在高級篇中更詳細地討論SQLXML),而後將更改發送回。
* 獲取ALFKI客戶的信息並顯示原始XML。 close databases all lcXML = GetNWCustomerByID('ALFKI') strtofile(lcXML, 'ALFKI.XML') modify file ALFKI.XML erase ALFKI.XML * 將其放入遊標中,瀏覽並進行更改。 xmltocursor(lcXML, 'CUSTOMERS') cursorsetprop('KeyFieldList', 'customerid') set multilocks on cursorsetprop('Buffering', 5) browse * 獲取updategram並將更改保存到SQL Server。 lcUpdate = xmlupdategram() SaveNWCustomers(lcUpdate) use * 此函數使用SQLXML將指定的客戶記錄獲取爲XML。 function GetNWCustomerByID(tcCustomerID) local loXML as MSXML2.XMLHTTP loXML = createobject('MSXML2.XMLHTTP') loXML.open('POST', 'http://localhost/northwind/template/ ' + ; 'customersbyid.xml?customerid=' + tcCustomerID, .F.) loXML.setRequestHeader('Content-type', 'text/xml') loXML.send() return loXML.responseText * 此函數使用SQLXML將指定的客戶記錄獲取爲XML。 function SaveNWCustomers(tcDiffGram) local loDOM as MSXML2.DOMDocument, ; loXML as MSXML2.XMLHTTP loDOM = createobject('MSXML2.DOMDocument') loDOM.async = .F. loDOM.loadXML(tcDiffGram) loXML = createobject('MSXML2.XMLHTTP') loXML.open('POST', 'http://localhost/northwind/', .F.) loXML.setRequestHeader('Content-type', 'text/xml') loXML.send(loDOM)
使用XML有不少好處:
使用XML還有一些缺點:
XML有不少優勢,包括存儲配置設置、在應用程序組件之間傳遞少許數據、在備註字段中存儲結構化數據等等,XML很是適合於n層應用程序,由於它易於傳輸(在組件之間或穿牆)和轉換到數據集(如VFP遊標)或從中轉換。使用XML Updategrams(和更新的Diffgrams),能夠限制傳輸的數據量。若是您正在啓動新的n層項目,這顯然是要使用的數據訪問機制。
你可能注意到的一點是,咱們所研究的每一種機制都與其餘機制徹底不一樣。這意味着每種機制都有一個新的學習曲線,將現有應用程序從一種機制轉換爲另外一種機制是一項很是重要的任務。
在我看來,CursorAdapter是VFP 8中最大的新特性之一。我以爲他們這麼酷的緣由是:
這是最後一點的例子。假設您有一個應用程序使用帶有CursorAdapter的ODBC來訪問SQL Server數據,出於某種緣由,您但願改成使用ADO。您只需更改CursorAdapters的DataSourceType並更改到後端數據庫的鏈接,就完成了。應用程序中的其餘組件既不知道也不關心這一點;它們仍然看到同一個遊標,而無論用於訪問數據的機制如何。
咱們將仔細查看高級文檔中的CursorAdapter。不過,在此期間,這裏有一個示例(CursorAdapterExample.prg),它從Northwind數據庫的Customers表中爲巴西客戶獲取某些字段。遊標是可更新的,所以若是您在遊標中進行了更改,請將其關閉,而後再次運行程序,您將看到您的更改已保存到後端。
local loCursor as CursorAdapter, ; laErrors[1] loCursor = createobject('CursorAdapter') with loCursor .Alias = 'Customers' .DataSourceType = 'ODBC' .DataSource = sqlstringconnect('driver=SQL Server;' + ; 'server=(local);database=Northwind;uid=sa;pwd=;trusted_connection=no') .SelectCmd = "select CUSTOMERID, COMPANYNAME, CONTACTNAME " + ; "from CUSTOMERS where COUNTRY = 'Brazil'" .KeyFieldList = 'CUSTOMERID' .Tables = 'CUSTOMERS' .UpdatableFieldList = 'CUSTOMERID, COMPANYNAME, CONTACTNAME' .UpdateNameList = 'CUSTOMERID CUSTOMERS.CUSTOMERID, ' + ; 'COMPANYNAME CUSTOMERS.COMPANYNAME, CONTACTNAME CUSTOMERS.CONTACTNAME' if .CursorFill() browse else aerror(laErrors) messagebox(laErrors[2]) endif .CursorFill() endwith
CursorAdapter的優勢本質上是全部其餘技術的結合。
CursorAdapter沒有太多缺點:
由於CursorAdapter建立VFP遊標,因此您不太可能在n層應用程序的中間層使用它們。然而,在UI層中,我看到CursorAdapter替換了全部遠程數據訪問的其餘技術,甚至在未來可能會被升級的新應用程序中替換了Cursor。
本文討論了ODBC(不管是遠程視圖仍是SQL Passthrough)、ADO和XML做爲訪問非VFP數據(如SQL Server或Oracle)的方法的優缺點。一般,您應該爲特定應用程序選擇哪一種機制取決於許多因素。然而,在VFP 8中使用新的CursorAdapter技術能夠更容易地過渡到遠程數據訪問,而且在須要時更容易在機制之間切換。
在「VFP的數據策略:高級篇」文檔中,咱們將詳細討論CursorAdapter類,查看使用ODBC、ADO和XML訪問本機數據或非VFP數據的細節。咱們還將研究如何建立可重用的數據類,並討論如何在報表中使用CursorAdapter。
Doug Hennig是Stonefield Systems Group Inc.的合做夥伴。他是獲獎的Stonefield數據庫工具包(SDT)的做者和獲獎的Stonefield查詢的共同做者。他是《黑客視覺FoxPro 7.0指南》的合著者(與Tamar Granor、Ted Roche和Della Martin一塊兒)和《視覺FoxPro 7.0的新特性》的合著者(與Tamar Granor和Kevin McNeish一塊兒),均來自Hentzenwerke出版社,在Pinnacle Publishing的Pros Talk VisualFoxPro系列中,「VisualFoxPro數據字典」的做者。他在FoxTalk上寫了每個月的「可重用工具」專欄。他是《黑客指南》和《基礎知識》的技術編輯,這兩本書都來自亨森沃克出版社。自1997年以來,道格在每次微軟FoxPro開發者大會(DevCon)以及北美各地的用戶團體和開發者大會上都發表過演講。他是微軟最有價值的專業人士(MVP)和認證專業人士(MCP)。