Search

Travel Tips

Lorem ipsum dolor sit amet, consectetur adipiscing elit.

Lifestyle

Lorem ipsum dolor sit amet, consectetur adipiscing elit.

Hotel Review

Lorem ipsum dolor sit amet, consectetur adipiscing elit.

获取酷狗top500名歌曲的名字,作者,排名,时间。并存入txt,csv,mysql。

爬虫简单一之获取酷狗top500名歌曲的名字,作者,排名,时间。并存入txt,csv,mysql。

 爬虫简单一之获取酷狗top500名歌曲的名字,作者,排名,时间。并存入txt,csv,mysql。



准备使用环境为Python3.6+csv+time+requests+beautifulsoup+os+pymysql

环境说明 安装所要使用的库,使用库的说明

  • csv库来实现存储csv文件

  •  time设置爬取间隔

  • request访问URL

  •  beautifulsoup解析页面

  •  os来创建文件夹来保存文件

  • pymysql来连接mysql数据库,把数据存储到mysql中

1.准备URL,打开https://www.kugou.com/yy/rank/home/1-8888.html?from=rank只能显示前22名

从图中看出的是只显示前22名,需要更多内容要下载客户端,但是通过改变1-8888.html中的数字1可以访问排行的前500名,一共需要24页。(他们后端可能并没有屏蔽其他的连接,仍然是可以访问的)

2.使用beautifulsoup的selector来获取所需要的具体内容,如歌手,歌名,歌曲时间等信息。(下面提供了一个简单而快捷的方法)

 2.1右击要选取的元素内容,点击检查可以看到具体的源代码中的具体位置

2.2再右击要选取的元素,选中copy会出现很多选项,常用的有copy selector和copy xpath,copy selector是使用beautifulsoup中的selector方法来选取元素时要使用的,而copy xpath是使用lxml库时使用xpath方法时使用的,使用这一个方法可以提高代码的生产效率。本文使用的是beautifulsoup的selector方法。

