zoukankan      html  css  js  c++  java
  • 零python基础--爬虫实践总结

      网络爬虫,是一种按照一定的规则,自动地抓取万维网信息的程序或者脚本。

      爬虫主要应对的问题:1.http请求 2.解析html源码 3.应对反爬机制。

    觉得爬虫挺有意思的,恰好看到知乎有人分享的一个爬虫小教程:https://zhuanlan.zhihu.com/p/20410446  立马学起!

    主要步骤:

    1、按照教程下载python、配置环境变量,学习使用pip命令、安装开发ide:pycharm

    2、学习使用python发送请求获取页面

    3、使用chrome开发者工具观察页面结构特征,使用beautifulsoup解析页面

    4、保存页面到本地文件

    遇到的主要问题:

    1.python基本语法:变量、函数、循环、异常、条件语句、创建目录、写文件。可以参考《Python基础教程

    2.python缩进很重要,缩进决定语句分组和层次,在循环的时候尤其看清楚。

    3.编码格式:从代码编辑、到网页内容、中文文件名,无处不有编码格式的问题。可以参考 《Python编码问题整理

    4.beautifulsoup使用。可以参考 《Python爬虫利器二之Beautiful Soup的用法

    5.抓取规则失效,重新分析失效页面,重新选择页面特征。

     实践,用爬虫获取网页上的试题(自动抓取下一页)代码:

    # encoding=utf8 
    #设置编辑源py文件的编码格式为utf8
    import requests, sys, chardet, os, time, random, time
    from bs4 import BeautifulSoup
    
    reload(sys)  #必须要重新加载
    sys.setdefaultencoding("utf8")
    
    print sys.getdefaultencoding(), sys.getfilesystemencoding()  # utf8 mbcs:MBCS(Multi-ByteChactacterSystem,即多字节字符系统)它是编码的一种类型,而不是某个特定编码的名称
    path = os.getcwd() #获取当前文件所在目录
    newPath = os.path.join(path, "Computer")
    if not os.path.isdir(newPath):
        os.mkdir(newPath) #新建文件夹
    destFile = unicode(newPath + "/题目.docx","utf-8) #存为word也可以,不过后续用office编辑后,保存的时候总需要另存为;用unicode()后,文件名取中文名不会变成乱码
    
    #最常见的模拟浏览器,伪装headers
    headers = {
        'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_2) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/47.0.2526.80 Safari/537.36'
    }
    
    
    def downLoadHtml(url):
        html = requests.get(url, headers=headers)
        content = html.content
        contentEn = chardet.detect(content).get("encoding", "utf-8")
        # print contentEn  #GB2312
        try:
            tranCon = content.decode(contentEn).encode(sys.getdefaultencoding())#转换网页内容编码格式;消除中文乱码
        except Exception:
            return content #用了编码转换,为什么还是存在少量页面异常?
        # print tranCon
        else:
            return tranCon
    
    
    def parseHtml(url):
        # print url, "now"
        content = downLoadHtml(url)
        contentEn = chardet.detect(content).get("encoding", "utf-8")
        soup = BeautifulSoup(content, "html.parser")  # soup.name  [document] BeautifulSoup 对象表示的是一个文档的全部内容
        # 查找下一页url
        theUL = soup.find("ul", {"class": "con_updown"})
        theLi = theUL.find("li")
        href = theLi.find("a").get("href")
        preUrl = None
        if href:
            print href, "next"
            preUrl = href
    
        # 查找所需内容
        topics = []
        try:
            divCon = soup.find("div", attrs={"class": "con_nr"})
            if divCon:
                subjects = divCon.find_all("p")  # __len__属性不是整数,而是:method-wrapper '__len__' of ResultSet object
                index = 0 #借助index标识查找第几个,还有别的方式?
                for res in subjects:
                    #跳过不想要的导读行内容
                    if index == 0 and res.string == "【导读】":
                        index = 1  # 跳出循环也要加1
                        continue  # 跳过 导读
                    topic = res.string  # res有子标签及文本,就会返回None
                    if topic:
                        #按需要,只留下纯文本,保存到文件
                        try:
                            parsed = topic.decode(contentEn).encode("utf8")
                        except Exception:
                            topics.append("本页面解码有误,请自行查看: " + url + "
    ")  # '%d' %index str(index) 数字转字符串
                            break
                        else:
                            topics.append(parsed + "
    ")
                    index = index + 1
                topics.append("
    ")
            else:
                topics.append("本页面查找试题有误,请自行查看: " + url + "
    ")
        except Exception:
            topics.append("本页面解析有误,请自行查看: " + url + "
    ")
    
        fp = open(destFile, 'a')  # a追加写
        fp.writelines(topics)
        fp.close()
        return preUrl
    
    
    #执行.py文件的入口
    if __name__ == '__main__':
        i = 0 #记录处理了多少页面
        next = "http://xxxxx/1.html" #起始页面
        print "start time:", time.strftime('%Y-%m-%d %H:%M:%S', time.localtime(time.time())) #打印时间,看跑了多久
        print next, "start"
        while next and i < 1000:
            next = parseHtml(next)
            i = i + 1
            #sTime = random.randint(3, 8) #随机整数 [3,8)
            #time.sleep(sTime)  # 休息:防反爬
        print "end time:", time.strftime('%Y-%m-%d %H:%M:%S', time.localtime(time.time()))
        print "i =", i, "url:", next
        fp = open(destFile, 'a')  # a追加写
        fp.writelines(["lastPage:" + str(next) + "
    ", "total:" + str(i) + "
    "])  # None及数字:无法和字符串用 + 拼接
        fp.close()

     抓取博客内容,未完待续……

    #encoding=utf8
    import sys,requests,chardet
    from bs4 import BeautifulSoup
    reload(sys)
    sys.setdefaultencoding("utf8")
    
    url = "http://www.cnblogs.com/"
    agent = "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/45.0.2454.101 Safari/537.36"
    headers={'User-Agent': agent}
    data={'user': '', 'pass': ''}
    syscode = sys.getdefaultencoding()
    print syscode
    titles = []
    def getHtml(url):
         if url:
            response = requests.post(url,headers=headers,data=data)
            if response.status_code != 200:
                 return None
            content = response.content
            #print content
            contentEn = chardet.detect(content).get("encoding", "utf-8")
            try:
               tranCon = content.decode(contentEn).encode(syscode)
            except Exception:
                return content 
            else:
                #print tranCon
                return tranCon
         else:
             return None
    
    
    def parseHtml(html):
        if html:
            soup = BeautifulSoup(html,"html.parser")
            tags = soup.find("div",attrs={"class":"catListTag"}).find_all("a")
            for tag in tags:
                href = tag.get("href")
                titles.add(href)
    
    def getWords():
        strs = ""
        if titles.__len__() != 0:
            for item in titles:
                strs = strs + item;
            tags = jieba.analyse.extract_tags(strs,topK=100,withWeight=True)
            for item in tags:
                print(itme[0] + "    "  + str(int(item[1]*1000)))
    
    
    if __name__ == '__main__':
        html = getHtml(url)
        parseHtml(html)
        getWords
  • 相关阅读:
    SignalR
    convert NameValueCollection/Dictionary<string, object> to JSON string
    CG标准函数库
    Unity shader学习之Alpha Blend
    Unity shader学习之Alpha Test
    Unity shader学习之遮罩纹理
    Unity shader学习之渐变纹理
    Unity shader学习之切线空间下计算凹凸映射
    Unity shader学习之Blinn-Phong光照模型
    Unity shader学习之高光反射光照模型
  • 原文地址:https://www.cnblogs.com/yongwangzhiqian/p/6686882.html
Copyright © 2011-2022 走看看