1. 程式人生 > >資料分析這個職位有前途嗎?--資料採集(一)

資料分析這個職位有前途嗎?--資料採集(一)

首先我們對資料進行抽樣,目前招聘網站比較多,選取其中一個網站(前程無憂),並只是分析一個城市(廣州)進行分析,通過scrapy爬蟲的框架對招聘的職位進行資料抓取,並匯出csv檔案。

1. 分析招聘網站的頁面資料結構

1.1 職位列表分析

通過網站輸入資料分析職位並選擇廣州地區,跳轉到一個職位列表,該列表只有5列資料顯示並且是通過分頁顯示,5列資料不能滿足後面分析維度的需要 image.png

1.2 職位詳情分析

職位詳情的資訊比較多,包括了對應聘者的學歷,工作經驗,能力要求,招聘公司的型別,人數,招聘人數,薪資要求等多個維度的資料。 image.png

1.3 資料獲取的思路

(1)獲取職位招聘資訊的列表的檢視詳情的url地址。 (2) 通過url地址訪問詳情頁面,獲取詳情頁面的資訊。

2 爬蟲程式的程式碼實現

2.1 專案建立

在cmd控制檯執行**“scrapy startproject job_spider”** 生成如下圖的結構的程式碼檔案,其中itemload.py,main.py檔案,data目錄是後面新增的,後面會講到這幾個檔案,在eclipse新建一個python的專案,把相應的檔案拷貝進來。 image.png

新建main.py檔案,是為了能夠在eclipse裡面除錯專案,並且在檔案裡面新增下面的程式碼,該程式碼就是整個爬蟲專案的入口,執行專案並把結構匯出到csv檔案,其中%(name)s 表示爬蟲的名稱的佔位符,%(time)s表示匯出檔案的時間

if __name__ ==
'__main__': cmdline.execute(argv=['scrapy','crawl','51job','-o','data/export_%(name)s_%(time)s.csv'])

2.2 招聘列表的資料讀取實現

 1 class JobSpider(scrapy.Spider):
 2    name = "51job"
 3    start_urls = [
 4        "https://search.51job.com/list/030200,000000,0000,00,9,99,%25E6%2595%25B0%25E6%258D%25AE%25E5%2588%2586%25E6%259E%2590,2,1.html?lang=c&stype=&postchannel=0000&workyear=99&cotype=99&degreefrom=99&jobterm=99&companysize=99&providesalary=99&lonlat=0%2C0&radius=-1&ord_field=0&confirmdate=9&fromType=&dibiaoid=0&address=&line=&specialarea=00&from=&welfare="
5 ] 6 def parse(self, response): 7 list=response.xpath('//*[@id="resultList"]/div') 8 for info in list: 9 name=info.xpath('p/span/a/text()').extract_first() 10 url=info.xpath('p/span/a/@href').extract_first() 11 if not name is None: 12 yield scrapy.Request(url,callback=self.parse_detail) 13 14 next_url=response.css('#resultList > div.dw_page > div > div > div > ul > li:last-child>a::attr(href)').extract_first(); 15 if next_url: 16 yield scrapy.Request(next_url,callback=self.parse)

第3行:資料分析,廣州地區的職位列表的url,這個地址作為爬蟲的開始地址 第6行:該方法是爬蟲框架解析完成頁面後,進行呼叫的解析方法 第7行:獲取職位資訊的列表區域的物件 第10行:迴圈職位列表的資料,獲取對應的詳情地址的url 第12行:呼叫詳情地址的解析方法 第14行:獲取職位列表的下一頁的連結元素 第16行:繼續解析職位列表的下一頁的資料

2.3 招聘列表的詳情頁面讀取實現

 1def parse_detail(self, response):
 2        job_title=response.xpath('/html/body/div[3]/div[2]/div[2]/div/div[1]/h1/text()').extract_first()
 3        work_info=response.xpath('/html/body/div[3]/div[2]/div[2]/div/div[1]/p[2]/text()').extract()
 4        salary=response.xpath('/html/body/div[3]/div[2]/div[2]/div/div[1]/strong/text()').extract_first()
 5        company_name=response.xpath('/html/body/div[3]/div[2]/div[4]/div[1]/div[1]/a/p/text()').extract_first()
 6        company_type=response.xpath('/html/body/div[3]/div[2]/div[4]/div[1]/div[2]/p[1]/text()').extract_first()
 7        company_num=response.xpath('/html/body/div[3]/div[2]/div[4]/div[1]/div[2]/p[2]/text()').extract_first()
 8        business=response.xpath('/html/body/div[3]/div[2]/div[4]/div[1]/div[2]/p[3]/text()').extract_first()
 9        job_desc=response.xpath('/html/body/div[3]/div[2]/div[3]/div[1]/div//text()').extract()
10        l=JobItemLoad(JobItem())
11        if len(work_info)>=5:
12            l.add_value('work_place', work_info[0])
13            l.add_value('work_experience', work_info[1])
14            l.add_value('education', work_info[2])
15            l.add_value('headcount', work_info[3])
16            l.add_value('publish_date', work_info[4])
17        elif len(work_info)==4:
18            l.add_value('work_place', work_info[0])
19            l.add_value('work_experience', work_info[1])
20            l.add_value('headcount', work_info[2])
21            l.add_value('publish_date', work_info[3])
22        l.add_value('job_title', job_title)
23        l.add_value('salary', salary)
24        l.add_value('company_name', company_name)
25        l.add_value('company_type', company_type)
26        l.add_value('company_num', company_num)
27        l.add_value('business', business)
28        l.add_value('job_desc', "".join(job_desc))
29        l.add_value("url", response.url)
30        yield l.load_item()

第2-9行:獲取頁面解析的資料 第10行:生成ItemLoader物件 第11-29行:進行資料賦值 第30行:返回詳情的資料

2.4 爬取的資料處理

檔案items.py是對爬取的資料進行處理的檔案,由於爬取下列的檔案有一些特殊的字元,還有換行,空格等問題,通過這個檔案對資料進行一些處理

1def normalize_space(value):
2    move = dict.fromkeys((ord(c) for c in u"\xa0\n\t\r"))
3    output = value.translate(move)
4    return output
5class JobItem(scrapy.Item):
6    job_title = scrapy.Field(input_processor=MapCompose(normalize_space))#職位名稱
7    work_place=scrapy.Field(input_processor=MapCompose(normalize_space))#工作地點

第2行:定義要移除的字元 第6行:定義該欄位的處理的方法,用MapCompost可以定義多個處理方法

3 踩過的坑

3.1 匯出檔案亂碼

需要在settings.py檔案新增如下配置

FEED_EXPORT_ENCODING = "gb18030"

3.2 欄位處理沒有生效

需要在itemload.py檔案新增如下程式碼

default_output_processor = TakeFirst()

關注公眾號,回覆“51job”獲取專案程式碼 image.png