我們知道,在數(shù)據(jù)庫(kù)中,每個(gè)數(shù)據(jù)表都是為完成不同的目標(biāo)功能而設(shè)計(jì)的,其字段結(jié)構(gòu)因設(shè)計(jì)目標(biāo)不同而各具差異。
當(dāng)需要對(duì)這些異構(gòu)數(shù)據(jù)表做選定字段的查詢操作時(shí),就必須編制不同的程序代碼或者定制不同的查詢表單來(lái)實(shí)現(xiàn)。而如果需要查詢的數(shù)據(jù)表比較多,查詢代碼或表單就會(huì)顯得冗長(zhǎng)而繁雜。
最近,筆者在開(kāi)發(fā)本單位一個(gè)項(xiàng)目管理軟件時(shí),就遇到了類似問(wèn)題。如何用一種通用方法實(shí)現(xiàn)對(duì)異構(gòu)數(shù)據(jù)表的查詢維護(hù),減少程序代碼冗余和系統(tǒng)開(kāi)銷(xiāo),優(yōu)化代碼編制,提高運(yùn)行效率,從而獲取解決此類問(wèn)題的通用途徑。
而后經(jīng)筆者分析,找到了一種可行的解決方案,現(xiàn)拿出來(lái)和讀者一起分享,希望能夠?qū)ψx者有所啟發(fā)和幫助。
筆者采用Delphi及Access作為應(yīng)用軟件制作工具。涉及通信、人才培訓(xùn)、幼兒教育、房地產(chǎn)租賃等15個(gè)服務(wù)行業(yè)。
查詢需求比較簡(jiǎn)單,就是在一個(gè)查詢窗口下,針對(duì)15個(gè)不同行業(yè)類別,結(jié)合其他查詢條件實(shí)施組合查詢。
圖1 查詢?cè)O(shè)計(jì)界面
系統(tǒng)查詢界面設(shè)計(jì)如圖1所示。通過(guò)行業(yè)下拉框,選擇不同行業(yè)(數(shù)據(jù)表)類別,設(shè)計(jì)其他查詢條件的下拉框或輸入框,如所屬單位范圍、類別區(qū)分、當(dāng)前狀態(tài)、單位名稱、項(xiàng)目名稱、項(xiàng)目類別、責(zé)任人等,用戶可以選取和輸入查詢條件,當(dāng)條件發(fā)生變化時(shí)激活查詢。
實(shí)現(xiàn)上述查詢功能一般都會(huì)用到三種數(shù)據(jù)構(gòu)件,一是數(shù)據(jù)表構(gòu)件KaDaoTable或ADOTable,用于定位不同的行業(yè)數(shù)據(jù)表;二是數(shù)據(jù)顯控構(gòu)件DBGrid,用于顯示查詢結(jié)果;三是數(shù)據(jù)源構(gòu)件DataSource,用于將數(shù)據(jù)表和數(shù)據(jù)顯控構(gòu)件進(jìn)行關(guān)聯(lián)。
雖然有15個(gè)行業(yè)的數(shù)據(jù)表,但我們不需要在系統(tǒng)中放置這么多的數(shù)據(jù)表構(gòu)件,而只需要設(shè)置1個(gè)KaDaoTable或ADOTable數(shù)據(jù)表構(gòu)件,通過(guò)簡(jiǎn)單的SQL語(yǔ)句,在程序中動(dòng)態(tài)進(jìn)行切換就可以了。
行業(yè)競(jìng)爭(zhēng)程度因素(Marketc),通過(guò)Herf i ndahl-Hirschman指數(shù)對(duì)企業(yè)所屬行業(yè)的競(jìng)爭(zhēng)度進(jìn)行檢測(cè)(Kafetzopoulos 和 Psomas 2015)[14]。
數(shù)據(jù)源DataSource構(gòu)件設(shè)置更簡(jiǎn)單,因?yàn)閿?shù)據(jù)表構(gòu)件只有1個(gè),所以只需要在DataSource中靜態(tài)設(shè)置好對(duì)應(yīng)數(shù)據(jù)表構(gòu)件名稱即可。
圖2 DBGrid構(gòu)件欄目結(jié)構(gòu)示例
數(shù)據(jù)顯控構(gòu)件DBGrid的設(shè)置就不一樣了,因?yàn)椴煌袠I(yè)的數(shù)據(jù)表,其字段結(jié)構(gòu)基本上不同,有的甚至差異巨大,與之對(duì)應(yīng)的DBGrid欄目數(shù)據(jù)項(xiàng)也就隨之完全不相同。傳統(tǒng)上可以利用兩種方法實(shí)現(xiàn)顯控:一是靜態(tài)法。即放置多個(gè)DBGrid構(gòu)件,分別對(duì)應(yīng)不同的行業(yè)數(shù)據(jù)表,通過(guò)DBGrid構(gòu)件的圖形化設(shè)計(jì)界面,事先設(shè)計(jì)好顯示欄目結(jié)構(gòu),運(yùn)行時(shí)直接調(diào)用(如圖2)。
二是動(dòng)態(tài)法。即編制程序代碼,在系統(tǒng)運(yùn)行過(guò)程中根據(jù)不同行業(yè)表的選擇,動(dòng)態(tài)將需要顯示的數(shù)據(jù)欄目添加到DBGrid構(gòu)件中。
靜態(tài)法的優(yōu)點(diǎn)是幾乎不需要編制程序代碼,但缺點(diǎn)卻顯而易見(jiàn),15個(gè)行業(yè)就需要增加15個(gè)DBGrid構(gòu)件,構(gòu)件冗余度高,系統(tǒng)資源開(kāi)銷(xiāo)大,運(yùn)行效率低;動(dòng)態(tài)法的優(yōu)點(diǎn)正好和靜態(tài)法相反,系統(tǒng)開(kāi)銷(xiāo)小,只需1個(gè)DBGrid構(gòu)件,但需要我們編制相應(yīng)程序代碼進(jìn)行顯示控制。以下是動(dòng)態(tài)添加1個(gè)DBGrid顯示欄目的代碼片斷:
可以想像,動(dòng)態(tài)添加1個(gè)顯示欄目就需要至少6條語(yǔ)句,如果行業(yè)表的數(shù)據(jù)項(xiàng)較多,并且要求顯示的DBGrid欄目也較多時(shí),動(dòng)態(tài)添加DBGrid構(gòu)件顯示欄目的程序代碼會(huì)十分冗長(zhǎng)繁雜。
因此,以上兩種方法要么增加了系統(tǒng)資源開(kāi)銷(xiāo),影響了執(zhí)行效率;要么程序代碼冗長(zhǎng),編制繁雜,達(dá)不到代碼優(yōu)化目標(biāo),都存在這樣那樣的問(wèn)題。那么,有沒(méi)有一種更好的實(shí)現(xiàn)方法呢?答案當(dāng)然是肯定的。
導(dǎo)出方法旨在將顯示欄目結(jié)構(gòu)導(dǎo)出到一個(gè)指定的文件中進(jìn)行保存,導(dǎo)入方法則正好相反,可以導(dǎo)入事先保存的顯示欄目結(jié)構(gòu)文件,用于結(jié)果顯示。有了DBGrid構(gòu)件這兩個(gè)方法支持,同時(shí)針對(duì)DBGrid一些特殊欄目,如序號(hào)、合計(jì)等欄目的特殊應(yīng)用處理,我們自然就有了可行的解決方案。
首先,生成DBGrid顯示欄目結(jié)構(gòu)文件。確定15個(gè)行業(yè)表需要顯示的數(shù)據(jù)字段,通過(guò)DBGrid圖形化界面對(duì)其進(jìn)行編輯,然后針對(duì)每一個(gè)DBGrid設(shè)置一個(gè)“DBGrid顯示欄目生成”按鈕,在其OnClick事件中輸入如下代碼:
運(yùn)行后,分別點(diǎn)擊“DBGrid欄目生成”按鈕,這樣就生成了15個(gè)后綴為tcc的文件,這些文件中存放著15個(gè)行業(yè)的DBGrid數(shù)據(jù)表欄目結(jié)構(gòu),便于后續(xù)動(dòng)態(tài)導(dǎo)入操作。
其次,動(dòng)態(tài)構(gòu)造KaDaoTable或ADOTable數(shù)據(jù)字段結(jié)構(gòu)。主要完成兩個(gè)步驟:一是切換數(shù)據(jù)表構(gòu)件到對(duì)應(yīng)的行業(yè)表;二是創(chuàng)建數(shù)據(jù)表構(gòu)件靜態(tài)字段,便于特殊處理。如前所述,從優(yōu)化的角度考慮,我們只使用了一個(gè)數(shù)據(jù)表構(gòu)件,因此在查詢不同行業(yè)數(shù)據(jù)表時(shí),就必須對(duì)KaDaoTable或ADOTable數(shù)據(jù)表構(gòu)件進(jìn)行切換,這可以通過(guò)編制SQL語(yǔ)句輕松實(shí)現(xiàn)。
此外,在切換到對(duì)應(yīng)行業(yè)表后,還必須動(dòng)態(tài)創(chuàng)建數(shù)據(jù)表靜態(tài)字段結(jié)構(gòu)。靜態(tài)字段結(jié)構(gòu)包括兩個(gè)部分,一是行業(yè)表中自身所具有的字段,也就是常規(guī)字段部分;二是為完成特殊顯控需求而自定義的字段,即特殊字段(Delphi也稱之為計(jì)算字段)部分,如記錄序號(hào)字段等。代碼如下:
圖3 行業(yè)數(shù)據(jù)表字段結(jié)構(gòu)
由以上代碼可見(jiàn),除了個(gè)別特殊字段(如序號(hào))需要命名、賦值及加載外,其他常規(guī)字段生成只需要一條循環(huán)語(yǔ)句即可完成。
這樣,我們就通過(guò)簡(jiǎn)單的程序代碼動(dòng)態(tài)簡(jiǎn)潔地實(shí)現(xiàn)了復(fù)雜的靜態(tài)設(shè)計(jì),如圖4所示。
最后,根據(jù)所選查詢條件實(shí)施查詢。該過(guò)程主要有兩個(gè)步驟:一是選取查詢條件;二是調(diào)入DBGrid顯示欄目結(jié)構(gòu),顯示查詢結(jié)果。代碼如下:
該方法可能只是在實(shí)現(xiàn)異構(gòu)數(shù)據(jù)表查詢維護(hù)中眾多方法的一種,但簡(jiǎn)單可行,它充分利用了DBGrid構(gòu)件方法,將不同數(shù)據(jù)表字段對(duì)應(yīng)的顯示欄目以文件的形式靜態(tài)保存,系統(tǒng)運(yùn)行時(shí)動(dòng)態(tài)調(diào)入,同時(shí),編制少量程序代碼,動(dòng)態(tài)生成個(gè)別特殊字段欄目(如序號(hào)、合計(jì)等),這樣既方便了系統(tǒng)設(shè)計(jì)維護(hù),又簡(jiǎn)化了程序代碼編制,是一種實(shí)現(xiàn)異構(gòu)多表查詢維護(hù)的有效方法,希望通過(guò)此文起到拋磚引玉、舉一反三的作用。