2.3下面是使用selector的具体代码(先使用beautiful soup来封装一下text再使用selector方法来选取。通过一下几行代码就可以把排名,名字,时间和歌手选取出来(歌手的名字和歌曲的名字在一个标签中使用-来分隔,选取出来之后可以使用split方法对字符串进行切分)。


```
html = requests.get(url, headers=headers)
    soup = BeautifulSoup(html.text, 'lxml')
    ranks = soup.select('#rankWrap > div.pc_temp_songlist > ul > li > span.pc_temp_num')
    names = soup.select('#rankWrap > div.pc_temp_songlist > ul > li > a')
    times = soup.select('#rankWrap > div.pc_temp_songlist > ul > li > span.pc_temp_tips_r > span')
```

源代码中的使用-连接的歌曲名个歌手名

分隔分别选出来的歌手名字和歌曲名字


```
name = names[i].get_text().strip().split('-')[1]
        signer = names[i].get_text().strip().split('-')[0]
```

 3.当得到所有的信息之后,接下来就是要存储到文件当中,可以使用txt,csv,mysql等文件进行存储。

 3.1存储到txt中(在存储到txt文件中时,使用的当写入时,只能写入一个元素,所以要把所有元素使用+号来连接起来再使用f.write()来存储到txt中去)


```
# 封装成函数
def write_txt(message):
    with open('../tmp/_02_kugou/kuGou.txt', 'a+') as f:
        f.write(message + '\n')
# 在进行调用时要使用加号把多个元素连接
write_txt(rank + name + signer + time1)
```

 3.2存储到csv中首先open()函数打开当前路径下的名字为../tmp/_02_kugou/kuGou.csv的文件,如果不存在这个文件,则创建它,返回f文件对象。csv.writer(f)返回writer对象csv_writer。writerow()方法是一行一行写入,writerows方法是一次写入多行。


```
def write_csv(rank, name, signer, time1):
    with open('../tmp/_02_kugou/kuGou.csv', 'a+') as f:
        csv_writer = csv.writer(f)
        csv_writer.writerow([rank, name, signer, time1])
```

 3.3存储到mysql中,使用pymysql的connect方法传入多个参数之后连接数据库,创建一个游标,使用游标来执行sql语句,把获取到的值存储到数据库中。


```
def writer_mysql(rank, name, signer, time1):
    con = pymysql.connect(user='root', password='root', db='spider', host='localhost', port=3306, charset='utf8')
    cursor = con.cursor()
    try:
        sql = '''INSERT INTO kugou(rank, name, signer, time) VALUES('%d', '%s', '%s', '%s')'''
        cursor.execute(sql % (int(rank), name, signer, pymysql.escape_string(time1)))
        con.commit()
    except pymysql.err.IntegrityError:
        pass
    cursor.close()
    con.close()
```

注意在向mysql存储数据的时候出现 pymysql.err.ProgrammingError: 1064 (Python字符串转义问题)时

使用模块MySQLdb自带的针对mysql的字符转义函数 escape_string把要存储的元素转义一下如


```
        cursor.execute(sql % (int(rank), name, signer, pymysql.escape_string(time1)))
```

如果还是出现pymysql.err.ProgrammingError: 1064 错误就使用三引号’‘’ 来括取sql语句。应该就可以解决这个错误了


```
sql = '''INSERT INTO kugou(rank, name, signer, time) VALUES('%d', '%s', '%s', '%s')'''
        cursor.execute(sql % (int(rank), name, signer, pymysql.escape_string(time1)))
```


 4.定义一个main函数,迭代所有的要爬取的URL链接,给爬虫函数传入链接,运行爬虫,作为一个文明的人,最好爬虫一次使用time.sleep()休息一段时间,一是为了不给服务器造成很大的客流量,二是爬虫过快,封禁ip等因素导致爬虫失败。

```
if __name__ == '__main__':
    urls = ['https://www.kugou.com/yy/rank/home/' + str(i) + '-8888.html' for i in range(1, 24)]
    for url in urls:
        print(url)
        get_message(url)
        time.sleep(5)
```

 5.完整代码


```
import csv
import time
import requests
from bs4 import BeautifulSoup
import os
import pymysql
if not os.path.exists('../tmp/_02_kugou'):
    os.makedirs('../tmp/_02_kugou')
headers = {
    'User-Agent': 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/73.0.3683.86 Safari/537.36',
}
def get_message(url):
    html = requests.get(url, headers=headers)
    soup = BeautifulSoup(html.text, 'lxml')
    ranks = soup.select('#rankWrap > div.pc_temp_songlist > ul > li > span.pc_temp_num')
    names = soup.select('#rankWrap > div.pc_temp_songlist > ul > li > a')
    times = soup.select('#rankWrap > div.pc_temp_songlist > ul > li > span.pc_temp_tips_r > span')
    # print(len(ranks))
    for i in range(0, len(ranks)):
        rank = ranks[i].get_text().strip()
        name = names[i].get_text().strip().split('-')[1]
        signer = names[i].get_text().strip().split('-')[0]
        time1 = times[i].get_text().strip()
        write_txt(rank + name + signer + time1)
        write_csv(rank, name, signer, time1)
        writer_mysql(rank, name, signer, time1)
        # print(rank, name, signer, time1)
def write_txt(message):
    with open('../tmp/_02_kugou/kuGou.txt', 'a+') as f:
        f.write(message + '\n')
def write_csv(rank, name, signer, time1):
    with open('../tmp/_02_kugou/kuGou.csv', 'a+') as f:
        csv_writer = csv.writer(f)
        csv_writer.writerow([rank, name, signer, time1])
def writer_mysql(rank, name, signer, time1):
    con = pymysql.connect(user='root', password='root', db='spider', host='localhost', port=3306, charset='utf8')
    cursor = con.cursor()
    try:
        sql = '''INSERT INTO kugou(rank, name, signer, time) VALUES('%d', '%s', '%s', '%s')'''
        cursor.execute(sql % (int(rank), name, signer, pymysql.escape_string(time1)))
        con.commit()
    except pymysql.err.IntegrityError:
        pass
    cursor.close()
    con.close()
if __name__ == '__main__':
    urls = ['https://www.kugou.com/yy/rank/home/' + str(i) + '-8888.html' for i in range(1, 24)]
    for url in urls:
        print(url)
        get_message(url)
        time.sleep(5)
```


这是一个简介
    互联网冲浪金牌选手。赖床世锦赛纪录保持者,拖延俱乐部顶级VIP,夜宵外卖一级鉴赏师,国家脱单脱贫重点扶持对象,中央戏精学院优秀学生,亚洲酸柠檬推广大使,国家一级退堂鼓表演艺术家。
评论 (125)
评论

我是 s enim interduante quis metus. Duis porta ornare nulla ut bibendum

Rosie

6 minutes ago

Sed ac lorem felis. Ut in odio lorem. Quisque magna dui, maximus ut commodo sed, vestibulum ac nibh. Aenean a tortor in sem tempus auctor

Agatha Christie

December 4, 2020 at 3:12 pm

Sed ac lorem felis. Ut in odio lorem. Quisque magna dui, maximus ut commodo sed, vestibulum ac nibh. Aenean a tortor in sem tempus auctor

Steven

December 4, 2020 at 3:12 pm

Donec in ullamcorper quam. Aenean vel nibh eu magna gravida fermentum. Praesent eget nisi pulvinar, sollicitudin eros vitae, tristique odio.

Danielle Steel

December 4, 2020 at 3:12 pm