學校官網沒有導師檢索工具怎麼辦?Python + BeautifulSoup 爬取導師信息自制檢索工具

1 背景

考研分數下來後,感覺成績不錯的就要開始聯繫目標院校的導師了。選擇導師要按照自己感興趣的研究生方向進行選擇,如果能按關鍵字檢索導師信息就會方便許多。我報考的是北京交通大學計算機學院,但官網中一欄 導師風采 並沒有檢索功能,只能按照拼音順序查找老師。這一頁一頁點進去看導師的信息效率實在是太低,篩選過程很不方便。所以想着乾脆直接用爬蟲把導師信息入庫,這樣就能自己實現檢索功能了,想怎麼查就怎麼查。

在這裏插入圖片描述
下面記錄一下我用 Python + BeautifulSoup 爬取導師信息的過程。因爲我平時不是做 Python 的,所以也是現學現賣,寫的不完善的地方還請指教。

2 網站分析

2.1 導師詳情頁分析

通過觀察每個導師的詳情頁可以發現,導師的介紹頁格式是統一的。每個導師的頁面都有紅框中的類別。這樣,對爬蟲工作就輕鬆多了,因爲越簡單的網站越容易爬取。
在這裏插入圖片描述

2.2 導師目錄頁

導師目錄頁以分頁形式展示,分頁標識是用 url 中 page 參數區分。這種情況也是比較好處理的,直接在代碼中 i++ 循環即可。
在這裏插入圖片描述

2.3 思路

根據分析,可以得出:

  1. 先遍歷目錄頁
  2. 解析每個目錄頁,找到每個老師的編號拼出每個導師詳情頁的地址
  3. 根據每個導師詳情頁地址,獲取導師的詳細信息並解析入庫

3 代碼編寫

3.1 Python 版本

3.7

3.2 第三方庫導入

該爬蟲需要引入三個庫:requests、BeautifulSoup、MySQLdb
requests:一個 Http 庫
BeautifulSoup:用於解析網頁數據
MySQLdb:用於與 mysql 連接

如果沒有安裝這三個庫需要先安裝。

pip3 install requests
pip3 install beautifulsoup4
pip3 install mysqlclient

3.3 遍歷目錄頁找到每個導師的網址

在這裏插入圖片描述

通過查看目錄頁的源碼,發現每個導師的詳情頁都對應一個編號。這個編號在一個 <div class="teacher_incard"> 標籤下的 <a> 標籤裏。所以通過解析出 <a> 標籤裏的 href 的值,前面再拼上網站域名,就可以得到導師詳情也的地址了。

具體有關 BeautifulSoup 的用法可以參考 beautifulsoup菜鳥教程

具體代碼:

def main():
    # 存放每個導師詳情頁地址
    professorList = []
    # 遍歷 7 頁導師目錄頁
    for i in range(1, 7):
        url = 'http://faculty.bjtu.edu.cn/cs/sdxx.html?page=' + str(i)
        print("正在爬取第 '%s' 頁導師:" % (i))
        print(url + '\n')
        # 獲取網頁內容
        html = getHTMLText(url, headers)
        parseProfessorsList(professorList, html)
    print("爬取鏈接完成")

# 解析目錄頁,獲得每個導師的詳情頁地址
def parseProfessorsList(professorList, html):
    # 域名
    url = 'http://faculty.bjtu.edu.cn'
    # 創建 soup
    soup = BeautifulSoup(html, 'html.parser')
    rows = soup.find_all('div', attrs={'class': 'row'})
    # 第二個 row 導師信息塊,根據 class="teacher_card" 解析
    i = rows[1].find_all('div', attrs={'class': 'teacher_card'})
    # 遍歷
    for professors in i:
        # 找到 a 標籤
        a = professors.find("a")
        # 拼接導師詳情地址
        pro = Professor(a.text.strip(), url + a.get('href'))
        professorList.append(pro)

3.4 解析詳情頁

在這裏插入圖片描述

同理,根據分析源碼裏的標籤,可以發現各模塊標題有着相同的樣式名,所以通過 BeautifulSoup 解析出來,再對內容做一些簡單的處理比如:去空格、按回車切分等,即能把數據分門別類地提取出來了。

具體代碼:

def parseProfessorsDetail(professor):
    professor.base = ''
    professor.eduBg = ''
    professor.workExp = ''
    professor.resOri = ''
    professor.resumeMajor = ''
    professor.sciResPro = ''
    professor.teachWork = ''
    professor.paper = ''
    professor.treatise = ''
    professor.patent = ''
    professor.softwarePatent = ''
    professor.honor = ''
    professor.partTimeJob = ''

    html = getHTMLText(professor.url, headers)
    soup = BeautifulSoup(html, 'html.parser')
    wrap = soup.find(id="wrap")

    # 頭像
    img = wrap.find("img")
    professor.img = img.get('src') + ""

    # title
    title = wrap.find(class_='border_p')
    professor.title = title.text.strip() + ""

    details = wrap.find_all(class_='mainleft_box')
    for detail in details:
        column = detail.find(class_='h4border').text.strip()
        [s.extract() for s in detail(class_='h4border')]
        contentOri = detail.text.strip()
        content = ''
        for line in contentOri.splitlines():
            if line == '':
                continue
            line = line.strip() + '\n'
            content = content + line
        content = content.rstrip('\n') + ""

        if column == '基本信息':
            professor.base = content
        elif column == '教育背景':
            professor.eduBg = content
        elif column == '工作經歷':
            professor.workExp = content
        elif column == '研究方向':
            professor.resOri = content
        elif column == '招生專業':
            professor.resumeMajor = content
        elif column == '科研項目':
            professor.sciResPro = content
        elif column == '教學工作':
            professor.teachWork = content
        elif column == '論文/期刊':
            professor.paper = content
        elif column == '專著/譯著':
            professor.treatise = content
        elif column == '專利':
            professor.patent = content
        elif column == '軟件著作權':
            professor.softwarePatent = content
        elif column == '獲獎與榮譽':
            professor.honor = content
        elif column == '社會兼職':
            professor.partTimeJob = content
        print(content)
    insertProfessor(professor)

3.5 入庫

入庫的話就比較簡單了
主要就是創建 cursor,執行sql,提交即可。

cursor = db.cursor()
cursor.execute(sql)
db.commit()

4 結語

至此,導師的信息就已經被錄入到數據庫中了。後續的話,可以通過數據庫檢索,或者製作個 web 頁對導師信息進行檢索和展示什麼的,就看個人的喜好了。

該爬蟲源碼和建表 sql 我都放在 GitHub 上了,感興趣的同學可以自取: bjtu_cs_prof_spider

另外我也做了個簡易的在線導師檢索工具,方便大家檢索:北交大計算機導師在線檢索工具


原文作者: 一隻因特馬
原文鏈接: https://www.matalking.com/a/2490095011/
版權聲明: 本博客所有文章除特別聲明外,均採用 BY-NC-ND 許可協議。轉載請註明出處!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章