美文网首页
2019-06-29—关于json,csv,多线程,ajax

2019-06-29—关于json,csv,多线程,ajax

作者: ElfACCC | 来源:发表于2019-06-29 19:32 被阅读0次

import json

python对象转为json。json.dunps()

json可以dump到文件中。json.dump()

image.png

如果有中文,指定编码,和关掉ASCII码

只有基本数据类型才能转换成json,类不行

image.png

json转成python对象,json.loads()

image.png

从文件中加载json。json.load()

image.png

import csv

读取csv文件,csv.reader()

有标题
无标题,用next函数

获取其中几项,通过索引

image.png

用键名获取,用DictReader()

image.png

csv读的两种方式:

image.png

csv写:encoding编码让他正常显示中文,newline默认是换行,要写成空字符串就不会产生新的空行。writerow写一行,把头写进去,writerows写多行

image.png

字典的方式来写:DictWriter,要手动传入表头

image.png

csv写的两种方式:

image.png

import threading

传统方式:

image.png

多线程方式,方法一:

先创建线程,再start。注意target传的参数是函数名,不能加括号(),因为如果加了括号,传的参数就是函数的返回值了


image.png

多线程方法二:

步骤:继承Thread类,重写run方法,创建线程,最后start


image.png

多线程中的全局变量要用global修饰才能修改

image.png

如果range变大就会出问题:


image.png

解决方法:加锁(用在修改全局变量的地方,如果只是访问全局变量就不需要加锁)

image.png

生产者与消费者模式lock版本,耗cpu(加锁)

image.png

condition的生产者与消费者,添加阻塞状态,wait()会释放锁,等待被notify,notify函数不会释放锁,还是要手动release,只是通知wait马上可以加锁了

image.png

wait函数排队获取锁,notify唤醒wait,再通过while条件判断现在还满足条件否,若不满足,继续wait

from queue import Queue

Queue线程安全队列

image.png

get和put是阻塞的,就是说,如果没有,就等待



下载表情包的爬虫

1、传统的方式

image.png
image.png

完整代码:

import re
import requests
from lxml import etree
from urllib import request
import urllib
import os

def parse_page(url):
    headers = {
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/75.0.3770.100 Safari/537.36'
    }
    response = requests.get(url,headers)
    text = response.text
    html = etree.HTML(text)
    imgs = html.xpath("//div[@class='page-content text-center']//img[@class!='gif']")
    opener=urllib.request.build_opener()
    opener.addheaders=[('User-Agent','Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/75.0.3770.100 Safari/537.36')]
    urllib.request.install_opener(opener)
    for img in imgs:
        img_url = img.get('data-original')
        img_suffix = os.path.splitext(img_url)[1]
        img_alt = img.get('alt')
        img_alt = re.sub(r'[\??!!\.。]','',img_alt)
        filename = img_alt + img_suffix
        request.urlretrieve(img_url,'images/'+filename)
        print(filename)

    

def main():
    for x in range(1,3):
        url = 'http://www.doutula.com/photo/list/?page=%d' %x
        parse_page(url)


if __name__ == "__main__":
    main()
image.png

出现的问题

在调用request.urlretrieve()函数下载图片的时候,网站反爬虫,会报403错误。
urllib.error.HTTPError: HTTP Error 403: Forbidden
解决办法:加一个headers

import urllib
opener=urllib.request.build_opener()
opener.addheaders=[('User-Agent','Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/75.0.3770.100 Safari/537.36')]
urllib.request.install_opener(opener)
request.urlretrieve(img_url,'images/'+filename)

这样就可以了

GIL全局解释器锁,使用与IO操作多的

image.png

百思不得姐的爬取,用多线程

完整代码:

import requests
from lxml import etree
import threading
from queue import Queue
import csv



class BSSpider(threading.Thread):
    headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/75.0.3770.100 Safari/537.36'}
    
    def __init__(self,page_queue,joke_queue,*args,**kwargs):
        super(BSSpider, self).__init__(*args,**kwargs)
        self.base_domain = 'http://www.budejie.com'
        self.page_queue = page_queue
        self.joke_queue = joke_queue
    
    def run(self):
        while True:
            if self.page_queue.empty():
                break
            url = self.page_queue.get()
            response = requests.get(url,headers=self.headers)
            text = response.text
            html = etree.HTML(text)
            descs = html.xpath("//div[@class='j-r-list-c-desc']")
            for desc in descs:
                jokes = desc.xpath(".//text()")
                joke = "\n".join(jokes).strip()
                link = self.base_domain + desc.xpath(".//a/@href")[0]
                self.joke_queue.put((joke,link))
            print('='*10+"第%s页下载完成!"%url.split('/')[-1]+"="*10)


class BSWriter(threading.Thread):
    headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/75.0.3770.100 Safari/537.36'}
    
    def __init__(self,joke_queue,writer,gLock, *args, **kwargs):
        super(BSWriter, self).__init__(*args, **kwargs)
        self.joke_queue = joke_queue
        self.writer = writer
        self.lock = gLock

    def run(self):
        while True:
            try:
                joke_info = self.joke_queue.get(timeout=40)
                joke,link = joke_info
                self.lock.acquire()
                self.writer.writerow((joke,link))
                self.lock.release()
                print("+1")
            except:
                break

    
    

def main():
    page_queue = Queue(5)
    joke_queue = Queue(250)
    gLock = threading.Lock()
    fp = open('bsbdj.csv','a',newline='',encoding='utf-8')
    writer = csv.writer(fp)
    writer.writerow(('content','link'))

    for x in range(1,6):
        url = 'http://www.budejie.com/text/%d' %x
        page_queue.put(url)

    for x in range(5):
        t = BSSpider(page_queue,joke_queue)
        t.start()

    for x in range(5):
        t = BSWriter(joke_queue,writer,gLock)
        t.start()


if __name__ == "__main__":
    main()

image.png
image.png

出现错误的地方:。。。self忘记加还有元组的括号忘记加。

一些要记的地方:

写入到一个文件中,a是用append方式,前面的就不会被覆盖
fp = open('bsbdj.csv','a',newline='',encoding='utf-8')

从队列中一个个取出来
queue.get()

在一个重写的run方法中,如何锁,再释放锁

self.lock.acquire()
self.writer.writerow((joke,link))
self.lock.release()

如何创建队列,如何创建锁,如何创建csv的writer,和写csv的头部

page_queue = Queue(5)
joke_queue = Queue(250)
gLock = threading.Lock()
fp = open('bsbdj.csv','a',newline='',encoding='utf-8')
writer = csv.writer(fp)
writer.writerow(('content','link'))

ajax两种方式

image.png

对于使用ajax的网页,可以用第二种方式:selenium和chromedriver

image.png
pip install selenium

安装chromedriver(遇到了很多坑。。)下载一个对应版本的driver,拖到python安装目录的script目录下(因为之前在环境变量里面配置过了)

image.png
之前的报错

我也不知道怎么回事。。。。现在可以了

相关文章

网友评论

      本文标题:2019-06-29—关于json,csv,多线程,ajax

      本文链接:https://www.haomeiwen.com/subject/raaucctx.html