鱼C论坛

 找回密码
 立即注册
查看: 6193|回复: 5

[已解决]关于爬取小说的章节排序和格式问题

[复制链接]
发表于 2018-3-12 17:03:24 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
本帖最后由 wongyusing 于 2018-3-12 17:49 编辑

代码如下:
  1. #!/usr/bin/env python

  2. # encoding: utf-8
  3. # Sing
  4. from bs4 import BeautifulSoup as Soup
  5. import re
  6. import urllib
  7. import requests



  8. def url_open(url):  # 网页打开函数,以防被禁
  9.     headers = {
  10.         'User-Agent': "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/62.0.3202.75 Safari/537.36"}
  11.     req = requests.get(url, headers=headers)
  12.     req.encoding = 'utf-8'
  13.     return req.text

  14. def get_book_list(url):#获取书籍的url并提取出修订版的url后缀列表
  15.     ret = url_open(url)
  16.     reg = r'<p class="title"><a href="(.*?)">.*?</a></p>'
  17.     req = re.findall(reg, ret)
  18.     return req[0:15]

  19. def get_chapter(url_char):#获取章节后缀和书名
  20.     ret = url_open(url_char)
  21.     reg = r'<li><a href="(.*?)">.*?</a></li>'
  22.     char = re.findall(reg, ret)#章节后缀
  23.     reg = r'<h1 class="title"><span>(.*?)</span>.*?</h1>'
  24.     name = re.findall(reg, ret)#书名

  25.     return char,name

  26. def getContent(html):#获取章节名和章节内容
  27.     ret = url_open(html)
  28.     soup = Soup(ret,'html.parser')
  29.     title = soup.find('div', class_='mbtitle').contents[-1].string or soup.find('h1', class_='title').contents[-1].string #获取标签 #获取标签
  30.     #上面是获取章节名这里总是报错误,说无法获取内容
  31.     content = soup.find('div',class_='vcon').strings #获取内容
  32.    
  33.     return title,content

  34. def writeFile(title,content,name):
  35.     with open(name +'.txt','a',encoding='utf-8')as ganrong:
  36.         #设置文件编码,避免写入时乱码
  37.         ganrong.write('\n'+title+'\n')
  38.         for line in content:
  39.             ganrong.write(line)
  40.     print('%s was writed ..'%title,name)


  41. def getganrong(): #主函数
  42.     url = 'http://www.jinyongwang.com/book/'
  43.     baseurl ='http://www.jinyongwang.com'
  44.     #ppp = url_open(url)
  45.     #print(ppp)
  46.     book_list = get_book_list(url)
  47.     #print(book_list)
  48.     for i in book_list:
  49.         url_char = baseurl + i
  50.         char, name = get_chapter(url_char)
  51.         for page in char:
  52.             html = baseurl + page
  53.             title, content = getContent(html)
  54.             writeFile(title, content,name[0])







  55. if __name__ == "__main__":
  56.     getganrong()

复制代码


问题如下:
1.小说文件爬取下来后,文本格式不好看,不能分好段落,全部连成一坨,求解决方案。
2.如果我想用scrapy框架的话,该如何写?我根据网上教程去写,运行的爬虫全部都报“DNS”错误,有好心人给个可以运行的scrapy爬虫让我测试和参考一下吗??
3.在获取标签的BS4表达式中总是报错误,具体位置在37行代码中。
错误信息如下:
第05章 老鼠汤 was writed .. 连城诀小说
第06章 血刀老祖 was writed .. 连城诀小说
Traceback (most recent call last):
  File "/home/sing/桌面/untitled1/bbbbb.py", line 74, in <module>
    getganrong()
  File "/home/sing/桌面/untitled1/bbbbb.py", line 64, in getganrong
    title, content = getContent(html)
  File "/home/sing/桌面/untitled1/bbbbb.py", line 37, in getContent
    title = soup.find('div', class_='mbtitle').contents[-1].string or soup.find('h1', class_='title').contents[-1].string #获取标签 #获取标签
AttributeError: 'NoneType' object has no attribute 'contents'
最佳答案
2018-3-12 23:18:28
本帖最后由 纳兰小寒 于 2018-3-12 23:37 编辑

写入每一行数据的时候,末尾加个换行符
  1. def writeFile(title,content,name):
  2.     with open(name +'.txt','a',encoding='utf-8')as ganrong:
  3.         #设置文件编码,避免写入时乱码
  4.         ganrong.write('\n'+title+'\n')#加个换行符
  5.         for line in content:
  6.             ganrong.write(line+'\n')
  7.     print('%s was writed ..'%title,name)
复制代码


