方錦文,童樺茜
(1.桂林電子科技大學信息科技學院,廣西桂林,541004;2.廣西城市建設學校,廣西桂林,541003)
搜索引擎是一種專門在網絡上提供查詢服務的系統,它把分布在網絡上的信息資源進行收集、處理,然后經過整理后方便人們查詢。目前像百度和Google這樣的大型搜索引擎能為用戶提供海量的信息查詢服務,其查詢范圍遍布各行各業,基本可以滿足各個領域的信息橫向搜索。也正是因為這類通用搜索引擎所覆蓋領域廣闊,所以很難在搜索的同時兼顧到搜索的精準度。其價值在于對大量的分散信息做信息導航,對于信息量相對集中、分類類別更詳細的某一特定領域的信息檢索就會表現出其縱向搜索的局限性。
垂直搜索引擎的出現正是為了解決通用搜索引擎在特定領域下的搜索精度不高、主題偏移、搜索深度不夠等問題。垂直搜索引擎專注于某一類信息、專業領域、特定主題下的信息檢索,其追求的是專業性和檢索服務深度。對于大學招生信息主題的搜索引擎,則專注于提供各個學校招生信息、學校信息、招生專業等信息的檢索服務。
系統主要由信息采集、信息預處理、信息檢索三部分組成。在信息采集部分,主要通過網絡爬蟲抓取因特網上的網頁數據的方式,用構建招生信息主題詞庫的過濾器過濾掉與招生信息不相關的網頁鏈接,然后把與招生信息相關的網頁信息存放到網頁庫中。在信息預處理部分通過索引器對對采集到的網頁庫建立索引方便系統查詢。信息檢索部分主要負責與用戶的直接對接,如圖1所示。

圖1 主題搜索引擎總體框架
用戶通過Web服務器界面接入系統,輸入要查詢的內容,檢索器與索引庫對接,在索引庫中搜索信息,用排序器對搜索結果進行排序處理后返回給用戶。
Scrapy是基于 Python 實現的爬蟲框架,其架構清晰,模塊耦合度低[1]。可以應用在包括數據挖掘,信息處理或存儲歷史數據等一系列的程序中,簡單來說,Scrapy是一個可以爬取網站的數據,提取數據的框架。
Scrapy 框架組件及其中間件的功能如下[2]:
(1)Scrapy Engine(引擎):串聯框架各個模塊,觸發事務處理流程,控制數據流在系統中所有組件中流動。
(2)Scheduler(調度器):負責管理待抓取 URL 隊列。接受請求后返回下一個要爬取的鏈接。
(3)Downloader(下載器):向網站服務器發送訪問頁面請求,獲取頁面數據并提供給引擎。
(4)Spiders(爬蟲):爬取指定網站的數據內容,管理爬取規則和網頁解析規則等。
(5)Item Pipeline(項目管道):處理被spider提取出來的item,包括數據清洗、驗證及持久化(例如存取到數據庫中)等。
(6)Middlewares(中間件):包括下載器中間件(Downloader middlewares)和Spider中間件(Spider middlewares),處理引擎與下載器、爬蟲之間的請求及響應,其提供了一個簡便的機制,通過插入自定義代碼來擴展Scrapy功能。
Scrapy框架安裝完成后,便可創建自己的爬蟲項目,Scrapy爬蟲項目結構如圖2所示。

圖2 項目文件結構
各文件功能如下[3]:
(1)scrapy.cfg: 項目運行的參數設定。
(2)middlewares.py:爬蟲程序中間件。
(3)items.py: 項目中的item文件,管理待抓取的一些信息。
(4)pipelines.py: 項目中的pipelines文件,對爬取的數據進行清洗。
(5)settings.py: 項目的設置文件。
(6)spiders: 放置spider代碼的目錄。
為使抓取的網頁與高校信息主題相關度更高,本文采用知名度較高的高校招生網作為初始目標網站爬取數據。通過觀察目標網頁,在高校信息詳情頁部分,可以找到高校名字、類型、聯系電話、地址、簡介、招生計劃等信息,均包含在屬性值為class的li標簽中。可以先獲取一級頁面的列表頁信息,在根據列表頁中的詳情頁URL來獲取詳情頁的數據。
先在項目的全局性配置文件setting.py中,配置好項目的名稱、下載延遲、Scrapy執行的最大并發請求數等信息[4]。然后在數據模塊items.py文件中設置好要爬取的高校信息字段,然后通過scripy對目標網頁的高校信息頁面進行一級頁面的連接爬取和二級頁面的詳細內容。在scripy文件中,通過start_urls = []設置初始目標網站,通過allowed_domains = []設置允許爬取的范圍,在def parse()通過Xpath獲取到爬取的一級頁面的列表
在數據處理模塊pipelines.py中定義對爬蟲爬取下來的數據進行過濾處理。對爬取到的信息中含有非法字符的數據進行清洗和過濾,在實際操作過程中,遇到了一些亂碼的文字,設置過濾條件即可過濾全部數據噪聲。過濾后的數據,就可以存放到數據庫中了,本文將爬取的數據利用pymysql存儲到MySQL數據庫中。如圖3所示。

