2020 年 4 月 20 日,Python 2 的最后一个版本 2.7.18 发布了,这意味着 Python 2 是真正的 EOL(end of life)了,一个时代终于落幕了。

Python 2.0 版本是在 2000 年发布的,至今正好到 20 周年(差半年),一代版本竟然持续了这么长时间。其中,2.7 版本是在 Python 3 推出后才发布的,它在 2010 年发布,至今已是 10 年之久。

事实上,Python 诞生了 30 年,但版本演进过程一直很慢,目前最新发布的版本只到 3.8.2。

对比一下相差几岁的隔壁家选手,C++ 已经发展到了 20,JAVA 发展到了 14 ,PHP 到了 7.4,差距悬殊。

但是,版本发布太频繁,也不总是一件好事。就在 Python 程序员抱怨自己的 Python 2 项目还没升 3 版本时,有些 JAVA 程序员还在维护 6、7 版本的项目呢。版本迁移之苦,大家彼此彼此,五十步笑百步。

编程语言跨版本间出现不兼容的特性,几乎是常态。很多时候,并不是说过去的设计是 bug,只是因为编程语言也是某种“生命体”,它会学习其它语言,也会自我进化,所以就有新陈代谢。

摆脱旧的不兼容性版本或者某些落后的设计,有时候需要挺漫长的过渡期。为了方便程序员迁移,核心开发者们形成了一些有效的惯例。

以 Python 为例,我知道有以下的几种策略:

1、DeprecationWarning 提示

当使用过期的类或方法时,会出现 DeprecationWarning 告警。

例如,从 collections 模块导入 ABC(Abstract Base Classes,即抽象基类)就是过期用法,会出现以下提示:

DeprecationWarning: Using or importing the ABCs from 'collections' instead of from 'collections.abc' is deprecated since Python 3.3, and in 3.9 it will stop working

从 3.3 版本起,正确的用法是from collections.abc import Iterable ,直到 3.9 版本时,会取消过期提示,出现报错。

2、将模块改名,约定为私有

在 Python 中,以单下划线“_”开头命名的变量,会被约定为私有的。如果在一个模块中定义了私有变量,理论上它就不该被导出到其它模块使用。

这种命名方式也被推广到了标准模块上。例如,在 Python 的极早期版本中有一个thread 模块,后来到 1.5.1 版本,以 thread 为基础又推出一个更方便好用的threading 模块,也就是我们熟知的实现多线程的模块。

为了摆脱/屏蔽旧的实现,Python 把 thread 模块重命名为_thread ,约定为私有的,这种方式很灵活,普通程序员不会感知它的存在,骨灰级程序员却可以用它实现更加低层的开发。

3、文档中作 deprecated 提示

它跟 DeprecationWarning 是同样的意思。之所以要单独列出来,是因为在构思本文时,我正巧在 Python 3.8 文档中发现了一则提示,忍不住分享一下。

文档中说: @asyncio.coroutine 装饰器不再支持基于yield from 生成器实现的协程,需要显式地写成“asyc def”这种定义方式。

这意味着,3.8 版本对该特性来说就是个分界线,它将进入一个平稳的淘汰周期。

以上三种方式可谓是“除旧”,是面向过去的版本所做的。与它们相对应,就少不了“迎新”的过程,要面向未来的版本。

Python 中有时候会在当前版本中加入一些实验性的特性,期待在未来版本中再完全地实现。而这,就需要给程序员们指出一些过渡性的提示。

例如,在《Python 3.9 性能优化:更快的 list()、dict() 和 range() 等内置类型》一文中,我就介绍了隐藏在 3.8 版本中的“vectorcall”协议,它要在 3.9 版本中才会真正地实现(而且不排除在未来还会继续扩展)。

此外,还有一个很著名的例子:3.2 版本中推出的 concurrent.futures 标准库(依据 PEP-3148)。

这是一个统合了多线程与多进程的异步开发库,“concurrent”指的是并发,而“并发”概念可以囊括多线程与多进程的实现方式。

为什么在“concurrent”下面要加一个“futures”呢?PEP-3148 中指出了这样命名的三点原因,其中最后一点是:希望在将来(in the future)能够添加和移动现有的跟并发相关的库到concurrent 库下面。

也就是说,3.2 版本的concurrent.futures 就是一种实验性的设计,它是为将来更好的concurrent 库而作的准备。虽然说将来的最终实现,可能跟 PEP 中设想的不同,但是,这种面向将来的长远考虑的设计思路,会给整个社区带来某种预期和共同的信念。

好了,聊了这么多,是时候收个尾了。

我从未真正开发或维护过 Python 2 的项目,所以在这个本应纪念它 EOL 的日子,所能想到的就是一个更具普遍性的“除旧迎新”的话题:旧的版本特性是如何逐步退出的,新的版本特性又是如何逐步加入的?

如果你喜欢这种风格的文章,欢迎搜索关注公众号“Python猫”。人生苦短,让我们一起用 Python!

推荐阅读:

本文首发地址:https://mp.weixin.qq.com/s/PIhtEIzBgy_ujcTeAQ2dxg

1、Python 3.9 性能优化,更快的 list()、dict() 和 range() 等内置类型:https://mp.weixin.qq.com/s/bjQjVmf7dP5fOqCS1cObqQ

2、PEP-3148:https://www.python.org/dev/peps/pep-3148

