Python 3.8正式发布,来尝鲜这些新特性吧
今天Python3.8发布啦,它是Python2终结前最后一个大版本,我们一起看看这个版本都添加了那些新功能和特性。
PEP572:AssignmentExpressions
PEP572的标题是赋值表达式,也叫做「命名表达式」,不过它现在被广泛的别名是「海象运算符」(TheWalrusOperator)。因为:=很像海象「眼睛小,长着两枚长长的牙」这个特点^_^。
具体内容可以看我之前写的文章: PEP572:海象运算符,在这里给大家展示个通过用PEP572改写的一行实现斐波那契数列的例子:
In:(lambdaf:f(f,int(input('Input:')),1,0,1))(lambdaf,t,i,a,b:print(f'fib({i})={b}')ort==iorf ...:(f,t,i+1,b,a+b)) Input:10 fib(1)=1 fib(2)=1 fib(3)=2 fib(4)=3 fib(5)=5 fib(6)=8 fib(7)=13 fib(8)=21 fib(9)=34 fib(10)=55 Out:True
基于RaymondHettinger版本改写:
In:[(t:=(t[1],sum(t))ifielse(0,1))[1]foriinrange(10)] Out:[1,1,2,3,5,8,13,21,34,55] PEP570:PythonPositional-Onlyparameters
PEP570说白了就是 强制使用者用位置参数
具体的可以看我之前写的文章: PEP570新语法:只接受位置参数
PEP578:PythonRuntimeAuditHooks
现在可以给Python运行时添加审计钩子:
In:importsys ...:importurllib.request ...: ...: ...:defaudit_hook(event,args): ...:ifeventin['urllib.Request']: ...:print(f'Network{event=}{args=}') ...: ...:sys.addaudithook(audit_hook) In:urllib.request.urlopen('https://httpbin.org/get?a=1') Networkevent='urllib.Request'args=('https://httpbin.org/get?a=1',None,{},'GET') Out:
目前支持审计的事件名字和API可以看PEP文档(延伸阅读链接2), urllib.Request是其中之一。另外还可以自定义事件:
In:defaudit_hook(event,args): ...:ifeventin['make_request']: ...:print(f'Network{event=}{args=}') ...: In:sys.addaudithook(audit_hook) In:sys.audit('make_request','https://baidu.com') Networkevent='make_request'args=('https://baidu.com',) In:sys.audit('make_request','https://douban.com') Networkevent='make_request'args=('https://douban.com',) Multiprocessingsharedmemory
可以跨进程直接访问同一内存(共享):
#IPython进程A In:frommultiprocessingimportshared_memory In:a=shared_memory.ShareableList([1,'a',0.1]) In:a Out:ShareableList([1,'a',0.1],name='psm_d5d6ba1b')#注意name #IPython进程B(另外一个终端进入IPython) In:frommultiprocessingimportshared_memory In:b=shared_memory.ShareableList(name='psm_d5d6ba1b')#使用name就可以共享内存 In:b Out:ShareableList([1,'a',0.1],name='psm_d5d6ba1b') Newimportlib.metadatamodule
使用新的 importlib.metadata模块可以直接读取第三方包的元数据:
In:fromimportlib.metadataimportversion,files,requires,distribution In:version('flask') Out:'1.1.1' In:requires('requests') Out: ['chardet(<3.1.0,>=3.0.2)', 'idna(<2.9,>=2.5)', 'urllib3(!=1.25.0,!=1.25.1,<1.26,>=1.21.1)', 'certifi(>=2017.4.17)', "pyOpenSSL(>=0.14);extra=='security'", "cryptography(>=1.3.4);extra=='security'", "idna(>=2.0.0);extra=='security'", "PySocks(!=1.5.7,>=1.5.6);extra=='socks'", 'win-inet-pton;(sys_platform=="win32"andpython_version=="2.7")andextra==\'socks\''] In:dist=distribution('celery') In:dist.version Out:'4.3.0' In:dist.metadata['Requires-Python'] Out:'>=2.7,!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*' In:dist.metadata['License'] In:dist.entry_points Out: [EntryPoint(name='celery',value='celery.__main__:main',group='console_scripts'), EntryPoint(name='celery',value='celery.contrib.pytest',group='pytest11')] In:files('celery')[8] Out:PackagePath('celery/__init__.py') In:dist.locate_file(files('celery')[8]) Out:PosixPath('/Users/dongweiming/test/venv/lib/python3.8/site-packages/celery/__init__.py') functools.cached_property
缓存属性(cached_property)是一个非常常用的功能,很多知名Python项目都自己实现过它,现在终于进入版本库了。
具体的可以看我之前写的文章: functools.cached_property(Python3.8)
functools.lru_cache作为装饰器时可以不加参数
lru_cache装饰器支持 max_size和 typed2个参数,如果对默认参数不敏感,过去只能这么用(需要空括号):
In:@lru_cache() ...:defadd(a,b): ...:returna+b ...:
从3.8开始可以直接作为装饰器,而不是作为返回装饰器的函数(不加括号):
In:@lru_cache ...:defadd(a,b): ...:returna+b ...:
就像 dataclasses.dataclass,绝大部分场景都是这么用:
@dataclass classInventoryItem: ...
其实 dataclass支持多个参数:
defdataclass(cls=None,/,*,init=True,repr=True,eq=True,order=False, unsafe_hash=False,frozen=False):
所以这种使用全部缺省值的装饰器工厂用法中,括号反而显得多余了。
AsyncioREPL
具体的可以看我之前写的文章: asyncioREPL(Python3.8)
F-stringsDEBUG
具体的可以看我之前写的文章: 使用f-strings调试(Python3.8)
AsyncMock
单元测试模块unittest添加了mock异步代码的类:
In:importasyncio In:fromunittest.mockimportAsyncMock,MagicMock In:mock=AsyncMock(return_value={'json':123}) In:awaitmock() Out:{'json':123} In:asyncio.run(mock()) Out:{'json':123} In:asyncdefmain(*args,**kwargs): ...:returnawaitmock(*args,**kwargs) ...: In:asyncio.run(main()) Out:{'json':123} In:mock=MagicMock()#AsyncMock也可以 In:mock.__aiter__.return_value=[1,2,3] In:asyncdefmain(): ...:return[iasyncforiinmock] ...: In:asyncio.run(main()) Out:[1,2,3] Generalizediterableunpackinginyieldandreturn
具体的可以看我之前写的文章: Python3.8对「可迭代解包」的改进
后记
全部更改详情请查阅Changelog(延伸阅读链接1),另外推荐阅读延伸阅读链接3和4,都是非常好的补充
延伸阅读
https://docs.python.org/3.8/whatsnew/3.8.html
https://www.python.org/dev/peps/pep-0578/#id11
https://speakerdeck.com/matrixise/whats-new-in-python-3-dot-8
https://realpython.com/python38-new-features/
总结
以上所述是小编给大家介绍的Python3.8正式发布,来尝鲜这些新特性吧,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对毛票票网站的支持!
如果你觉得本文对你有帮助,欢迎转载,烦请注明出处,谢谢!