1. 程式人生 > >python學習筆記(一)

python學習筆記(一)

href ons xxx 自動下載 fail 響應 cdn pat pda

  因為工作需要,經常需要到新浪某博客去找資料,在博文目錄裏一頁頁地肉眼搜索,看到合適的標題再點擊開鏈接查看內容,知道合適地再復制下來。很煩人。於是一直有個想法,學會爬蟲。

  拿著單位發的購書卡去買了本入門的書《python編程從入門到實踐》,憑著一點編程的底子,三個小時看完了基礎部分,然後安裝python就開始搜集各種網絡文字教程,開始實踐。

  (一)正則標題式提取博文文字

  新浪博客博文一句話可以放在幾個標簽裏面,感覺很奇葩(也許就是我無知)。因為亂七八糟的緣故,sir學習了一下re正則表達式模塊,然後開始動手

#導入request方法
from urllib import request
#導入正則表達式模塊
import re

#打開網頁,獲取響應文本
response=request.urlopen(‘http://blog.sina.com.cn/s/blog_xxxxxxx.html‘)

#讀取網頁源碼 不知道怎麽表達這個東西
page=response.read()

#轉碼
js= page.decode(‘utf-8‘)

#編譯匹配模式
pat=re.compile(r‘((?<=>)[^>]+?(?=</FONT>)|(?<=>)[^>]+?(?=</SPAN>))‘)

#匹配網頁內容
match=re.findall(pat,js)

#若匹配則輸出
if match:
    n=0
    for each_match in match:
        n+=1
        print(n," : "+each_match +‘\n‘)

  正則匹配模式寫得不夠完美把極少數的無關的內容匹配出來,加上各種網絡教程各種的看不懂,使得sir失去了努力的方向。

  (二)根據Excel中的Url下載圖片

  時隔一個月,突然有了采集圖片的機會,又讓sir有了一點動力。因為URL已經通過其他爬蟲采集到excel工作簿當中,於是sir又學習了一下第三方包openpyxl,之後又開始動手了。

from urllib import request                    #導入request函數
from openpyxl import load_workbook #導入load_workbook函數

#自定義一個根據url和圖片文件名稱為參數,自動下載圖片的函數
def downloadImage(imageUrl,imagePath):
    response=request.urlopen(imageUrl)#訪問圖片地址,獲得響應
    imageContents=response.read()#獲取圖片內容
    f=open(imagePath,‘wb‘)#打開文件
    f.write(imageContents)#寫入內容
    f.close#關閉文件


#打開Excel workbook
wb=load_workbook(‘image.xlsx‘)
#指定工作表
ws=wb.active
#獲取單元格內容 從第二行開始 到空白單元格結束 i=2 while ws.cell(row=i,column=1).value!=None: #生成文件名 A列為文件名稱 Path= str(i-1)+‘_‘+ws.cell(row=i,column=1).value +‘.jpg‘ #獲取URL地址 B列為URL地址 Url=ws.cell(row=i,column=2).value #調用函數下載圖片 downloadImage(imageUrl=Url,imagePath=Path) #循環下載圖片 print(‘已下載第‘+str(i-1)+‘張高清圖片>>>‘) i+=1

  因為函數downloadimage內部沒有添加異常處理,於是碰到request失敗的時候,腳本就停止不動了。添加了異常處理之後,sir有發覺下載的速度真的好慢。於是第二天求助了一位相識。

  (三)多線程下載圖片

  這位朋友發了一段代碼,讓我自己學習。研究之後sir發現了,把具體要做的事情,放到多線程下載那個類的內部,就可以使用多線程下載。速度立馬快的飛起。30秒給我下了2000多張圖片,高達1G,還好我及時終止了腳本。

同時Sir也學到異常處理怎麽寫,就是在json中找到圖片地址那個寫法一開始令人費解,花了一段時間才明白怎麽回事。

import requests
import json
import threading

Default_Header = {
    #具體請求頭自己去弄
}
_session=requests.session()
_session.headers.update(Default_Header)


#多線程下載
class myThread(threading.Thread):
    def __init__(self,imgUrl,fname):
        threading.Thread.__init__(self)
        self.imgUrl=imgUrl
        self.fname=fname
    def run(self):
        print("downloading",self.imgUrl)
        download(self.imgUrl,self.fname)

def download(fileid,type):
    img_url="http://img.hb.aicdn.com/"+fileid
    imgresp=requests.get(img_url)
    byte_img = imgresp.content
    try:
        out = open(type, ‘wb‘)
        out.write(byte_img)
        out.flush()
        out.close()
    except Exception as e:
        print(e)
if __name__ == "__main__":
    r =_session.get(‘http://huaban.com/pins/873774526/?xxxxxx‘)
    url=json.loads(r.text)
    urlList=url[‘pin‘][‘board‘][‘pins‘]
    for i in urlList:
        key=i[‘file‘][‘key‘]
        print(key)
        #download(key,key+‘.jpg‘)
        myThread(key,key+‘.jpg‘).start()

  

  (四)多線程采集改造

 

from urllib import request     
from bs4 import BeautifulSoup  
from openpyxl import Workbook   
import threading
import re
import time

#功能函數
def get_title(url):
    global n          #變量全局化
    global pageindex  #變量全局化
    #global ws        #為什麽聲明與不聲明都一樣?
    try:              #打開網頁,保存試卷標題和鏈接
        r=request.urlopen(url,timeout=10) #打開網頁,設置超時 response
        s=r.read()    #讀取網頁源碼
        js=s.decode(‘utf-8‘) #網頁轉碼
        soup=BeautifulSoup(js,‘lxml‘) #網頁解析
        #正則查找子節點
        for a in soup.find_all(‘a‘,href=re.compile(r‘http://blog.sina.com.cn/s/blog‘)): 
            n+=1      #計數
            ws.cell(row=n+1,column=1).value=n             #寫入序號
            ws.cell(row=n+1,column=2).value=a.string      #寫入標題
            ws.cell(row=n+1,column=3).value=a.get(‘href‘) #寫入鏈接
        print("download succeed >>>>"+url+‘\n‘)           #正常輸出
    except  Exception as e:
        print("download failed  >>>>"+url+‘\n‘)           #異常輸出
        
if __name__ ==‘__main__‘:#主線程
    start=time.time()    #開始時間
    filename=‘多線程爬取啟迪慧想試題標題與鏈接.xlsx‘ #Excel文件名
    threads=[]           #新建線程列表
    wb=Workbook()        #新建工作簿
    ws=wb.active         #活動工作表
    n=0                  #初始化計數
    #輸入表頭
    ws.cell(row=n+1,column=1).value=‘序號‘
    ws.cell(row=n+1,column=2).value=‘標題‘
    ws.cell(row=n+1,column=3).value=‘鏈接‘

    #設置起止頁碼
    pageindex=1
    pagecount=10
    #filename=str(pagecount)+filename
    
    while pageindex<=pagecount:
        url=u‘http://blog.sina.com.cn/s/articlelist_xxxxxxxxx_0_‘+str(pageindex)+‘.html‘
        t=threading.Thread(target=get_title,args=(url,))#添加子線程
        threads.append(t) #加入線程列表
        pageindex+=1      #下一頁

    
    for t in threads:
        t.setDaemon(True) #守護線程 必須在start()之前
        t.start()         #開始線程
                          #若t.join()放此處 則變成單線程
    for t in threads:
        t.join()          #線程等待 主線程必須在子線程執行結束之後 才能繼續  
    
    wb.save(filename=filename) #保存工作簿
    end=time.time()       #結束時間
    print(‘Usedtime %f seconds!‘ % (end-start) +‘\n‘) #輸出耗時!

  

  

  

  

  

  

python學習筆記(一)