目錄 前言 本次案例實現目標 最基本思路流程: <通用> 一. 數據來源分析 二. 代碼實現步驟過程: 代碼實現基本四大步驟 代碼實現 獲取書籍詳情信息 發送請求 解析數據 保存數據 運行代碼得到結果 可視化圖表 書籍總體價格區間 各個出版社書籍數量柱狀圖 電子書版本占比 書籍評論數據 詞雲 對於本 ...
目錄
對於本篇文章有疑問的同學可以加【資料白嫖、解答交流群:326937069】
前言
本次案例實現目標
- 書籍基本數據
- 實現可視化圖表
- 書籍評論數據
- 評論可以實現詞雲圖
最基本思路流程: <通用>
一. 數據來源分析
- 只有當你知道你想要數據內容, 是來自於哪裡的時候, 才能通過代碼請求得到數據
- 打開 F12 開發者工具進行抓包分析
- 通過關鍵字進行搜索查詢 數據包是請求那個url地址
二. 代碼實現步驟過程: 代碼實現基本四大步驟
- 發送請求, 模擬瀏覽器對於url地址<剛剛分析得到的url地址>發送請求
- 獲取數據, 獲取伺服器返迴響應數據 —> 開發者工具裡面 response
- 解析數據, 提取我們想要的數據內容 —> 書籍基本信息
- 保存數據, 把數據內容保存到表格裡面
代碼實現
獲取書籍詳情信息
發送請求
url = f'http://bang.dangdang.com/books/bestsellers/01.00.00.00.00.00-recent7-0-0-1-1' # 代碼模擬瀏覽器發送請求 ---> headers請求頭 <可以複製粘貼> headers = { # User-Agent 用戶代理 表示瀏覽器基本身份標識 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.0.0 Safari/537.36' } # 發送請求 response = requests.get(url=url, headers=headers)
解析數據
# 轉換數據類型 ---> 可解析對象 selector = parsel.Selector(response.text) # 第一次提取, 獲取所有li標簽 lis = selector.css('.bang_list_mode li') # 返回列表 # for迴圈遍歷, 把列表裡面的元素一個一個提取出來 for li in lis: title = li.css('.name a::attr(title)').get() # 標題/書名 recommend = li.css('.tuijian::text').get().replace('推薦', '') # 推薦 star = li.css('.star a::text').get().replace('條評論', '') # 評價 author = li.css('div:nth-child(5) a:nth-child(1)::attr(title)').get() # 作者 date = li.css('div:nth-child(6) span::text').get() # 出版日期 press = li.css('div:nth-child(6) a::text').get() # 出版社 price_r = li.css('.price .price_r::text').get() # 原價 price_n = li.css('.price .price_n::text').get() # 售價 price_e = li.css('.price_e span::text').get() # 電子書價格 href = li.css('.name a::attr(href)').get() # 詳情頁 dit = { '標題': title, '推薦': recommend, '評價': star, '作者': author, '出版日期': date, '出版社': press, '原價': price_r, '售價': price_n, '電子書價格': price_e, '詳情頁': href, } csv_writer.writerow(dit) print(dit)
保存數據
f = open('書籍.csv', mode='a', encoding='utf-8', newline='') csv_writer = csv.DictWriter(f, fieldnames=[ '標題', '推薦', '評價', '作者', '出版日期', '出版社', '原價', '售價', '電子書價格', '詳情頁', ]) # 寫入表頭 csv_writer.writeheader()
運行代碼得到結果
可視化圖表
書籍總體價格區間
pie1 = ( Pie(init_opts=opts.InitOpts(theme='dark',width='1000px',height='600px')) .add('', datas_pair_1, radius=['35%', '60%']) .set_series_opts(label_opts=opts.LabelOpts(formatter="{b}:{d}%")) .set_global_opts( title_opts=opts.TitleOpts( title="噹噹網書籍\n\n原價價格區間", pos_left='center', pos_top='center', title_textstyle_opts=opts.TextStyleOpts( color='#F0F8FF', font_size=20, font_weight='bold' ), ) ) .set_colors(['#EF9050', '#3B7BA9', '#6FB27C', '#FFAF34', '#D8BFD8', '#00BFFF', '#7FFFAA']) ) pie1.render_notebook()
pie1 = ( Pie(init_opts=opts.InitOpts(theme='dark',width='1000px',height='600px')) .add('', datas_pair_2, radius=['35%', '60%']) .set_series_opts(label_opts=opts.LabelOpts(formatter="{b}:{d}%")) .set_global_opts( title_opts=opts.TitleOpts( title="噹噹網書籍\n\n售價價格區間", pos_left='center', pos_top='center', title_textstyle_opts=opts.TextStyleOpts( color='#F0F8FF', font_size=20, font_weight='bold' ), ) ) .set_colors(['#EF9050', '#3B7BA9', '#6FB27C', '#FFAF34', '#D8BFD8', '#00BFFF', '#7FFFAA']) ) pie1.render_notebook()
各個出版社書籍數量柱狀圖
bar=( Bar(init_opts=opts.InitOpts(height='500px',width='1000px',theme='dark')) .add_xaxis(counts.index.tolist()) .add_yaxis( '出版社書籍數量', counts.values.tolist(), label_opts=opts.LabelOpts(is_show=True,position='top'), itemstyle_opts=opts.ItemStyleOpts( color=JsCode("""new echarts.graphic.LinearGradient( 0, 0, 0, 1,[{offset: 0,color: 'rgb(255,99,71)'}, {offset: 1,color: 'rgb(32,178,170)'}]) """ ) ) ) .set_global_opts( title_opts=opts.TitleOpts( title='各個出版社書籍數量柱狀圖'), xaxis_opts=opts.AxisOpts(name='書籍名稱', type_='category', axislabel_opts=opts.LabelOpts(rotate=90), ), yaxis_opts=opts.AxisOpts( name='數量', min_=0, max_=29.0, splitline_opts=opts.SplitLineOpts(is_show=True,linestyle_opts=opts.LineStyleOpts(type_='dash')) ), tooltip_opts=opts.TooltipOpts(trigger='axis',axis_pointer_type='cross') ) .set_series_opts( markline_opts=opts.MarkLineOpts( data=[ opts.MarkLineItem(type_='average',name='均值'), opts.MarkLineItem(type_='max',name='最大值'), opts.MarkLineItem(type_='min',name='最小值'), ] ) ) ) bar.render_notebook()
電子書版本占比
c = ( Liquid() .add("lq", [1-per], is_outline_show=False) .set_global_opts(title_opts=opts.TitleOpts(title="電子書版本占比")) ) c.render_notebook()
書籍評論數據
for page in range(1, 11): time.sleep(1) # 確定請求url地址 url = 'http://product.dangdang.com/index.php' # 請求參數 data = { 'r': 'comment/list', 'productId': '29129370', 'categoryPath': '01.43.79.01.00.00', 'mainProductId': '29129370', 'mediumId': '0', 'pageIndex': page, 'sortType': '1', 'filterType': '1', 'isSystem': '1', 'tagId': '0', 'tagFilterCount': '0', 'template': 'publish', 'long_or_short': 'short', } # headers 請求頭 headers = { 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.0.0 Safari/537.36' } # 發送請求 response = requests.get(url=url, params=data, headers=headers) # response.json() 獲取響應json字典數據 鍵值對取值 ---> 根據冒號左邊的內容, 提取冒號右邊的內容 html_data = response.json()['data']['list']['html'] content_list = re.findall("<span><a href=.*?' target='_blank'>(.*?)</a></span>", html_data) with open('評論.txt', mode='a', encoding='utf-8') as f: f.write('\n'.join(content_list)) f.write('\n') print(content_list)
詞雲
import jieba # 分詞模塊 pip install jieba import wordcloud import imageio img = imageio.imread('123.png') # wordcloud # 1. 打開文件 獲取彈幕數據 # mode='r' 一定要寫嗎 不一定 預設以 r # encoding='' 要寫嗎? 肯定要的 f = open('評論.txt', mode='r', encoding='utf-8') txt = f.read() # print(txt) # 2. jieba分詞 分割辭彙 txt_list = jieba.lcut(txt) # print(txt_list) # 列表轉字元串怎麼轉 string = ' '.join(txt_list) # print(string) # 3. 詞雲圖設置 wc = wordcloud.WordCloud( width=800, # 寬度 height=500, # 高度 background_color='white', # 背景顏色 mask=img, # 設置圖片樣式 font_path='msyh.ttc', scale=15, stopwords={'了', '的'}, contour_width=5, contour_color='red' ) # 4. 輸入文字內容 (字元串的形式) wc.generate(string) # 5. 輸出圖片 wc.to_file('output2.png')