python3中__get__,getattr,__getattribute__的区别javascript
什么是 GIL
详细博客
GIL = Global Intercept Lock 全局解释器锁,任意时刻在解释器中只会有一个线程在运行html
Python中的@staticmethod和@classmethod的区别 (**)前端
@classmethod 有 cls 绑定, 而 @staticmethod 没有java
Python里面如何拷贝一个对象,并解析深浅拷贝python
import copy copy.copy copy.deepcopy 浅拷贝只拷贝List这种复杂结构的第一层,也就是 List 里若是还有List等,不会再次被建立而是共享内存,由于修改第二层中的一个元素会影响到另外一个元素 深拷贝则会拷贝第二层中的从新建立,独享内存,修改其中一个不会影响另外一个 import copy a = [1,2,3,[4,5],6] b=a c=copy.copy(a) d=copy.deepcopy(a) b.append(10) # [1,2,3,[4,5],6,10] c[3].append(11) # [1,2,3,[4,5,11],6] d[3].append(12) # [1,2,3,[4,5,12],6] a,b,c,d 这个例子理解了那么深浅拷贝就懂了!
Python里面的search()和match()的区别mysql
search 会搜索字符串中符合规则的第一条字符串,而 match 则会从被搜索的字符串第0个位置开始匹配react
简述迭代器生成器以及他们之间的区别linux
迭代器 Iterable --> Iterator --> Generatorios
个人理解是生成器是特殊的迭代器,而迭代器是特殊的可迭代对象。nginx
迭代器和生成器都是Python中特有的概念,迭代器能够看做是一个特殊的对象,每次调用该对象时会返回自身的下一个元素,从实现上来看,一个可迭代的对象必须是定义了iter()方法的对象,而一个迭代器必须是定义了iter()方法和next()方法的对象。生成器的概念要比迭代器稍显复杂,由于生成器是可以返回一个迭代器的函数,其最大的做用是将输入对象返回为一个迭代器。Python中使用了迭代的概念,是由于当须要循环遍历一个较大的对象时,传统的内存载入方式会消耗大量的内存,不如须要时读取一个元素的方式更为经济快捷。 迭代器 迭代器(iterator)是一种对象,它可以用来遍历标准模板库容器中的部分或所有元素,每一个迭代器对象表明容器中的肯定的地址。迭代器修改了常规指针的接口,所谓迭代器是一种概念上的抽象:那些行为上像迭代器的东西均可以叫作迭代器。然而迭代器有不少不一样的能力,它能够把抽象容器和通用算法有机的统一块儿来。 迭代器提供一些基本操做符:*、++、==、!=、=。这些操做和C/C++“操做array元素”时的指针接口一致。不一样之处在于,迭代器是个所谓的复杂的指针,具备遍历复杂数据结构的能力。其下层运行机制取决于其所遍历的数据结构。所以,每一种容器型别都必须提供本身的迭代器。事实上每一种容器都将其迭代器以嵌套的方式定义于内部。所以各类迭代器的接口相同,型号却不一样。这直接导出了泛型程序设计的概念:全部操做行为都使用相同接口,虽然它们的型别不一样。 迭代器使开发人员可以在类或结构中支持foreach迭代,而没必要整个实现IEnumerable或者IEnumerator接口。只需提供一个迭代器,便可遍历类中的数据结构。当编译器检测到迭代器时,将自动生成IEnumerable接口或者IEnumerator接口的Current,MoveNext和Dispose方法。 生成器 生成器是一次生成一个值的特殊类型函数。能够将其视为可恢复函数。调用该函数将返回一个可用于生成连续 x 值的生成器【Generator】 简单的说就是在函数的执行过程当中,yield语句会把你须要的值返回给调用生成器的地方,而后退出函数,下一次调用生成器函数的时候又从上次中断的地方开始执行,而生成器内的全部变量参数都会被保存下来供下一次使用。
什么是协程,Python中的协程是如何实现的
一个线程内部中断某一个步骤而后再次回到yield地方执行,经过yield来实现
什么是装饰器,请使用装饰器实现singletion。
装饰器相似于java的AOP能够用来对方法进行加强,如日志事务等...
举例 todo
请使用Python实现快速排序
todo
简述select和epoll的原理和区别
select、poll、epoll之间的区别总结[整理] select,poll,epoll都是IO多路复用的机制。I/O多路复用就经过一种机制,能够监视多个描述符,一旦某个描述符就绪(通常是读就绪或者写就绪),可以通知程序进行相应的读写操做。但select,poll,epoll本质上都是同步I/O,由于他们都须要在读写事件就绪后本身负责进行读写,也就是说这个读写过程是阻塞的,而异步I/O则无需本身负责进行读写,异步I/O的实现会负责把数据从内核拷贝到用户空间。关于这三种IO多路复用的用法,前面三篇总结写的很清楚,并用服务器回射echo程序进行了测试。链接以下所示: select:http://www.cnblogs.com/Anker/archive/2013/08/14/3258674.html poll:http://www.cnblogs.com/Anker/archive/2013/08/15/3261006.html epoll:http://www.cnblogs.com/Anker/archive/2013/08/17/3263780.html 今天对这三种IO多路复用进行对比,参考网上和书上面的资料,整理以下: 一、select实现 select的调用过程以下所示: (1)使用copy_from_user从用户空间拷贝fd_set到内核空间 (2)注册回调函数__pollwait (3)遍历全部fd,调用其对应的poll方法(对于socket,这个poll方法是sock_poll,sock_poll根据状况会调用到tcp_poll,udp_poll或者datagram_poll) (4)以tcp_poll为例,其核心实现就是__pollwait,也就是上面注册的回调函数。 (5)__pollwait的主要工做就是把current(当前进程)挂到设备的等待队列中,不一样的设备有不一样的等待队列,对于tcp_poll来讲,其等待队列是sk->sk_sleep(注意把进程挂到等待队列中并不表明进程已经睡眠了)。在设备收到一条消息(网络设备)或填写完文件数据(磁盘设备)后,会唤醒设备等待队列上睡眠的进程,这时current便被唤醒了。 (6)poll方法返回时会返回一个描述读写操做是否就绪的mask掩码,根据这个mask掩码给fd_set赋值。 (7)若是遍历完全部的fd,尚未返回一个可读写的mask掩码,则会调用schedule_timeout是调用select的进程(也就是current)进入睡眠。当设备驱动发生自身资源可读写后,会唤醒其等待队列上睡眠的进程。若是超过必定的超时时间(schedule_timeout指定),仍是没人唤醒,则调用select的进程会从新被唤醒得到CPU,进而从新遍历fd,判断有没有就绪的fd。 (8)把fd_set从内核空间拷贝到用户空间。 总结: select的几大缺点: (1)每次调用select,都须要把fd集合从用户态拷贝到内核态,这个开销在fd不少时会很大 (2)同时每次调用select都须要在内核遍历传递进来的全部fd,这个开销在fd不少时也很大 (3)select支持的文件描述符数量过小了,默认是1024 2 poll实现 poll的实现和select很是类似,只是描述fd集合的方式不一样,poll使用pollfd结构而不是select的fd_set结构,其余的都差很少。 关于select和poll的实现分析,能够参考下面几篇博文: http://blog.csdn.net/lizhiguo0532/article/details/6568964#comments http://blog.csdn.net/lizhiguo0532/article/details/6568968 http://blog.csdn.net/lizhiguo0532/article/details/6568969 http://www.ibm.com/developerworks/cn/linux/l-cn-edntwk/index.html?ca=drs- http://linux.chinaunix.net/techdoc/net/2009/05/03/1109887.shtml 三、epoll epoll既然是对select和poll的改进,就应该能避免上述的三个缺点。那epoll都是怎么解决的呢?在此以前,咱们先看一下epoll和select和poll的调用接口上的不一样,select和poll都只提供了一个函数——select或者poll函数。而epoll提供了三个函数,epoll_create,epoll_ctl和epoll_wait,epoll_create是建立一个epoll句柄;epoll_ctl是注册要监听的事件类型;epoll_wait则是等待事件的产生。 对于第一个缺点,epoll的解决方案在epoll_ctl函数中。每次注册新的事件到epoll句柄中时(在epoll_ctl中指定EPOLL_CTL_ADD),会把全部的fd拷贝进内核,而不是在epoll_wait的时候重复拷贝。epoll保证了每一个fd在整个过程当中只会拷贝一次。 对于第二个缺点,epoll的解决方案不像select或poll同样每次都把current轮流加入fd对应的设备等待队列中,而只在epoll_ctl时把current挂一遍(这一遍必不可少)并为每一个fd指定一个回调函数,当设备就绪,唤醒等待队列上的等待者时,就会调用这个回调函数,而这个回调函数会把就绪的fd加入一个就绪链表)。epoll_wait的工做实际上就是在这个就绪链表中查看有没有就绪的fd(利用schedule_timeout()实现睡一会,判断一会的效果,和select实现中的第7步是相似的)。 对于第三个缺点,epoll没有这个限制,它所支持的FD上限是最大能够打开文件的数目,这个数字通常远大于2048,举个例子,在1GB内存的机器上大约是10万左右,具体数目能够cat /proc/sys/fs/file-max察看,通常来讲这个数目和系统内存关系很大。 总结: (1)select,poll实现须要本身不断轮询全部fd集合,直到设备就绪,期间可能要睡眠和唤醒屡次交替。而epoll其实也须要调用epoll_wait不断轮询就绪链表,期间也可能屡次睡眠和唤醒交替,可是它是设备就绪时,调用回调函数,把就绪fd放入就绪链表中,并唤醒在epoll_wait中进入睡眠的进程。虽然都要睡眠和交替,可是select和poll在“醒着”的时候要遍历整个fd集合,而epoll在“醒着”的时候只要判断一下就绪链表是否为空就好了,这节省了大量的CPU时间。这就是回调机制带来的性能提高。 (2)select,poll每次调用都要把fd集合从用户态往内核态拷贝一次,而且要把current往设备等待队列中挂一次,而epoll只要一次拷贝,并且把current往等待队列上挂也只挂一次(在epoll_wait的开始,注意这里的等待队列并非设备等待队列,只是一个epoll内部定义的等待队列)。这也能节省很多的开销。 参考资料: http://www.cnblogs.com/apprentice89/archive/2013/05/09/3070051.html http://www.linuxidc.com/Linux/2012-05/59873p3.htm http://xingyunbaijunwei.blog.163.com/blog/static/76538067201241685556302/ http://blog.csdn.net/kkxgx/article/details/7717125 https://banu.com/blog/2/how-to-use-epoll-a-complete-example-in-c/epoll-example.c
简述Python的垃圾回收机制
内部采用对象引用计数,当引用计数为0时,系统自动回收
写一个简单的python socket编程
todo tcp ,udp
简述Python上下文管理器原理,并用上下文管理器实现将“hello world”写入文件的功能。
todo
利用python执行shell命令并取得返回结果
todo
用python继承process,写一个并行执行任务的类,并写出使用过程。
todo
18.请列出你使用过的HA方案。
19.请列出你了解的Web服务器负载架构。
如何判断一个邮箱是否合法。
.请实现一个装饰器,限制该函数被调用的频率,如10秒一次。
介绍一下python的异常处理机制和本身开发过程当中的体会。
解释下HTTP常见的响应状态码。
编写快速排序或者冒泡排序。
U5G()9(NW3()46463T.png)
Web开发中有哪些技术手段防止SQL注入?
xxx
31.解释top命令和vmstat命令。
32.mysql高可用方案有哪些,备份方案有哪些,有什么优缺点?
33.linux基础问题:
- 怎么查看用户登陆日志。
- linux中的utmp,wtmp,lastlog,message各文件的做用。
- 列举你属性的服务器性能查看命令。
- linux服务器间怎么实现无密码登陆,列举操做步骤
34.画出TCP三次握手,四次挥手断开示意图。
35.叙述mysql半同步复制原理。
python中如何动态获取和设置对象的属性?
经过__dict__ 或者元类
如何用python查询和替换一个文本字符串?
string.replace() 或者 re 模块的 sub 或 subn 函数
45.Django里QuerySet的get和filter方法的区别?
46.简述Django对HTTP请求的执行流程。
47.简述Django下的(内建的)缓存机制。
48.Django中Model的slugFied类型字段有什么用途?
49.Django中如何加载初始数据?
python中怎么有效读取一个20G大小的文件。
for line in f
或者使用本身建立的 生成器
如何查看占用8080端口的是什么进程?
一、lsof -i:端口号
二、netstat -tunlp|grep 端口号
63.DNS解析过程是怎样的?有几种解析方式?各自的区别是什么?
64.TCP创建链接三次握手,断开链接四次挥手的过程是怎样的?
64.谈谈Django中的中间件。
65.谈谈CSRF原理
66.谈谈RESTful规范
67.谈谈Python中的面向对象
68.谈谈Django中CBV原理
68.谈谈Django REST freamwork
一、大数据的文件读取
① 利用生成器generator
②迭代器进行迭代遍历:for line in file
二、迭代器和生成器的区别
1)迭代器是一个更抽象的概念,任何对象,若是它的类有next方法和iter方法返回本身自己。对于string、list、dict、tuple等这类容器对象,使用for循环遍历是很方便的。在后台for语句对容器对象调用iter()函数,iter()是python的内置函数。iter()会返回一个定义了next()方法的迭代器对象,它在容器中逐个访问容器内元素,next()也是python的内置函数。在没有后续元素时,next()会抛出一个StopIteration异常
2)生成器(Generator)是建立迭代器的简单而强大的工具。它们写起来就像是正规的函数,只是在须要返回数据的时候使用yield语句。每次next()被调用时,生成器会返回它脱离的位置(它记忆语句最后一次执行的位置和全部的数据值)
区别:生成器能作到迭代器能作的全部事,并且由于自动建立了__iter__()和next()方法,生成器显得特别简洁,并且生成器也是高效的,使用生成器表达式取代列表解析能够同时节省内存。除了建立和保存程序状态的自动方法,当发生器终结时,还会自动抛出StopIteration异常
三、装饰器的做用和功能:
引入日志
函数执行时间统计
执行函数前预备处理
执行函数后的清理功能
权限校验等场景
缓存
四、简单谈下GIL:
Global Interpreter Lock(全局解释器锁)
Python代码的执行由Python 虚拟机(也叫解释器主循环,CPython版本)来控制,Python 在设计之初就考虑到要在解释器的主循环中,同时只有一个线程在执行,即在任意时刻,只有一个线程在解释器中运行。对Python 虚拟机的访问由全局解释器锁(GIL)来控制,正是这个锁能保证同一时刻只有一个线程在运行。
在多线程环境中,Python 虚拟机按如下方式执行:
设置GIL
切换到一个线程去运行
运行:
a. 指定数量的字节码指令,或者
b. 线程主动让出控制(能够调用time.sleep(0))
把线程设置为睡眠状态
解锁GIL
再次重复以上全部步骤
在调用外部代码(如C/C++扩展函数)的时候,GIL 将会被锁定,直到这个函数结束为止(因为在这期间没有Python 的字节码被运行,因此不会作线程切换)。
五、find和grep
grep命令是一种强大的文本搜索工具,grep搜索内容串能够是正则表达式,容许对文本文件进行模式查找。若是找到匹配模式,grep打印包含模式的全部行。
find一般用来再特定的目录下搜索符合条件的文件,也能够用来搜索特定用户属主的文件。
六、线上服务可能由于种种缘由致使挂掉怎么办?
linux下的后台进程管理利器 supervisor
每次文件修改后再linux执行 service supervisord restart
七、如何提升python的运行效率
使用生成器;关键代码使用外部功能包(Cython,pylnlne,pypy,pyrex);针对循环的优化--尽可能避免在循环中访问变量的属性
八、经常使用Linux命令:
ls,help,cd,more,clear,mkdir,pwd,rm,grep,find,mv,su,date
九、Python中的yield用法
yield简单说来就是一个生成器,这样函数它记住上次返 回时在函数体中的位置。对生成器第 二次(或n 次)调用跳转至该函 次)调用跳转至该函数。
十、Python是如何进行内存管理的
1、垃圾回收:python不像C++,Java等语言同样,他们能够不用事先声明变量类型而直接对变量进行赋值。对Python语言来说,对象的类型和内存都是在运行时肯定的。这也是为何咱们称Python语言为动态类型的缘由(这里咱们把动态类型能够简单的归结为对变量内存地址的分配是在运行时自动判断变量类型并对变量进行赋值)。
2、引用计数:Python采用了相似Windows内核对象同样的方式来对内存进行管理。每个对象,都维护这一个对指向该对对象的引用的计数。当变量被绑定在一个对象上的时候,该变量的引用计数就是1,(还有另一些状况也会致使变量引用计数的增长),系统会自动维护这些标签,并定时扫描,当某标签的引用计数变为0的时候,该对就会被回收。
3、内存池机制Python的内存机制以金字塔行,-1,-2层主要有操做系统进行操做,
第0层是C中的malloc,free等内存分配和释放函数进行操做;
第1层和第2层是内存池,有Python的接口函数PyMem_Malloc函数实现,当对象小于256K时有该层直接分配内存;
第3层是最上层,也就是咱们对Python对象的直接操做;
在 C 中若是频繁的调用 malloc 与 free 时,是会产生性能问题的.再加上频繁的分配与释放小块的内存会产生内存碎片. Python 在这里主要干的工做有:
若是请求分配的内存在1~256字节之间就使用本身的内存管理系统,不然直接使用 malloc.
这里仍是会调用 malloc 分配内存,但每次会分配一块大小为256k的大块内存.
经由内存池登记的内存到最后仍是会回收到内存池,并不会调用 C 的 free 释放掉.以便下次使用.对于简单的Python对象,例如数值、字符串,元组(tuple不容许被更改)采用的是复制的方式(深拷贝?),也就是说当将另外一个变量B赋值给变量A时,虽然A和B的内存空间仍然相同,但当A的值发生变化时,会从新给A分配空间,A和B的地址变得再也不相同
十一、描述数组、链表、队列、堆栈的区别?
数组与链表是数据存储方式的概念,数组在连续的空间中存储数据,而链表能够在非连续的空间中存储数据;
队列和堆栈是描述数据存取方式的概念,队列是先进先出,而堆栈是后进先出;队列和堆栈能够用数组来实现,也能够用链表实现。
十二、你知道几种排序,讲一讲你最熟悉的一种?
你是最棒的!
web框架部分
1.django 中当一个用户登陆 A 应用服务器(进入登陆状态),而后下次请求被 nginx 代理到 B 应用服务器会出现什么影响?
若是用户在A应用服务器登录的session数据没有共享到B应用服务器,纳米以前的登陆状态就没有了。
2.跨域请求问题django怎么解决的(原理)
启用中间件
post请求
验证码
表单中添加{%csrf_token%}标签
3.请解释或描述一下Django的架构
对于Django框架遵循MVC设计,而且有一个专有名词:MVT
M全拼为Model,与MVC中的M功能相同,负责数据处理,内嵌了ORM框架
V全拼为View,与MVC中的C功能相同,接收HttpRequest,业务处理,返回HttpResponse
T全拼为Template,与MVC中的V功能相同,负责封装构造要返回的html,内嵌了模板引擎
4.django对数据查询结果排序怎么作,降序怎么作,查询大于某个字段怎么作
排序使用order_by()
降序须要在排序字段名前加-
查询字段大于某个值:使用filter(字段名_gt=值)
5.说一下Django,MIDDLEWARES中间件的做用?
答:中间件是介于request与response处理之间的一道处理过程,相对比较轻量级,而且在全局上改变django的输入与输出。
6.你对Django的认识?
Django是走大而全的方向,它最出名的是其全自动化的管理后台:只须要使用起ORM,作简单的对象定义,它就能自动生成数据库结构、以及全功能的管理后台。
Django内置的ORM跟框架内的其余模块耦合程度高。
应用程序必须使用Django内置的ORM,不然就不能享受到框架内提供的种种基于其ORM的便利;理论上能够切换掉其ORM模块,但这就至关于要把装修完毕的房子拆除从新装修,倒不如一开始就去毛胚房作全新的装修。
Django的卖点是超高的开发效率,其性能扩展有限;采用Django的项目,在流量达到必定规模后,都须要对其进行重构,才能知足性能的要求。
Django适用的是中小型的网站,或者是做为大型网站快速实现产品雏形的工具。
Django模板的设计哲学是完全的将代码、样式分离; Django从根本上杜绝在模板中进行编码、处理数据的可能。
使用HttpResponseRedirect
redirect和reverse
状态码:302,301
8.ngnix的正向代理与反向代理?
正向代理 是一个位于客户端和原始服务器(origin server)之间的服务器,为了从原始服务器取得内容,客户端向代理发送一个请求并指定目标(原始服务器),而后代理向原始服务器转交请求并将得到的内容返回给客户端。客户端必需要进行一些特别的设置才能使用正向代理。
反向代理正好相反,对于客户端而言它就像是原始服务器,而且客户端不须要进行任何特别的设置。客户端向反向代理的命名空间中的内容发送普通请求,接着反向代理将判断向何处(原始服务器)转交请求,并将得到的内容返回给客户端,就像这些内容本来就是它本身的同样。
Tornado 的核心是 ioloop 和 iostream 这两个模块,前者提供了一个高效的 I/O 事件循环,后者则封装了 一个无阻塞的 socket 。经过向 ioloop 中添加网络 I/O 事件,利用无阻塞的 socket ,再搭配相应的回调 函数,即可达到求之不得的高效异步执行。
10.Django 自己提供了 runserver,为何不能用来部署?
runserver 方法是调试 Django 时常常用到的运行方式,它使用 Django 自带的
WSGI Server 运行,主要在测试和开发中使用,而且 runserver 开启的方式也是单进程 。
uWSGI 是一个 Web 服务器,它实现了 WSGI 协议、uwsgi、http 等协议。注意 uwsgi 是一种通讯协议,而 uWSGI 是实现 uwsgi 协议和 WSGI 协议的 Web 服务器。uWSGI 具备超快的性能、低内存占用和多 app 管理等优势,而且搭配着 Nginx
就是一个生产环境了,可以将用户访问请求与应用 app 隔离开,实现真正的部署 。相比来说,支持的并发量更高,方便管理多进程,发挥多核的优点,提高性能。
网络编程和前端部分
1.AJAX是什么,如何使用AJAX?
ajax(异步的javascript 和xml) 可以刷新局部网页数据而不是从新加载整个网页。
第一步,建立xmlhttprequest对象,var xmlhttp =new XMLHttpRequest();XMLHttpRequest对象用来和服务器交换数据。
第二步,使用xmlhttprequest对象的open()和send()方法发送资源请求给服务器。
第三步,使用xmlhttprequest对象的responseText或responseXML属性得到服务器的响应。
第四步,onreadystatechange函数,当发送请求到服务器,咱们想要服务器响应执行一些功能就须要使用onreadystatechange函数,每次xmlhttprequest对象的readyState发生改变都会触发onreadystatechange函数。
200 OK
301 Moved Permanently
302 Found
304 Not Modified
307 Temporary Redirect
400 Bad Request
401 Unauthorized
403 Forbidden
404 Not Found
410 Gone
500 Internal Server Error
501 Not Implemented
GET请求,请求的数据会附加在URL以后,以?分割URL和传输数据,多个参数用&链接。URL的编码格式采用的是ASCII编码,而不是uniclde,便是说全部的非ASCII字符都要编码以后再传输。
POST请求:POST请求会把请求的数据放置在HTTP请求包的包体中。上面的item=bandsaw就是实际的传输数据。
所以,GET请求的数据会暴露在地址栏中,而POST请求则不会。
二、传输数据的大小
在HTTP规范中,没有对URL的长度和传输的数据大小进行限制。可是在实际开发过程当中,对于GET,特定的浏览器和服务器对URL的长度有限制。所以,在使用GET请求时,传输数据会受到URL长度的限制。
对于POST,因为不是URL传值,理论上是不会受限制的,可是实际上各个服务器会规定对POST提交数据大小进行限制,Apache、IIS都有各自的配置。
三、安全性
POST的安全性比GET的高。这里的安全是指真正的安全,而不一样于上面GET提到的安全方法中的安全,上面提到的安全仅仅是不修改服务器的数据。好比,在进行登陆操做,经过GET请求,用户名和密码都会暴露再URL上,由于登陆页面有可能被浏览器缓存以及其余人查看浏览器的历史记录的缘由,此时的用户名和密码就很容易被他人拿到了。除此以外,GET请求提交的数据还可能会形成Cross-site request frogery攻击。
4.cookie 和session 的区别?
一、cookie数据存放在客户的浏览器上,session数据放在服务器上。
二、cookie不是很安全,别人能够分析存放在本地的COOKIE并进行COOKIE欺骗考虑到安全应当使用session。
三、session会在必定时间内保存在服务器上。当访问增多,会比较占用服务器的性能考虑到减轻服务器性能方面,应当使用COOKIE。
四、单个cookie保存的数据不能超过4K,不少浏览器都限制一个站点最多保存20个cookie。
五、建议:
将登录信息等重要信息存放为SESSION
其余信息若是须要保留,能够放在COOKIE中
5.建立一个简单tcp服务器须要的流程
1.socket建立一个套接字
2.bind绑定ip和port
3.listen使套接字变为能够被动连接
4.accept等待客户端的连接
5.recv/send接收发送数据
爬虫和数据库部分
1.scrapy和scrapy-redis有什么区别?为何选择redis数据库?
1) scrapy是一个Python爬虫框架,爬取效率极高,具备高度定制性,可是不支持分布式。而scrapy-redis一套基于redis数据库、运行在scrapy框架之上的组件,可让scrapy支持分布式策略,Slaver端共享Master端redis数据库里的item队列、请求队列和请求指纹集合。
2) 为何选择redis数据库,由于redis支持主从同步,并且数据都是缓存在内存中的,因此基于redis的分布式爬虫,对请求和数据的高频读取效率很是高。
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,而且异步框架出错后是不会停掉其余任务的,数据出错后难以察觉。
3.你经常使用的mysql引擎有哪些?各引擎间有什么区别?
主要 MyISAM 与 InnoDB 两个引擎,其主要区别以下:
1、InnoDB 支持事务,MyISAM 不支持,这一点是很是之重要。事务是一种高
级的处理方式,如在一些列增删改中只要哪一个出错还能够回滚还原,而 MyISAM
就不能够了;
2、MyISAM 适合查询以及插入为主的应用,InnoDB 适合频繁修改以及涉及到
安全性较高的应用;
3、InnoDB 支持外键,MyISAM 不支持;
4、MyISAM 是默认引擎,InnoDB 须要指定;
5、InnoDB 不支持 FULLTEXT 类型的索引;
6、InnoDB 中不保存表的行数,如 select count(*) from table 时,InnoDB;须要
扫描一遍整个表来计算有多少行,可是 MyISAM 只要简单的读出保存好的行数即
可。注意的是,当 count(*)语句包含 where 条件时 MyISAM 也须要扫描整个表;
7、对于自增加的字段,InnoDB 中必须包含只有该字段的索引,可是在 MyISAM
表中能够和其余字段一块儿创建联合索引;
8、清空整个表时,InnoDB 是一行一行的删除,效率很是慢。MyISAM 则会重
建表;
9、InnoDB 支持行锁(某些状况下仍是锁整表,如 update table set a=1 where
user like '%lee%'
4.描述下scrapy框架运行的机制?
从start_urls里获取第一批url并发送请求,请求由引擎交给调度器入请求队列,获取完毕后,调度器将请求队列里的请求交给下载器去获取请求对应的响应资源,并将响应交给本身编写的解析方法作提取处理:1. 若是提取出须要的数据,则交给管道文件处理;2. 若是提取出url,则继续执行以前的步骤(发送url请求,并由引擎将请求交给调度器入队列...),直到请求队列里没有请求,程序结束。
5.什么是关联查询,有哪些?
将多个表联合起来进行查询,主要有内链接、左链接、右链接、全链接(外链接)
6.写爬虫是用多进程好?仍是多线程好? 为何?
IO密集型代码(文件处理、网络爬虫等),多线程可以有效提高效率(单线程下有IO操做会进行IO等待,形成没必要要的时间浪费,而开启多线程能在线程A等待时,自动切换到线程B,能够不浪费CPU的资源,从而能提高程序执行效率)。在实际的数据采集过程当中,既考虑网速和响应的问题,也须要考虑自身机器的硬件状况,来设置多进程或多线程
7.数据库的优化?
优化索引、SQL 语句、分析慢查询;
设计表的时候严格根据数据库的设计范式来设计数据库;
使用缓存,把常常访问到的数据并且不须要常常变化的数据放在缓存中,能
节约磁盘IO;
优化硬件;采用SSD,使用磁盘队列技术(RAID0,RAID1,RDID5)等;
采用MySQL 内部自带的表分区技术,把数据分层不一样的文件,可以提升磁
盘的读取效率;
垂直分表;把一些不常常读的数据放在一张表里,节约磁盘I/O;
主从分离读写;采用主从复制把数据库的读操做和写入操做分离开来;
分库分表分机器(数据量特别大),主要的的原理就是数据路由;
选择合适的表引擎,参数上的优化;
进行架构级别的缓存,静态化和分布式;
不采用全文索引;
采用更快的存储方式,例如 NoSQL存储常常访问的数据
8.常见的反爬虫和应对方法?
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进行分析获得须要的数据。
可以直接模拟ajax请求获取数据当然是极好的,可是有些网站把ajax请求的全部参数所有加密了。咱们根本没办法构造本身所须要的数据的请求。这种状况下就用selenium+phantomJS,调用浏览器内核,并利用phantomJS执行js来模拟人为操做以及触发页面中的js脚本。从填写表单到点击按钮再到滚动页面,所有均可以模拟,不考虑具体的请求和响应过程,只是完完整整的把人浏览页面获取数据的过程模拟一遍。
用这套框架几乎能绕过大多数的反爬虫,由于它不是在假装成浏览器来获取数据(上述的经过添加 Headers必定程度上就是为了假装成浏览器),它自己就是浏览器,phantomJS就是一个没有界面的浏览器,只是操控这个浏览器的不是人。利selenium+phantomJS能干不少事情,例如识别点触式(12306)或者滑动式的验证码,对页面表单进行暴力破解等。
9.分布式爬虫主要解决什么问题?
1)ip
2)带宽
3)cpu
4)io
10.爬虫过程当中验证码怎么处理?
1.scrapy自带
2.付费接口