圖3 數據庫表中的爬取數據
用戶實際進行查詢操作時,對自己信息需求的描述方式,可能會與本來想要表達的意思有一定的出入,這樣系統在按用戶輸入的描述進行檢索的過程中,檢索結果中也許會出現很多用戶并不關心的信息,而用戶本來比較感興趣的一部分信息卻被忽視掉。為了讓這些沒有被描述過的信息在檢索結果中的重要性提升,就需要一個反饋的機制。
一個理想的檢索結果應該是用戶感興趣的內容最多,而用戶不感興趣的內容最少。但是這樣的理想情況是不可能一次實現的,要想得到讓用戶滿意的檢索結果,必須通過若干次的反饋過程。
Rocchio算法提供了一種將相關反饋信息融入到向量空間模型的方法,是實現相關反饋的一個經典算法[5]。它的基本思想是將用戶需求表示為一個向量,根據用戶的反饋情況來動態調整向量中每一維的關鍵詞的權重來使得向量更接近用戶想要的理想查詢。
D是文檔集合,包括所有相關和不相關的文檔。我們想要的,是找到一個最優的查詢向量q,使得q與相關文檔的相似度最大并且與不相關的文檔的相似度最小,如下:

Rocchio經過推導計算可以得到一種常見修正形式如下:

公式(2)中引入了可變參數α、β、γ,來調控修改結果和原始向量之間的平衡,讓公式更具有普遍適用性。在實際使用中,正反饋往往比負反饋更重要,因此在很多系統中會把參數設置成β>γ,甚至很多系統都只允許進行正的反饋,即γ=0。一種在性能上比較穩定的方法是只對檢索結果中排名最高的不相關文檔進行負反饋,如下:

Rocchio算法要求用戶對檢索結果進行相關性評價,我們可以詢問用戶檢索結果是否相關,讓系統進行自動修正,但是更多情況下,用戶并不會耐心閱讀檢索出來的所有文檔,也不一定會對文檔進行直接的相關性評價。不過我們可以通過分析用戶閱讀文檔時的一些操作,間接得到用戶對文檔的評價,如:
(1)若用戶反復閱讀某一個文檔,即文檔的被點擊次數較多,則用戶對這個文檔感興趣。
(2)若用戶下載某個文檔,說明用戶對這個文檔感興趣。
(3)若用戶長時間閱讀某個文檔,則認為用戶對這個文檔感興趣。
(4)對于用戶沒有點擊訪問的文檔,則認為用戶對這個文檔不感興趣。
(5)對于用戶點擊進入后很快離開的頁面,則認為用戶對這個文檔不感興趣。
本文將高校名字、地址、類型、招生批次等數據作為Rocchio算法中的向量,然后根據用戶的時間使用情況動態調整。用戶相關性向量模型不必根據用戶每次的閱讀行為進行調整,我們可以搜集一段時間內的反饋信息后再進行調整。這樣可以減輕系統壓力,也可以避免用戶行為的偶然性的反饋影響。
本文基于Scrapy框架設計了一個高校招生信息主題的垂直搜索引擎。利用 Scrapy 爬蟲框架以及Pythn語言擴展庫實現了網頁數據的爬取,針對用戶輸入查詢詞不明確的情況,本文還對基于Rocchio算法的反饋模型進行了研究,為用戶提供更精確的搜索體驗。系統同時也有一些有待改進的地方,比如數據分類存儲優化,Rocchio算法參數的優化等,這些都是需要進一步進行研究的內容。