網絡爬蟲(又被稱爲網頁蜘蛛,網絡機器人,在FOAF社區中間,更常常的稱爲網頁追逐者),是一種按照必定的規則,自動地抓取萬維網信息的程序或者腳本。php
爬蟲的本質就是一段自動抓取互聯網信息的程序,從網絡獲取感興趣的信息,抓取對於咱們有價值的信息,爬蟲技術是大數據和雲計算的基礎。python
爬蟲的實現可認爲是模擬瀏覽器與服務器數據交互,僞造HTTP請求。web
網頁爬取庫:正則表達式
一、urllib模塊的urllib.request json
#基本被取代服務器
二、requests 第三方庫 cookie
#中小型爬蟲開發網絡
#官網:http://www.python-requests.org/en/master/框架
三、Scrapy 框架 函數
#大型爬蟲開發
內容解析庫:
一、BeautifulSoup庫
#提取HTML和XML裏的數據
#官網https://www.crummy.com/software/BeautifulSoup/bs4/doc/
二、re模塊
#正則表達式,處理字符串
查看網站爬蟲協議
url/robots.txt
安裝:
sudo pip3 install requests
使用介紹:
1 import requests #導入庫 2 3 4 #get請求數據 5 res=requests.get("http://www.baudu.com")#get請求URL 6 # res=requests.get("http://www.baidu.com",params={"w1":"ww11","w2":"ww22"})#get帶參數請求 7 print(res.url)#獲取到訪問的URL 8 9 10 11 #post請求數據 12 res=requests.post("http://www.baudu.com")#post請求URL 13 # res=requests.post("http://www.baidu.com",data={"w1":"ww11","w2":"ww22"})#post帶參數請求 14 15 #post上傳文件 16 #filex={"img":open('dongdd/web.py','rb')}#文件表單 17 #filex={"img":("evil.jpg",open('dongdd/1.jpg','rb'))}#指定文件名更改成evil.jpg 18 filex={"img":("veil.txt","人的一切痛苦,\r\n本質上是對本身無能的憤怒!\r\n wowo")}#以文件保存字符串 19 res=requests.post(urlx,files=filex) 20 21 22 23 #cookies 24 #cookie在請求頁第一次設置後是不能立刻用下列函數拿到值的,必須是請求前存在 25 26 print(res.cookies)#打印全部cookie 27 print(res.cookies["us"])#獲取單個cookie 28 29 #攜帶自定義cookie,可作當次頁面cookie比較驗證 30 coo={"cc1":"ccc01","cc2":"ccco2"} 31 res=ss.post("http://192.168.43.21:8080/login.php",cookies=coo) 32 33 #自動攜帶網站上的cookie,訪問頁面,上面代碼設置cookie的不可被自動攜帶,必須每次手動 34 ss=requests.Session() 35 res=ss.post("http://192.168.43.21:8080/login.php") 36 res=ss.post("http://192.168.43.21:8080/cancel.php")#可作頁面1中cookie驗證 37 38 39 40 #超時 41 #默認爲一直請求URL,處於中止狀態,因此必需要設置超時 42 res=requests.post("http://192.168.43.121:8080/login.php",timeout=0.2)#鏈接時間爲:0.2s 43 #設置鏈接超時和讀超時:timeout=(3.05, 27) #第一個爲規定鏈接時間,第二個爲規定讀取時間 44 #永遠等待相應:timeout=None 45 46 47 #修改或添加請求頭,請求頭的必要參數可修改 48 headx={'User-Agent': 'wwwwwwwww', 'Connection': 'xxxxxxx', 'tt': '--------'} 49 res=requests.get("http://193.112.87.66/wx/file.php",headers=headx) 50 print(res.request.headers)#獲取請求頭 51 52 #其餘相關參數 53 print(res.status_code)#獲取訪問狀態碼,200(系統常量:requests.codes.ok)爲成功 54 print(res.raise_for_status())#請求錯誤時能夠打印錯誤(4XX客戶端錯誤或5XX服務器錯誤響應) 55 print(res.encoding)#查看編碼 56 res.encoding="utf-8"#更改編碼 另外值:ISO-8859-1 57 print(res.headers)#以字典形式打印相應頭,HTTP標頭名稱不區分大小寫 58 print(res.headers["date"])#print(res.headers.get("DAte"))打印出相應頭時間信息 59 print(res.text)#打印網頁源碼 60 61 #json數據解析: 62 jsontt1=res.json()#獲得json數據 63 print(jsontt1.keys())#輸出全部json可鍵名 64 print(jsontt1["key11"])#獲取單個鍵的數據 65 66 #二進制格式數據:res.content 67 #獲取一張網絡圖片並存儲實現: 68 res=requests.get("http://193.112.87.88/wx/img/0.jpg",timeout=5)#訪問獲得圖片數據 69 f=open("ww.jpg","wb")#以二進制方式打開文件 70 f.write(res.content)#寫入二進制數據 71 f.close()#必須關閉文件 72 73 #從服務器獲取原始套接字響應,您能夠訪問res.raw,必須設置:stream=True 74 #數據只能使用一次(相似文件指針) 75 res=requests.get("http://193.112.87.88/wx/file.php",stream=True) 76 res.raw.read(10)#讀十個字節 77 78 #另外一種方式獲取網頁源代碼: 79 res=requests.get("http://193.112.87.88/wx/file.php",stream=True) 80 rxx=res.raw.read(1)#讀取一個字節 81 f=open("www.txt","wb") 82 while rxx:#判斷是否爲空 83 print(rxx) 84 f.write(rxx)#寫一個字節 85 rxx = res.raw.read(1)#讀下一個字節 86 f.close();#必須關閉文件
安裝:
python3環境自帶
基本介紹:
一、正則表達式是獨立的語言,正則語言是共通的,好比以前寫的PHP正則裏有不少共同性
二、匹配單元介紹
轉義字符:如點表明全部字符,因此可用\.表示字符串的點
【.】、【\】、【?】、【^】、【$】、【*】、【+】、【}】、【{】、【[】、【]】、【|】、【(】、【)】
特殊符號字符:
【\d】全部數字,至關於[0-9]
【\D】全部非數字,至關於[^0-9]
【\w】任意一個字(a-z、A-Z、0-九、下劃線、中文字)
【\W】任意非字,至關於[^a-zA-Z0-9_中文字]
【.】(點)任意一個原子
【\s】全部空白(空格、tab鍵、換行),至關於[\r\t\n\f\v]
【\S】任意非空白
匹配任意一個:
[字符1字符2字符3]//也可爲[a-zA-Z]區間//匹配任意一個
注意:
【^】爲取反,寫在中括號內開頭處,表示除了括號裏的全部字符均可以
【^】表示普通字符,寫在括號裏除最前面的任意位置
括號裏的字符須要轉義,雖然有些不用轉義
三、 匹配單元的修飾補充
【*】修飾前面的單個原子能夠出現任意次
【+】修飾前面的單個原子至少要出現1次
【?】修飾前面的單個原子只能出現0次或者1次
【{ n }】修飾前面的單個原子只能出現n次
【{a,b}】修飾前面的單個原子只能出現 [ a , b ] 次 //至少兩次用{2, }
【|】修飾兩邊字符串任意誰總體出現,/intelligent|diligent/
【^字符1】必須以字符1開始的行,r’^xceee’必須以xceee爲開始,寫在表達式最前面
【$字符2】必須以字符2結尾的行,/\Aaa.*wo$/必須以aa開始和wo爲結束,.*表示任意
【\A和\Z】開始和結束,用法跟上相同 ,但不是以行爲結束
【\b】單詞邊界(空格),r’\bare\b’,匹配字符串「ware are xxx」匹配到are單詞,
【\B】單詞邊界之外的部分
【( )】改變優先級,r’t(r|x)ol’,可匹配trol或者txol
以小變大:r’tel*’表示l可出現任意次=>r’t(el)*’表示el可出現任意次
用於取出:r’t(el)(.*)’如"xxwtelelllll"輸出:[('el', 'elllll')]
使用介紹:
1 import re #導入re模塊 2 3 #總體匹配 4 str=r'To live is to live' #原字符串,r表示原始字符,如‘\n’並不會被解釋爲換行 5 zstr=re.findall("li",str); #查找全部,返回列表 6 print(zstr); #打印列表 輸出:['li', 'li'] 7 8 #用[ ]匹配其中一個 9 str=r'live and love' 10 zstr=re.findall("l[io]ve",str); 11 print(zstr); #輸出:['live', 'love'] 12 13 14 15 16 #方法:compile(),生成re對象 17 str=r'aawobbxxaatabbb' #原字符串 18 re_job=re.compile("a a.*?b b",re.I|re.X)#建立re對象 19 zstr=re_job.findall(str); #使用re對象去查找 20 print(zstr); #打印列表,輸出:['aawobb', 'aatabb'] 21 22 #第二個參數值: 23 #【re.I】不區分大小寫,r’teL’可匹配tel、Tel、TEL 等 24 #【re.M】換行後不示爲同行,默認將\n換行示爲以上一行爲同一行,影響【^】【$】/^aa/使用有區別 25 #【re.S】修正表達式中【.】可匹配回車\n,如/a.*art/s匹配"I am \nsmart" 26 #【re.X】忽略正則表達式內容裏所寫的空白間隔,去掉空字符和# 後面的註釋 27 #【re.U】根據Unicode字符集解析字符。這個標誌影響 \w, \W, \b, \B 28 29 #方法:match(),正則字符串匹配開頭 30 str=r'xxwtelelllll' #原字符串 31 zstr=re.match('xx',str); #使用re對象去查找 32 print(zstr); #輸出對象:<re.Match object; span=(0, 2), match='xx'>,未匹配到則返回None 33 if(zstr): 34 print("匹配成功") 35 else: 36 print("匹配失敗") 37 38 #方法:search(),正則字符串匹配任意一個位置 39 str=r'wtxxelelxxllll' #原字符串 40 zstr=re.search('xx',str); #使用re對象去查找 41 print(zstr); #輸出對象:<re.Match object; span=(2, 4), match='xx'>,未匹配到則返回None 42 if(zstr): 43 print("匹配成功") 44 else: 45 print("匹配失敗") 46 47 #方法:sub(),正則法替換字符串內容 48 str=r'--x2x--xvx--' #原字符串 49 zstr=re.sub('x.*?x','Python',str); #使用re對象去查找 50 print(zstr);#輸出:--Python--Python— 51 #將re.sub換成:re.subn()則輸出次數:('--Python--Python--', 2) 52 53 #方法:split(),正則法拆分字符串內容 54 str=r'1+2-6/1|2^5' #原字符串 55 zstr=re.split(r'[\^\+\*\|\/\-]',str); #使用re對象去查找 56 print(zstr);#輸出:['1', '2', '6', '1', '2', '5']
安裝:
sudo pip3 install beautifulsoup4
使用介紹:
1 from bs4 import BeautifulSoup#導入模塊 2 import requests #網頁訪問庫 3 res=requests.get("http://193.112.87.88/wx/file.php") 4 res.encoding="utf-8" 5 6 be=BeautifulSoup(res.text,"lxml")#獲得BeautifulSoup對象,lxml爲HTML解析器,如XML解析則要用xml 7 print(be.original_encoding)#輸出編碼 8 print(be.prettify())#以標準HTML格式輸出網頁源碼 9 10 print(be.input)#獲取到第一個input標籤所有內容:<input name="img" type="file"/> 11 print(be.form.input)#獲取到標籤(form)下的子標籤(input) 12 print(be.form.encode("latin-1"))#自定義編碼輸出 13 print(be.input.parent.parent)#獲取input標籤的父節點的父節點 14 print(be.input.previous_sibling)#上一個兄弟節點 15 print(be.input.next_sibling)#下一個兄弟節點 16 print(be.img)#獲取到第一個img標籤內容:<img src="img/0.jpg"/> 17 picture=be.img 18 print(picture.get('src'))#獲取該屬性值(優先考慮):img/0.jpg 19 print(be.img["src"])#直接獲取屬性值 20 21 #獲取到標籤內容值 22 print(be.title) # <title>東小東頁</title> 23 print(be.title.text) #東小東頁 24 print(be.title.string) #東小東頁 25 26 #函數find_all()和find()使用,參數使用是相同的 27 #參數值都可使用:字符串、列表、正則對象、True(任意值) 28 29 print(be.find_all(class_="yzm",limit=2))#limit爲要返回的條數 30 print(be.find_all('input')) #查詢全部標籤名爲input,存入到列表 31 be.find_all(id='link2')#經過id值查找 32 print(be.find_all(type=True))#type爲true表示能夠接收任意值 33 print(be.find_all(class_="yzm"))#經過class屬性查找內容,注意class後面有下劃線 34 print(be.find_all(src=re.compile(r"img/.*?jpg")))#經過src屬性查找 35 print(be.find_all('img')[0]["src"])# img/0.jpg 36 #-------------------------------------------------- 37 import re #使用正則表達式 38 for inx in be.find_all(re.compile(r"i")):#匹配帶i字母的全部標籤名 39 print(inx.name) 40 #------------------------------------------------ 41 for inx in be.find_all(["input","img"]):#列表傳遞多個需匹配標籤名 42 print(inx) 43 print(inx.get("name"))#獲取標籤name屬性值 44 #------------------------------------------------------ 45 46 #找到第一個,且只找一個 47 print(be.find(type="file"))#經過屬性查找 48 print(be.find("input"))#經過標籤查找 49 print(be.find("input",type="password"))#經過標籤加屬性查找,可支持有:id、type等 50 print(be.find(text="東小東").parent)#經過text屬性查找:<legend>東小東</legend> 51 #參數不支持name和data-* 52 print(be.find_all(attrs={"name":"yzm"}))#可用此方法解決 53 54 55 #擴展: 56 be=BeautifulSoup(open("www.txt","rb"))#直接讀取文件內容