本文正在参加「Python主题月」,详情查看 活动连接html
做为Python的使用者来讲,Python中的垃圾回收主要以引用计数
为主,再引入标记
、清除
,分代为辅
来解决循环引用的问题。前端
一个对象被引用时,引用计数加1,当对象被del时,引用计数减去1,为0时,对象就被清除,通常状况下用户不会去操做Python 的垃圾回收机制,但它留有API接口。python
主要区别是列表是可变的,而元组是不可变的。web
>>> mylist=[1,3,3]
>>> mylist[1]=2
>>> mytuple=(1,3,3)
>>> mytuple[1]=2
Traceback (most recent call last):
File "<pyshell#97>", line 1, in <module>
复制代码
首先一个对象能不能做为字典的key, 就取决于其有没有__hash__
方法。 因此除了容器对象(list/dict/set)和内部包含容器对象的tuple 是不可做为字典的key, 其余的对象均可以。redis
一、操做系统进行资源分配和调度的基本单位,多个进程之间相互独立算法
二、稳定性好,若是一个进程崩溃,不影响其余进程,可是进程消耗资源大,开启的进程数量有限制shell
一、CPU进行资源分配和调度的基本单位,线程是进程的一部分,是比进程更小的能独立运行的基本单位,一个进程下的多个线程能够共享该进程的全部资源数据库
二、若是IO操做密集,则能够多线程运行效率高,缺点是若是一个线程崩溃,都会形成进程的崩溃django
一、子程序调用老是一个入口,一次返回,调用顺序是明确的。而协程的调用和子程序不一样。后端
二、协程看上去也是子程序,但执行过程当中,在子程序内部可中断,而后转而执行别的子程序,在适当的时候再返回来接着执行。
深拷贝就是将一个对象拷贝到另外一个对象中,这意味着若是你对一个对象的拷贝作出改变时,不会影响原对象
。在Python中,咱们使用函数deepcopy()执行深拷贝
浅拷贝则是将一个对象的引用拷贝到另外一个对象上,因此若是咱们在拷贝中改动,会影响到原对象
GIL
是python的全局解释器锁,同一进程中假若有多个线程运行,一个线程在运行python程序的时候会霸占python解释器(加了一把锁即GIL),使该进程内的其余线程没法运行,等该线程运行完后其余线程才能运行。若是线程运行过程当中遇到耗时操做,则解释器锁解开,使其余线程运行。因此在多线程中,线程的运行还是有前后顺序的,并非同时进行。
多进程中由于每一个进程都能被系统分配资源,至关于每一个进程有了一个python解释器,因此多进程能够实现多个进程的同时运行,缺点是进程系统资源开销大
先经过转换为集合去重,在转列表
外层循环从1到n-1,内循环从当前外层的元素的下一个位置开始,依次和外层的元素比较,出现逆序就交换,经过与相邻元素的比较和交换来把小的数交换到最前面。
def bubbleSort(array):
if len(array) < 2:
return array
else:
isSorted = False
counter = 0
while not isSorted:
isSorted = True
for idx in range(len(array) - 1 - counter):
if array[idx] > array[idx + 1]:
isSorted = False
(array[idx + 1], array[idx]) = (array[idx], array[idx + 1])
counter += 1
return array
复制代码
经过一趟排序将待排记录分隔成独立的两部分,其中一部分记录的关键字均比另外一部分的关键字小,则可分别对这两部分记录继续进行排序,以达到整个序列有序。
一、选定Pivot中心轴
二、从R指针开始,将大于Pivot的数字放在Pivot的右边
三、将小于Pivot的数字放在Pivot的左边
四、分别对左右子序列重复前三步操做
def quickSort(array):
print(array)
if len(array) < 2:
return array
else:
pivot_index = 0
pivot = array[pivot_index]
less_part = [i for i in array[pivot_index+1:] if i <= pivot]
large_part = [i for i in array[pivot_index+1:] if i > pivot]
return quickSort(less_part) + [pivot] + quickSort(large_part)
复制代码
函数的返回值是函数对象,只有外部函数才能够对他进行访问,提升了安全性
with
语句的使用,能够简化了代码,有效避免资源泄露的发生
打开文件在进行读写的时候可能会出现一些异常情况,若是按照常规的f.open
写法,咱们须要try
,except
,finally
,作异常判断,而且文件最终无论遇到什么状况,都要执行finally f.close()
关闭文件,with方法帮咱们实现了finally中f.close
实例方法只能被实例调用,静态方法(@由staticmethod装饰器的方法)、类方法(由@classmethod装饰器的方法),能够被类或类的实例对象调用。
一、实例方法,第一个参数必需要默认传递实例对象,通常使用self。 二、静态方法,参数没有必要。 三、类方法,第一个参数必需要默认传递,通常使用cls。
迭代器是一个能够记住遍历的位置的对象。
迭代器对象从集合的第一个元素开始访问,直到全部的元素被访问完结束。迭代器只能往前不会后退。
迭代器有两个基本的方法:iter()
和 next()
。
字符串,列表或元组对象均可用于建立迭代器:
>>> list=[1,2,3,4]
>>> it = iter(list) # 建立迭代器对象
>>> print (next(it)) # 输出迭代器的下一个元素
1
>>> print (next(it))
2
>>>
复制代码
使用了yield
的函数被称为生成器
生成器是一个返回迭代器的函数,只能用于迭代操做,更简单点理解生成器就是一个迭代器
在调用生成器运行的过程当中,每次遇到 yield 时函数会暂停并保存当前全部的运行信息,返回 yield 的值, 并在下一次执行 next() 方法时从当前位置继续运行
print [(lambda x:x*x)(x)for x in range(5)]
[0, 1, 4, 9, 16, 25]
复制代码
对可迭代对象中的每一个元素进行相同的操做
def fn(x):
return x+1
resp = map(fn,li)
print(list(resp))
[2, 3, 4]
复制代码
从左到右对一个序列的项累计地应用有两个参数的函数,以此合并序列到一个单一值。(例如累加或累乘列表元素等等)
from functools import reduce
nums=[1, 2, 3, 4]
def fn(x, y):
return x * y
resp = reduce(fn, nums)
print(resp)
24
复制代码
filter
函数用于过滤序列,过滤掉不符合条件的元素,返回由符合条件元素组成的新列表。该接收两个参数: 第一个为函数
,第二个为序列
,序列的每一个元素做为参数传递给函数进行判,而后返回 True 或 False,最后将返回 True 的元素放到新列表
a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
def fn(a):
return a%2 == 1
newlist = filter(fn, a)
newlist = [i for i in newlist]
print(newlist)
## 输出: [1, 3, 5, 7, 9]
复制代码
Python Web Server Gateway Interface,翻译过来是Python web服务器网关接口,实际上就是一种协议,咱们的应用(Django,Flask)实现了WSGI,就能够配合实现了WSGI(uWSGI,gunicorn)的服务器工做了
前端发送请求
wsgi, 他就是socket服务端,用于接收用户请求并将请求进行初次封装,而后将请求交给web框架(Flask、Django)
中间件处理请求,帮助咱们对请求进行校验或在请求对象中添加其余相关数据,例如:csrf、request.session
路由匹配,根据当前请求的URL找到视图函数,若是是FBV写法,经过判断method两类型,找到对应的视图函数;若是是CBV写法,匹配成功后会自动去找dispatch方法,而后Django会经过dispatch反射的方式找到类中对应的方法并执行
视图函数,在视图函数中进行业务逻辑的处理,可能涉及到:orm、view视图将数据渲染到template模板
视图函数执行完毕以后,会把客户端想要的数据返回给dispatch方法,由dispatch方法把数据返回经客户端
中间件处理响应
wsgi,将响应的内容发送给浏览器
浏览器渲染
Admin: 对model中对应的数据表进行增删改查提供的组件
model:负责操做数据库
form:1.生成HTML代码 2.数据有效性校验 3校验信息返回并展现
ModelForm: 即用于数据库操做,也可用于用户请求的验证
process_request : 请求进来时,权限认证
process_view : 路由匹配以后,可以获得视图函数
process_exception : 异常时执行
process_template_responseprocess : 模板渲染时执行
process_response : 请求有响应时执行
FBV和CBV本质是同样的,基于函数的视图叫作FBV,基于类的视图叫作CBV
在python中使用CBV的优势:
class WSGIHandler(base.BaseHandler):
request = self.request_class(environ)
复制代码
请求走到WSGIHandler类的时候,执行cell
方法,将environ封装成了request
from django.utils.decorators import method_decorator
@method_decorator(check_login)
def post(self, request):
...
复制代码
@method_decorator(check_login)
def dispatch(self, request, *args, **kwargs):
复制代码
@method_decorator(check_login, name="get")
@method_decorator(check_login, name="post")
class HomeView(View):
...
复制代码
<1> all(): 查询全部结果
<2> filter(**kwargs): 它包含了与所给筛选条件相匹配的对象。获取不到返回None
<3> get(**kwargs): 返回与所给筛选条件相匹配的对象,返回结果有且只有一个。
若是符合筛选条件的对象超过一个或者没有都会抛出错误。
<4> exclude(**kwargs): 它包含了与所给筛选条件不匹配的对象
<5> order_by(*field): 对查询结果排序
<6> reverse(): 对查询结果反向排序
<8> count(): 返回数据库中匹配查询(QuerySet)的对象数量。
<9> first(): 返回第一条记录
<10> last(): 返回最后一条记录
<11> exists(): 若是QuerySet包含数据,就返回True,不然返回False
<12> values(*field): 返回一个ValueQuerySet——一个特殊的QuerySet,运行后获得的
并非一系 model的实例化对象,而是一个可迭代的字典序列
<13> values_list(*field): 它与values()很是类似,它返回的是一个元组序列,values返回的是一个字典序列
<14> distinct(): 从返回结果中剔除重复纪录
复制代码
有外键存在时,能够很好的减小数据库请求的次数,提升性能
select_related 经过多表 join 关联查询, 一次性得到全部数据, 只执行一次SQL查询 prefetch_related 分别查询每一个表, 而后根据它们之间的关系进行处理, 执行两次查询
第一步:django第一次响应来自某个客户端的请求时,后端随机产生一个token值,把这个token保存在SESSION状态中;同时,后端把这个token放到cookie中交给前端页面;
第二步:下次前端须要发起请求(好比发帖)的时候把这个token值加入到请求数据或者头信息中,一块儿传给后端;Cookies:{csrftoken:xxxxx}
第三步:后端校验前端请求带过来的token和SESSION里的token是否一致。
# 使用Django的信号机制,能够在添加、删除数据先后设置日志记录:
pre_init # Django中的model对象执行其构造方法前,自动触发
post_init # Django中的model对象执行其构造方法后,自动触发
pre_save # Django中的model对象保存前,自动触发
post_save # Django中的model对象保存后,自动触发
pre_delete # Django中的model对象删除前,自动触发
post_delete # Django中的model对象删除后,自动触发
# 使用
@receiver(post_save, sender=Myclass) # 信号接收装饰器。因为内置信号,因此直接接收
def signal_handler(sender, **kwargs): # 接收到信号后,在此处理
logger = logging.getLogger()
logger.success('保存成功')
复制代码
CACHES = {
'default': {
'BACKEND': 'django.core.cache.backends.dummy.DummyCache', # 缓存后台使用的引擎
'TIMEOUT': 300, # 缓存超时时间(默认300秒,None表示永不过时,0表示当即过时)
'OPTIONS':{
'MAX_ENTRIES': 300, # 最大缓存记录的数量(默认300)
'CULL_FREQUENCY': 3, # 缓存到达最大个数以后,剔除缓存个数的比例,即:1/CULL_FREQUENCY(默认3)
},
}
}
复制代码
CACHES = {
"default": {
"BACKEND": "django_redis.cache.RedisCache",
"LOCATION": "redis://127.0.0.1:6379",
"OPTIONS": {
"CLIENT_CLASS": "django_redis.client.DefaultClient",
"CONNECTION_POOL_KWARGS": {"max_connections": 100}
# "PASSWORD": "密码",
}
}
}
复制代码
主要是经过name的值,来查找url地址,能够理解为反射做用。在html模板中使用name来反射url优点就是后期url规则发生改变以后,只需调整urls.py便可,全部的模板文件都不须要修改。