• Python3爬虫之爬取某一路径的所有html文件


    要离线下载易百教程网站中的所有关于Python的教程,需要将Python教程的首页作为种子url:http://www.yiibai.com/python/,然后按照广度优先(广度优先,使用队列;深度优先,使用栈),依次爬取每一篇关于Python的文章。为了防止同一个链接重复爬取,使用集合来限制同一个链接只处理一次。
    使用正则表达式提取网页源码里边的文章标题和文章url,获取到了文章的url,使用Python根据url生成html文件十分容易。


    1. import re
    2. import urllib.request
    3. import urllib
    4. from collections import deque
    5. # 保存文件的后缀
    6. SUFFIX='.html'
    7. # 提取文章标题的正则表达式
    8. REX_TITLE=r'<title>(.*?)</title>'
    9. # 提取所需链接的正则表达式
    10. REX_URL=r'/python/(.+?).html'
    11. # 种子url,从这个url开始爬取
    12. BASE_URL='http://www.yiibai.com/python/'
    13. # 将获取到的文本保存为html文件
    14. def saveHtml(file_name,file_content):
    15. #    注意windows文件命名的禁用符,比如 /
    16.     with open (file_name.replace('/','_')+SUFFIX,"wb") as f:
    17. #   写文件用bytes而不是str,所以要转码
    18.         f.write(bytes(file_content, encoding = "utf8"))
    19. #   获取文章标题
    20. def getTitle(file_content):
    21.     linkre = re.search(REX_TITLE,file_content)
    22.     if(linkre):
    23.         print('获取文章标题:'+linkre.group(1))
    24.         return linkre.group(1)
    25.  
    26. #   爬虫用到的两个数据结构,队列和集合
    27. queue = deque()
    28. visited = set()
    29. #   初始化种子链接 
    30. queue.append(BASE_URL)
    31. count = 0
    32.  
    33. while queue:
    34.   url = queue.popleft()  # 队首元素出队
    35.   visited |= {url}  # 标记为已访问
    36.  
    37.   print('已经抓取: ' + str(count) + '   正在抓取 <---  ' + url)
    38.   count += 1
    39.   urlop = urllib.request.urlopen(url)
    40.   # 只处理html链接
    41.   if 'html' not in urlop.getheader('Content-Type'):
    42.     continue
    43.  
    44.   # 避免程序异常中止
    45.   try:
    46.     data = urlop.read().decode('utf-8')
    47.     title=getTitle(data);
    48.     # 保存文件
    49.     saveHtml(title,data)
    50.   except:
    51.     continue
    52.  
    53.   # 正则表达式提取页面中所有链接, 并判断是否已经访问过, 然后加入待爬队列
    54.   linkre = re.compile(REX_URL)
    55.   for sub_link in linkre.findall(data):
    56.       sub_url=BASE_URL+sub_link+SUFFIX;
    57. # 已经访问过,不再处理
    58.       if sub_url in visited:
    59.           pass
    60.       else:
    61.           # 设置已访问
    62.           visited |= {sub_url}
    63.           # 加入队列
    64.           queue.append(sub_url)
    65.           print('加入队列 --->  ' + sub_url)



  • 相关阅读:
    asp.net 中的viewstate用法?
    .net中 过滤 指定 字符串
    js中replace的用法
    restart
    外部函数
    JQuery实现Ajax 根据商品名称自动显示价格
    ListView中命令行按钮应用;
    GridView中获取行数和列数
    全局应用程序类Global
    如何获取gridview中模板列中控件的值?
  • 原文地址:https://www.cnblogs.com/jpfss/p/9235209.html
Copyright © 2020-2023  润新知