Python中赋值 浅拷贝和深拷贝的区别
1、赋值:简单地拷贝对象的引用,两个对象的id相同。
2、浅拷贝:创建一个新的组合对象,这个新对象与原对象共享内存中的子对象。
3、深拷贝:创建一个新的组合对象,同时递归地拷贝所有子对象,新的组合对象与原对象没有任何关联。
虽然实际上会共享不可变的子对象,但不影响它们的相互独立性
。
浅拷贝和深拷贝的不同仅仅是对组合对象来说,所谓的组合对象就是包含了其它对象的对象,如列表,类实例。而对于数字、字符串以及其它“原子”类型,没有拷贝一说,产生的都是原对象的引用。
Python中 == 和is的区别
is和 == 都可以对两个对象进行比较,而且它们的返回值都是布尔类型。
is和 == 比较的对象的内容时不同的,即:is比较的是两个对象的地址值,也就是说两个对象是否为同一个实例对象;而 ==比较的是对象的值是否相等,其调用了对象的__eq__()方法。
线程如何在Python 中实现
线程
在程序里一个执行路线就叫做线程,线程是程序执行的最小单位.
多线程
多线程类似于同时执行多个不同程序。
多线程运行有如下优点:
使用线程可以把占据长时间的程序中的任务放到后台去处理。 程序的运行速度可能加快在一些等待的任务实现上如用户输入、文件读写和网络收发数据等。
在这种情况下我们可以释放一些珍贵的资源如内存占用等等。
threading模块实现多线程
threading提供了如下方法:
- run(): 用以表示线程活动的方法。
- start():启动线程活动。
- join([time]): 等待至线程中止。
- isAlive(): 返回线程是否活动的。
- getName(): 返回线程名。
- setName(): 设置线程名。
Python中使用线程有两种方式:函数或者用类来包装线程对象。
函数方式:
导入threading包
对象名= threading.Thread(target = 函数名) 创建线程对象
对象名.start() 创建线程
注:由于代码执行过快,为了显示效果,使用sleep延时执行。
继承方式:
导入threading包
创建一个类继承Thread类,重写run方法
创建类对象,调用start()方法创建线程
注:由于代码执行过快,为了显示效果,使用sleep延时执行。
Python中 负值索引
1、python中正索引从左到右0,1,2… 负索引从右到左-1,-2,-3…
2、高维数组难以直观理解,所以负索引提供了一种从高维到低维的查找方式
3、numpy中高级索引,花式索引可将数组作为索引变量,解决手写迭代的繁琐
类里面的new 和init的区别
__init__ 方法通常用在初始化一个类实例的时候。
但__init__其实不是实例化一个类的时候第一个被调用 的方法。当使用 Persion(name, age) 这样的表达式来实例化一个类时,最先被调用的方法 其实是 new 方法。
__new__方法接受的参数虽然也是和__init__一样
但__init__是在类实例创建之后调用,而 __new__方法正是创建这个类实例的方法。
大数据的文件读取
利用生成器
generator
迭代器进行迭代遍历:for line in file
迭代器和生成器的区别
迭代器是一个更加抽象的概念,任何对象,如果它的类有next方法和iter方法返回自身。
对于string、list、dict、tuple等这类容器对象,使用for循环遍历是很方便的。
在后台for语句对容器对象调用iter()函数,iter()是Python的内置函数。
iter()会返回一个定义了next()方法的迭代器对象,它在容器中逐个访问容器内元素,next()也是python的内置函数。
在没有后续元素时,next()会抛出一个StopIterration的异常。
生成器(Generator)是创建迭代器的简单而强大的工具。
它们写起来就像是正规的函数,只是在返回数据的时候需要使用yield语句。
每次next()被调用时,生成器会返回它脱离的位置(它记忆语句最后一次执行的位置和所有的数据值)
装饰器的作用和功能
引入日志
函数执行时间统计
执行函数钱预备处理
执行函数后的清理功能
权限校验等场景
缓存
如何提高python的运行效率
使用生成器;
关键代码使用外部功能包(Cython,pylnlne,pypy,pyrex);
针对循环的优化–尽量避免在循环中访问变量的属性
Python是如何进行内存管理的
一、垃圾回收:
python不像C++,Java等语言一样,他们可以不用事先声明变量类型而直接对变量进行赋值。对python语言来讲,对象的类型和内存都是在运行时确定的。
二、引用计数:
python采用了类似windows内核对象一样的方式来对内存进行管理。每一个对象,都维护这一个对指向该对象的引用的计数。三、内存池机制
python的内存机制成金字塔形:第-1,-2层主要有操作系统进行操作; 第0层是C中的malloc,free等内存分配和释放函数进行操作; 第1层和第2层是内存池,有python的接口函数PyMem_Malloc函数实现,当对象小于256字节时由该层直接分配内存; 第三层是最上层,也就是我们对python对象的直接操作;
描述数组、链表、队列、堆栈的区别?
数组和链表是数据存储方式的概念,数组在连续的空间中存储数据,而链表可以在非连续的空间中存储数据;
队列和堆栈是描述数据存取方式的概念,队列是先进先出,而堆栈是后进先出;队列和堆栈可以用数组来实现,也可以用链表实现。
跨域请求问题django怎么解决的(原理)
启用中间件
post请求
验证码
表单中添加{%csrf_token%}标签
请解释或描述一下Django的架构
对于Django框架遵循MVC设计,并且有一个专有的名词:MVT
M全拼为Model,与MVC中的M功能相同,负责数据处理,内嵌了ORM框架
V全拼为View,与MVC中的C功能相同,接收HttpRequest,业务处理,返回HttpReponse
T全拼为Template,与MVC中的V功能相同,负责封装构造要返回的html,内嵌了模板引擎
说一下Django,MIDDLEWARES中间件的作用?
中间件是介于request和response处理之间的一道处理过程,相对比较轻量级,并且在全局上改变Django的输入和输出
谈谈对Django的认识?
Django是走大而全的方向,它最出名的是全自动化的管理后台;只需要使用ORM,做简单的对象定义,它就能自动生成数据库结构、以及全功能的管理后台。
Django内置的ORM跟框架内的其他模块耦合程度高
应用程序必须使用Django内置的ORM,否则就不能享受到框架内提供的种种基于其ORM的便利。理论上可以切换掉其ORM模块,但这就相当于要把装修完毕的房子拆除重新装修,倒不如一开始就去毛坯房做全新的装修。
Django的卖点是超高的开发效率,其性能扩展有限;采用Django的项目,在流量达到一定规模后,都需要对其进行重构,才能满足性能的要求。
Django适用的是中小型的网站,或者是作为大型网站快速实现产品雏形的工具。
Django模板的设计哲学是彻底的将代码、样式分离; Django从根本上杜绝在模板中进行编码、处理数据的可能。
Django重定向你是如何实现的?用的什么状态码?
使用HttpResponseRedirect
redire和reverse
状态码:302
,301
ngnix的正向代理与反向代理?
正向代理
是一个位于客户端和原始服务器(origin
server)之间的服务器,为了从原始服务器取得内容,客户端向代理发送一个请求并指定目标(原始服务器),然后代理向原始服务器转交请求并将获得的内容返回给客户端。客户端必须要进行一些特别的设置才能使用正向代理。
反向代理
对于客户端而言它就像是原始服务器,并且客户端不需要进行任何特别的设置。客户端向反向代理的命名空间中的内容发送普通请求,接着反向代理将判断向何处(原始服务器)转交请求,并将获得的内容返回给客户端,就像这些内容原本就是它自己的一样。
常见的HTTP状态码有哪些?
1**:请求收到,继续处理
2**:操作成功收到,分析、接受
3**:完成此请求必须进一步处理
4**:请求包含一个错误语法或不能完成
5**:服务器执行一个完全有效请求失败
100
——客户必须继续发出请求
101
——客户要求服务器根据请求转换HTTP协议版本
200
——服务器成功返回网页
201
——提示知道新文件的URL
202
——接受和处理、但处理未完成
203
——返回信息不确定或不完整
204
——请求收到,但返回信息为空
205
——服务器完成了请求,用户代理必须复位当前已经浏览过的文件
206
——服务器已经完成了部分用户的GET请求
300
——请求的资源可在多处得到
301
——删除请求数据
302
——在其他地址发现了请求数据
303
——建议客户访问其他URL或访问方式
304
——客户端已经执行了GET,但文件未变化
305
——请求的资源必须从服务器指定的地址得到
400
——错误请求,如语法错误
401
——请求授权失败
402
——保留有效ChargeTo头响应
403
——请求不允许
404
——请求的网页不存在
405
——用户在Request-Line字段定义的方法不允许
406
——根据用户发送的Accept拖,请求资源不可访问
500
——服务器产生内部错误
501
——服务器不支持请求的函数
502
——服务器暂时不可用,有时是为了防止发生系统过载
503
——服务器超时过载或暂停维修
504
——关口过载,服务器使用另一个关口或服务来响应用户,等待时间设定值较长
505
——服务器不支持或拒绝支请求头中指定的HTTP版本
Post和get区别?
GET请求
请求的数据会附加在URL之后,以?分割URL和传输数据,多个参数用&连接。
URL的编码格式采用的是ASCII编码,而不是unicode,即是说所有的非ASCII字符都要编码之后再传输。
POST请求
POST请求会把请求的数据放置在HTTP请求包的包体中。
上面的item=bandsaw就是实际的传输数据。
因此,GET请求的数据会暴露在地址栏中,而POST请求则不会。
cookie 和session 的区别?
1、cookie数据存放在客户的浏览器上,session数据放在服务器上。
2、cookie不是很安全,别人可以分析存放在本地的COOKIE并进行COOKIE欺骗考虑到安全应当使用session。
3、session会在一定时间内保存在服务器上。当访问增多,会比较占用服务器的性能考虑到减轻服务器性能方面,应当使用COOKIE。
4、单个cookie保存的数据不能超过4K,很多浏览器都限制一个站点最多保存20个cookie。
建议: 将登陆信息等重要信息存放为SESSION 其他信息如果需要保留,可以放在COOKIE中
你用过的爬虫框架或者模块有哪些?谈谈他们的区别或者优缺点?
Python自带:urllib
,urllib2
第 三 方:requests
框 架:Scrapy
urllib和urllib2模块都做与请求URL相关的操作,但他们提供不同的功能。
urllib2.:
urllib2.urlopen可以接受一个Request对象或者url,(在接受Request对象时候,并以此可以来设置一个URL
的headers),urllib.urlopen只接收一个url
urllib
有urlencode,urllib2没有,因此总是urllib,urllib2常会一起使用的原因
scrapy
是封装起来的框架,他包含了下载器,解析器,日志及异常处理,基于多线程, twisted的方式处理,对于固定单个网站的爬取开发,有优势,但是对于多网站爬取100个网站,并发及分布式处理方面,不够灵活,不便调整与括展。
request
是一个HTTP库,它只是用来,进行请求,对于HTTP请求,他是一个强大的库,下载,解析全部自己处理,灵活性更高,高并发与分布式部署也非常灵活,对于功能可以更好实现.
Scrapy优缺点:
优点:
scrapy 是异步的
采取可读性更强的xpath代替正则
强大的统计和log系统
同时在不同的url上爬行
支持shell方式,方便独立调试
写middleware,方便写一些统一的过滤器
通过管道的方式存入数据库
缺点:
基于python的爬虫框架,扩展性比较差
基于twisted框架,运行中的exception是不会干掉reactor,并且异步框架出错后是不会停掉其他任务的,数据出错后难以察觉。
你常用的mysql引擎有哪些?各引擎间有什么区别?
主要 MyISAM 与 InnoDB 两个引擎,其主要区别如下:
一、InnoDB 支持事务,MyISAM 不支持,这一点是非常之重要。事务是一种高级的处理方式,如在一些列增删改中只要哪个出错还可以回滚还原,而 MyISAM就不可以了;
二、MyISAM 适合查询以及插入为主的应用,InnoDB 适合频繁修改以及涉及到安全性较高的应用;
三、InnoDB 支持外键,MyISAM 不支持;
四、MyISAM 是默认引擎,InnoDB 需要指定;
五、InnoDB 不支持 FULLTEXT 类型的索引;
六、InnoDB 中不保存表的行数,如 select count() from table 时,InnoDB;需要扫描一遍整个表来计算有多少行,但是 MyISAM 只要简单的读出保存好的行数即可。注意的是,当 count()语句包含 where 条件时 MyISAM 也需要扫描整个表;
七、对于自增长的字段,InnoDB 中必须包含只有该字段的索引,但是在 MyISAM表中可以和其他字段一起建立联合索引;
八、清空整个表时,InnoDB 是一行一行的删除,效率非常慢。MyISAM 则会重建表;
九、InnoDB 支持行锁(某些情况下还是锁整表,如 update table set a=1 where user like ‘%lee%’
什么是关联查询,有哪些?
将多个表联合起来进行查询
内连接、左连接、右连接、全连接(外连接)
数据库的优化?
优化索引、SQL 语句、分析慢查询;
设计表的时候严格根据数据库的设计范式来设计数据库;
使用缓存,把经常访问到的数据而且不需要经常变化的数据放在缓存中,能节约磁盘IO;
优化硬件;采用SSD,使用磁盘队列技术(RAID0,RAID1,RDID5)等;
采用MySQL 内部自带的表分区技术,把数据分层不同的文件,能够提高磁盘的读取效率;
垂直分表;把一些不经常读的数据放在一张表里,节约磁盘I/O;
主从分离读写;采用主从复制把数据库的读操作和写入操作分离开来;
分库分表分机器(数据量特别大),主要的的原理就是数据路由;
选择合适的表引擎,参数上的优化;
进行架构级别的缓存,静态化和分布式;
不采用全文索引;
采用更快的存储方式,例如 NoSQL存储经常访问的数据
常见的反爬虫和应对方法?
1.通过Headers反爬虫
从用户请求的Headers反爬虫是最常见的反爬虫策略。很多网站都会对Headers的User-Agent进行检测,还有一部分网站会对Referer进行检测(一些资源网站的防盗链就是检测Referer)。如果遇到了这类反爬虫机制,可以直接在爬虫中添加Headers,将浏览器的User-Agent复制到爬虫的Headers中;或者将Referer值修改为目标网站域名。对于检测Headers的反爬虫,在爬虫中修改或者添加Headers就能很好的绕过。
2.基于用户行为反爬虫
还有一部分网站是通过检测用户行为,例如同一IP短时间内多次访问同一页面,或者同一账户短时间内多次进行相同操作。
大多数网站都是前一种情况,对于这种情况,使用IP代理就可以解决。
可以专门写一个爬虫,爬取网上公开的代理ip,检测后全部保存起来。
这样的代理ip爬虫经常会用到,最好自己准备一个。
有了大量代理ip后可以每请求几次更换一个ip,这在requests或者urllib2中很容易做到,这样就能很容易的绕过第一种反爬虫。对于第二种情况,可以在每次请求后随机间隔几秒再进行下一次请求。
有些有逻辑漏洞的网站,可以通过请求几次,退出登录,重新登录,继续请求来绕过同一账号短时间内不能多次进行相同请求的限制。
3.动态页面的反爬虫
上述的几种情况大多都是出现在静态页面,还有一部分网站,我们需要爬取的数据是通过ajax请求得到,或者通过JavaScript生成的。
首先用Fiddler对网络请求进行分析。
如果能够找到ajax请求,也能分析出具体的参数和响应的具体含义,我们就能采用上面的方法,直接利用requests或者urllib2模拟ajax请求,对响应的json进行分析得到需要的数据。
结尾给大家推荐一个非常好的学习教程,希望对你学习Python有帮助!
有什么疑惑欢迎来交流圈互动:690577709【别忘记备注:编学小屋】
Python基础入门教程推荐:更多Python视频教程-关注B站:编学小屋
Web前端开发-筑基十四式
爬虫是干嘛的?看完你会发现新大陆!