抓到了你说的第二个问题,爬虫返回的是“<title>500 Internal Server Error</title>”
换IP或者换个浏览器头就好了,再或者在采集的时候加个间隔时间
  1. def url_open(url):  # 网页打开函数,以防被禁
  2.     headers = {
  3.         'User-Agent': rand_ua()}
  4.     req = requests.get(url, headers=headers)
  5.     req.encoding = 'utf-8'
  6.     return req.text

  7. def rand_ua():
  8.     headers = ["Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/62.0.3202.75 Safari/537.36"]
  9.     headers.append('Mozilla/5.0 (Windows NT 6.1; rv:53.0) Gecko/20100101 Firefox/53.0')
  10.     headers.append('Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/56.0.2924.87 Safari/537.36')
  11.     headers.append('Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.81 Safari/537.36')
  12.     headers.append('Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Ubuntu Chromium/57.0.2987.98 Chrome/57.0.2987.98 Safari/537.36')
  13.     return headers[rd.randint(0,4)]
复制代码

网页上的排版

网页上的排版

手机上的排版

手机上的排版

手机上的排版

手机上的排版
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2018-3-12 17:09:13 | 显示全部楼层
本帖最后由 °蓝鲤歌蓝 于 2018-3-12 17:18 编辑

1.贴图看看
2.http://blog.csdn.net/mr_blued/article/list?t=1
3.报错信息是什么?
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2018-3-12 17:22:35 | 显示全部楼层
本帖最后由 wongyusing 于 2018-3-12 17:51 编辑


等等,报错是不定的,有时会报错,有时不报,好气人的,我先弄个错误信息再发出来。
有错误信息了
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2018-3-12 19:15:14 | 显示全部楼层
wongyusing 发表于 2018-3-12 17:22
等等,报错是不定的,有时会报错,有时不报,好气人的,我先弄个错误信息再发出来。
有错误信息了
  1. import requests
  2. import re


  3. url = 'http://www.jinyongwang.com/fei/484.html'
  4. headers = {'User-Agent':'Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36\
  5.             (KHTML, like Gecko) Chrome/64.0.3282.119 Safari/537.36'
  6.            }
  7. response = requests.get(url, headers=headers)
  8. p = r'<p>(.*?)</p>'
  9. content = re.findall(p, response.text)

  10. for i in content:
  11.     print(i+'\n')
复制代码
TIM截图20180312191538.png
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2018-3-12 23:18:28 | 显示全部楼层    本楼为最佳答案   
本帖最后由 纳兰小寒 于 2018-3-12 23:37 编辑

写入每一行数据的时候,末尾加个换行符
  1. def writeFile(title,content,name):
  2.     with open(name +'.txt','a',encoding='utf-8')as ganrong:
  3.         #设置文件编码,避免写入时乱码
  4.         ganrong.write('\n'+title+'\n')#加个换行符
  5.         for line in content:
  6.             ganrong.write(line+'\n')
  7.     print('%s was writed ..'%title,name)
复制代码


抓到了你说的第二个问题,爬虫返回的是“<title>500 Internal Server Error</title>”
换IP或者换个浏览器头就好了,再或者在采集的时候加个间隔时间
  1. def url_open(url):  # 网页打开函数,以防被禁
  2.     headers = {
  3.         'User-Agent': rand_ua()}
  4.     req = requests.get(url, headers=headers)
  5.     req.encoding = 'utf-8'
  6.     return req.text

  7. def rand_ua():
  8.     headers = ["Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/62.0.3202.75 Safari/537.36"]
  9.     headers.append('Mozilla/5.0 (Windows NT 6.1; rv:53.0) Gecko/20100101 Firefox/53.0')
  10.     headers.append('Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/56.0.2924.87 Safari/537.36')
  11.     headers.append('Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.81 Safari/537.36')
  12.     headers.append('Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Ubuntu Chromium/57.0.2987.98 Chrome/57.0.2987.98 Safari/537.36')
  13.     return headers[rd.randint(0,4)]
复制代码
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2018-3-13 01:25:30 | 显示全部楼层
纳兰小寒 发表于 2018-3-12 23:18
写入每一行数据的时候,末尾加个换行符

抓到了你说的第二个问题,爬虫返回的是“500 Internal Server Er ...

还是不行,每次下载到大概30到40章左右呢,就会停止,报错的意思没看错的话就是爬虫无法获取内容。
按照顺序来看,到天龙八部第一章到第十章左右就会停止,1点12分左右就出现了反爬机制拒绝访问了,但浏览器还是可以访问。我还是学一下用scrapy来分布式爬虫试一下。报错图如下:

停止信息

停止信息
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-4-30 23:41

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表