三、用Css來提取網頁

scrapy提供了兩種提取方法,Xpath和Css。

Xpath用起來覺得好麻煩,有點笨,我還是比較喜歡Css的提取方式。因為CSS定位語法比Xpath簡潔,定位方式更靈活多樣,可以使用#id來根據ID獲取元素,以及使用.class來根據class獲取元素.用XPath實現的話都不會那么簡潔,反過來呢,XPath可以使用,來返回到DOM樹的上層節點中。anyway先操練起來!

http://blog.jobbole.com/102337/


F12來打開網頁源代碼,也可以點擊firefox旁邊那個小蜜蜂??

我現在想提取“我想對所有新手程序員說些肺腑之言”

關鍵詞:entry-header;? ? h1

我們現在用mac終端來測試一下提取結果,進入虛擬環境

輸入:

scrapy shellhttp://blog.jobbole.com/102337/

1.提取title

>>> response.css(".entry-header h1::text").extract()[0]

'我想對所有新手程序員說些肺腑之言'

解釋一下:

這個點.? 表示 選擇所有class包含container的節點

extract()提取出他的值

[0]

::text偽類選擇器

這里要用py3,編碼才是Unicode中文字,不然py2的話,還是utf8字符串的顯示模式。

2.提取日期

>>> response.css("p.entry-meta-hide-on-mobile::text").extract()[0].strip()

'2017/05/27 ·'

3、提取點贊數

>>> response.css(".vote-post-up? h10::text").extract()[0]

'3'

4、提取收藏數

>>> response.css(".bookmark-btn::text").extract()[0]

' 7 收藏'

用正則表達式把7提取出來

進入python環境,測試一下正則表達式

是騾子是馬拉出來溜溜,不行慢慢調試

importre

match_re=re.match(".*?(\d+).*"," 7 收藏")

ifmatch_re:

print(match_re.group(1))

yeah!7出來了

5、提取評論數

我用了比較笨的方法提取的:

>>> response.css(".btn-bluet-bigger::text").extract()

[' ', ' 贊', ' 7 收藏', ' 3 評論']

>>> response.css(".btn-bluet-bigger::text").extract()[3]

' 3 評論'

>>> response.css(".btn-bluet-bigger::text").extract()[3].strip()

'3 評論'

Bobby老師是這么做的,

response.css("a[href='#article-comment'] span::text").extract()[0]

走神中:

自己做個小練習:


把博士帽那個240聲望值提取一下。

>>> response.css("#author-bio .author-bio-info-block a::text").extract()[2].strip()

'240'

哎,還是我的笨方法好用,先這樣吧,以后慢慢優化吧

6.提取內容

>>> response.css ( ".entry" ).extract()[0]或者

>>> response.css ( "div.entry" ).extract()[0]

都可以

7、提取tag標簽

>>> response.css(".entry-meta-hide-on-mobile a::text").extract()

['開發', ' 3 評論 ', '程序員']

如何把3評論給扔掉呢?

用數組的方式在python里面簡單寫段代碼來驗證一下

tag_list= ['開發',' 3 評論 ','程序員']

tag_list= [elementforelementintag_listif notelement.strip ().endswith ("評論")]

tags =",".join (tag_list)

print(tag_list)



Xpath基本語法

舉例元素標簽為artical標簽

一:

artical 選取所有artical元素的子節點

/artical 選取根元素artical

artical/a 選取所有屬于artical的子元素a元素

//div??? 選取所有div 子元素,無論div在任何地方

artical//div? 選取所有屬于artical的div 元素,無論div元素在artical的任何位置

//@class 選取所有名為class 的屬性的

二:謂語

/artical/div[1]?? 選取所有屬于artical 子元素的第一個div元素

/artical/div[last()]? 選取所有屬于artical子元素的最后一個元素

/artical/div[last()-1] 選取所有屬于artical子元素的倒數低2個元素

//div[@lang]?? 選取所有擁有屬性為lang的元素

//div[@lang="eng"] 選取所有div下lang屬性為eng的元素

三:

/div/* 選取所有屬于div元素的所有子節點

//*??? 選取所有元素

//div[@*]?? 選取所有帶屬性的title元素

//div/a|//div/p?? 選取所有div元素的a和p 元素

//span | //ul?? 選取文檔中所有span和ul 的元素

artical/div/pl|//span? 選取所有div下的pl和文檔中所有span

注意事項:

1) 按照審查元素的寫法不一定正確,要按照網頁源碼的才行

因為不一樣,網頁源碼才是你看到的

2) 瀏覽器有自帶的復制xpath功能,firefox下載firebug插件

3) xpath有c的速度,所以按照[@class=""]準確性較高

CCS選擇器語法

* ??? ??? ??? ??? ?選擇所有節點

#container ?? ??? ?選擇id為container的節點

.container????? 選擇所有class包含container的節點

li a??????????? 選取所有li 下所有a節點

ul + p????????? 選取ul后面的第一個p元素

div#container > ul 選取id為container的div的第一個ul子元素

ul ~p ?? ??? ??? ?選取與ul相鄰的所有p元素

a[title]??????? 選取所有有title屬性的a元素

a[]? 選取所有href屬性為http://jobbole.com的a元素

a[href*="jobbole"]???? 選取所有href屬性值中包含jobbole的a元素

a[href^="http"]??? 選取所有href屬性值中以http開頭的a元素

a[href$=".jpg"]??? 選取所有href屬性值中以.jpg結尾的a元素

input[type=radio]:checked?? 選擇選中的radio的元素

div:not(#container)? 選取所有id為非container 的div屬性

li:nth-child(3)????? 選取第三個li元素

li:nth-child(2n)????? 選取第偶數個li元素

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容