Python爬虫——爬取IEEE论文
目錄
- 1 獲取文章列表
- 1.1 問題
- 1.2 解決方法
- 1.2.1 創建瀏覽器對象進行模擬訪問[1?4]^{[1-4]}[1?4]
- 1.2.2 POST請求[5]^{[5]}[5]
- 2 獲取完整摘要
- 2.1 問題
- 2.2 解決方法
- 參考資料
說明:本文為個人解決問題過程記錄,方法和理論不一定完全正確,如有錯誤,歡迎指出。
1 獲取文章列表
1.1 問題
??IEEE是第3個爬的數據庫,前兩個Pubmed和ScienceDirect都直接用requests.get()可以直接返回一個Response對象,然后用Beautifulsoup解析Response的.content,最后用find和find_all找想要的信息就可以了,如下所示:
# 模板 res = requests.get(url, params=searchDic) # 發送GET請求 s = BeautifulSoup(res.content, 'lxml') # 解析html amount = s.find('div', class_="results-amount") # 獲取文章總數量??修改代碼后程序報錯,調試發現是find函數找不到類名
url = 'https://ieeexplore.ieee.org/search/searchresult.jsp? \newsearch=true&queryText=support' IEEE_response = requests.get(url=url, verify=False) response_text = IEEE_response.content s = BeautifulSoup(response_text, 'lxml') papers = s.find_all('div', class_="List-results-items") # 找不到List-results-items??問題就出在這,在瀏覽器里F12可以找到對應信息的標簽,但是在程序里直接find卻找不到,直接輸出Beautifulsoup解析后的數據,發現問題。
??Beautifulsoup解析后的數據如下:
<div class="global-content-wrapper u-relative"> <xpl-root> <div class="Spinner"></div> </xpl-root> </div>??瀏覽器中html如下:
??論文列表就在紅色箭頭所指向的標簽,但是get返回的信息中直接被“刪除”了。
1.2 解決方法
??網上百度了一圈,找到了解決方法,最開始找到的是方法1,后來又找到了方法2.
1.2.1 創建瀏覽器對象進行模擬訪問[1?4]^{[1-4]}[1?4]
??刷新網頁,可以發現論文信息那部分是其它頁面顯示后過了一陣才刷出來的。這是因為IEEE用了ajax慢加載的方式來防止爬蟲爬取頁面,直接訪問鏈接并不能得到任何東西。對于這種問題我們可以使用工具selenium來解決。selenium是一種自動化測試的工具,可以控制瀏覽器來自動完成一些動作,在這里正好能成為 ajax 防爬的克星。
??代碼如下:
browser = webdriver.Chrome() browser.get(url) browser.implicitly_wait(10) # 隱式等待 WebDriverWait(browser, 5, 0.5).until(lambda x:x.find_elements_by_class_name('List-results-items')) amount = browser.find_element_by_xpath("//*[@id=\"xplMainContent\"] \/div[1]/div[2]/xpl-search-dashboard/section/div/div[1] \/span[1]/span[2]")??通過創建瀏覽器對象,selenium會自動打開chrome,來模擬瀏覽器訪問。通過WebDriverWait().until()來等待網頁加載完成后,再用find_element_by_×××來獲取數據。
??不過這樣存在一定的問題,由于是模擬人去瀏覽網頁以及瀏覽器啟動,網頁渲染等操作一個不落,所以無法發揮爬蟲的機器高效性;另外即使是無界瀏覽模式,瀏覽器還是會占用大量的電腦內存資源。
1.2.2 POST請求[5]^{[5]}[5]
??參考[5]中搜索部分的代碼可以正常運行,且獲得正確數據,發現是用post請求進行訪問的,于是研究了一番。
??瀏覽器中按F12看網址加載過程,方法如下:
如下圖,點進Preview中發現,想要的信息都在這里
如下圖,點擊Headers,訪問方式是POST
如下圖,Headers信息
??因此確定要用POST方式來進行訪問,Resoponse Headers中顯示返回類型為json格式,知道這些信息后就可以開始寫代碼處理了。
# 請求頭 headers = {'Accept': 'application/json,text/plain,*/*','Accept-Encoding': 'gzip,deflate,br','Accept-Language': 'zh-TW,zh;q=0.9,en-US;q=0.8,en;q=0.7','Connection': 'keep-alive','Content-Length': '122','Content-Type': 'application/json','Referer': 'https://ieeexplore.ieee.org/search/searchresult.jsp? \newsearch=true&queryText=mechanical','User-Agent': 'Mozilla/5.0 (X11; Linux x86_64; \rv:27.0) Gecko/20100101 Firefox/27.0'} # 請求體 data = {'newsearch': 'true','queryText': keyword,'pageNumber': page,'publicationYear': year_range,'rowsPerPage': 100} # 返回結果處理 url = 'https://ieeexplore.ieee.org/rest/search' IEEE_response = requests.post(url=url, data=json.dumps(data), \headers=headers, verify=False) response_text = IEEE_response.text papers = json.loads(response_text)['records'] for paper in papers:paper_name = paper['articleTitle']journal_name = paper['publicationTitle']paper_date = paper['publicationDate']paper_abstract = paper['abstract']paper_doi = paper['doi']paper_num = paper['articleNumber']??可以看出,第2種方式在進行數據處理時也比較簡單明了,因此我采用了第2種方法。
2 獲取完整摘要
2.1 問題
??通過上述步驟,就可以順利的從IEEE檢索結果中獲取論文信息了,如論文題目、作者、會議/期刊名、日期、摘要、doi等。但是,獲得的摘要是不完整的,因為在搜索結果列表狀態下的論文摘要只顯示了一部分,剩下的需要到文章的詳情頁才能看到。
??瀏覽器中F12后,定位到摘要位置也是不完整的。
2.2 解決方法
??首先在文章詳情頁中定位到摘要部分
??點Preview后發現預覽里面并沒有論文相關信息,如下圖
??在Response中定位,發現是用Javascript寫的,如下圖
??復制最外側{}括號之間內容,用JSON解析器解析一下,確實是完整的論文信息,如下圖
??從Headers中找到訪問相關的信息
??再次上百度大法,找到方法來獲取HTML中的JavaScript內容[6?8]^{[6-8]}[6?8]?;玖鞒叹褪前l送GET請求,用Beautifulsoup解析返回信息,然后用正則表達式來獲取到json數據,最后將json數據轉換為字典格式。
# 請求頭 gheaders = {'Referer': 'https://ieeexplore.ieee.org/search/searchresult.jsp? \newsearch=true&queryText=support','User-Agent': 'Mozilla/5.0 (X11; Linux x86_64; rv:27.0) \Gecko/20100101 Firefox/27.0','Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9, \image/avif,image/webp,image/apng,*/*;q=0.8,''application/signed-exchange;v=b3;q=0.9','Accept-Encoding': 'gzip, deflate, br','Accept-Language': 'zh-CN,zh;q=0.9','Connection': 'keep-alive' } # 請求鏈接 url = 'https://ieeexplore.ieee.org/document/4537113' IEEE_response = requests.get(url=url, headers=gheaders) # GET請求 soup = BeautifulSoup(IEEE_response.text, 'lxml') # 解析 # 正則表達式 創建模式對象 pattern = re.compile(r'xplGlobal.document.metadata=(.*?);', re.MULTILINE | re.DOTALL) script = soup.find("script", text=pattern) # 根據模式對象進行搜索 res_dic = pattern.search(script.string).group(1) # 配合search找到字典 print(res_dic) json_data = json.loads(res_dic) # 將json格式數據轉換為字典 print(json_data['userInfo']) # 測試一下。。參考資料
[1]IEEE 論文爬取
[2]python系列之網絡爬蟲
[3]selenium采用find_element_by方法識別頁面元素
[4]Python selenium有多個class值時如何定位
[5]爬取ieee
[6]如何獲取在Python中的JavaScript內容
[7]python 爬蟲如何獲取js里面的內容
[8]python中的search的group(0),group(1)的方法
總結
以上是生活随笔為你收集整理的Python爬虫——爬取IEEE论文的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Docker操作篇
- 下一篇: week3note函数