3、聊聊 Python 的内置电池:https://mp.weixin.qq.com/s/XzCqoCvcpFJt4A-E4WMqaA

4、聊聊 print 的前世今生:https://mp.weixin.qq.com/s/NuzfuH_zCZzcrmSFR04NHw

Python 如何移除旧的版本特性,如何迎接新的特性?的更多相关文章

  1. python之使用__future__(解决版本不同,不兼容问题)

    Python的新版本会引入新的功能,但是,实际上这些功能在上一个老版本中就已经存在了.要“试用”某一新的特性,就可以通过导入__future__模块的某些功能来实现. 例如,Python 2.7的整数 ...

  2. C# 语言规范_版本5.0 (第17章 特性)

    1. 特性 C# 语言的一个重要特征是使程序员能够为程序中定义的实体指定声明性信息.例如,类中方法的可访问性是通过使用 method-modifiers(public.protected.intern ...

  3. xmake v2.1.5版本正式发布,大量新特性更新

    此版本带来了大量新特性更新,具体详见:xmake v2.1.5版本新特性介绍. 更多使用说明,请阅读:文档手册. 项目源码:Github, Gitee. 新特性 #83: 添加 add_csnippe ...

  4. Python包管理工具和多版本环境管理

    1. Python包管理工具 在安装Python包的过程中,经常涉及到distutils.setuptools.distribute.setup.py.easy_install.easy_instal ...

  5. python - selenium 2 升级到最新版本

    python - selenium 2 升级到最新版本 之前一直用的是selenium 2.48 .firefox36 而实际用户的浏览器可能都有自动更新功能,所以版本基本上是最新的.所以这次专门做了 ...

  6. VS2015中C#版本6.0的新特性

    [z]http://www.cnblogs.com/xszjk/articles/6417173.html [z]https://www.cnblogs.com/qixu/p/6047229.html ...

  7. Ubuntu16.04 下 python 3.6 安装以及各版本python切换(同时解决各种依赖缺失)

    有些博客给出了从源代码通过./configure.make.sudo make 会导致安装玩之后出现各种依赖缺失的问题,如_sqlite3._bz2 等问题. 当然也有很多帖子给出了从系统自带的pyt ...

  8. Python3.6引入的f-string 与 Python 3的新的特性:类型注解;

    f-string 1.介绍 f-string(formatted string literals):格式化字符串常量,是Python3.6新引入的一种字符串格式化方法,使格式化字符串的操作更加简便. ...

  9. Python在windows平台的多版本配置

    Python在windows平台的多版本配置 快速阅读: ​ python在windows平台的环境变量以及多版本配置 ,以及pycharm如何安装包,以及安装包出错时如何排查. 1.python环境 ...

随机推荐

  1. vim-0-indent(缩进)

    缩进: 参考自http://liuzhijun.iteye.com/blog/1831548,http://blog.csdn.net/chenxiang6891/article/details/41 ...

  2. TensorFlow 模型优化工具包  —  训练后整型量化

    模型优化工具包是一套先进的技术工具包,可协助新手和高级开发者优化待部署和执行的机器学习模型.自推出该工具包以来,  我们一直努力降低机器学习模型量化的复杂性 (https://www.tensorfl ...

  3. Java方法调用数组,是否改变原数组元素的总结

    Java方法调用数组,是否改变原数组元素的总结 //个人理解, 欢迎吐槽 注意String是引用型变量, 我的理解也就是指向型, 指向一个数据或变量, 画图理解最容易, string 指向的 数据的值 ...

  4. 如何在Linux下优雅的查询日志

    做为一名合格的Java后台开发 经常需要查询线上的日志,定位线上问题 所以熟练掌握日志查询的命令 可以使你更加迅速的定位错误日志位置,及时解决问题 在此,我将介绍几个自己工作中经常使用到的日志查询命令 ...

  5. Lisp-02: 函数

    函数(functions) 在 Lisp 中,函数分两种:有名函数和匿名函数(lambda函数). 有名函数 defun 有名函数的标准定义格式为: (defun <name> (list ...

  6. 【Java技术系列】爱情36技之追美妹的技术

    1. 在古老的非洲大陆上,有个原始人无意中抬头仰望星空,凝视的时间稍微长了一些,超过了外星人设置的阈值,立刻拉响了人类即将产生文明的警报.因为外星人认为,人类已经产生了对宇宙的好奇心,文明的产生,科技 ...

  7. 如何让Java应用成为杀不死的小强?(上篇)

    各位坐稳扶好,我们要开车了.不过在开车之前,我们还是例行回顾一下上期分享的要点. 项庄舞剑意在沛公,而咱们上期主要借助应用服务器 Resin 的源码,体验了一次 JMX 的真实应用.鉴于 9012 年 ...

  8. C++不被继承的内容

    C++不被继承的内容 派生类会继承基类所有的方法和变量,除了: 构造函数,析构函数 重载运算符 友元函数 注意,私有成员是被继承了的,只是无法访问.我们可以通过sizeof判断出来.下面附一张清晰的图

  9. 用SQL*Plus命令启动和关闭数据库

    用SQL*Plus命令启动和关闭数据库 1.启动方式 starup或startup open startup nomount startup mount startup read only [x] s ...

  10. stdio.h file not found mac catalina clion 头文件 找不到

    问题:mac update catalina 版本之后引发的include文件问题 ​ 近期Mac 版本升级到catalina版本,使用CLion调试c/c++程序,莫名其妙的发现,有些头文件incl ...