我的特一营演员(我的特一营演员表小岛)
8402023-12-02
本篇文章给大家谈谈python不适合开发的领域,以及为什么不建议用python对应的知识点,文章可能有点长,但是希望大家可以阅读完,增长自己的知识,最重要的是希望对各位有所帮助,可以解决了您的问题,不要忘了收藏本站喔。
本文目录
NealKrawetz有一群geek朋友,经常一起讨论技术话题,有时候也会谈到编程语言。「IhatePython」,作者表示。他对Python厌恶至极。即使有现成的Python代码可用,他也宁愿用C语言重写。为了系统地吐槽Python,作者专门写了这篇博客,细数Python的「八宗罪」。
这个话题已经在HackerNews上引发了热烈的讨论(评论400+),感兴趣的读者可以去围观或参与一下。
HackerNews讨论:https://news.ycombinator.com/item?id=18706174
1.版本
如果要安装一个默认的Linux操作系统,那你很有可能需要安装多个版本的Python:Python2、Python3甚至是3.5、3.7。原因在于:Python3无法与Python2完全兼容。甚至一些用小数表示的版本(如3.5、3.7)也明显缺乏向后的兼容性。
我完全赞成往编程语言中添加新的功能,我甚至不介意淘汰一些旧的版本。但Python却要分开安装。我的Python3.5代码不适用于Python3.7安装版本,除非我特意将其导入3.7。很多Linux开发者都觉得导出太麻烦,因此安装Ubuntu的时候会一并安装Python2和Python3——因为有的核心功能需要前者,而有的需要后者。
向后兼容性的缺乏和各自为政的版本通常会为其敲响丧钟。Commodore创造了第一批家用电脑(比IBMPC和苹果都要早很多)。但CommodorePET不能与后续的CommodoreCBM兼容。CBM又不与VIC-20、Commodore-64、Amiga等兼容。因此,你要么选择花很多时间将代码从一个平台导到另一个,要么选择放弃这个平台。(Commodore今天何在?早被用户抛弃凉凉了……)
类似地,Perl也火过一阵。但Perl3与Perl2的很多代码也不兼容。社区骂声一片,于是一些好的代码导了出来,其他的则被抛弃了。Perl4也是如此。等Perl5出来的时候,人们干脆改用另一种更稳定的编程语言。如今,只有一小部分人还在频繁使用Perl来维持之前的项目。但已经没有人用Perl创建新的大项目了。
同理,Python的每个版本也都存在谷仓效应。之前的版本还要留着,最终造成手里有一堆旧的无用Python代码,因为大家都不想花时间将其移到最新版上。据我所知,没有人为Python2创建新代码了,但我们还留着它,因为没有人想将所需代码移到Python3.x中。Python2.7、3.5、3.6、3.7的文档都还在Python官网上积极维护着,因为他们无法下决心弃用之前的代码。Python就像一种僵尸编程语言——已经死掉的部分还在以行尸走肉的方式存在着。
2.安装
很多软件包都可以帮你轻松地运行apt、yum、rpm或其他一些安装库,并获得最新版本的代码。但Python并非如此。如果用「apt-getinstallpython」安装,你都不知道自己安的是哪个版本,它可能也无法与你所需的所有代码兼容。
因此,你要安装你需要的那版Python。我的其中一个项目用到Python,但必须用Python3.5。所以最后,我的电脑安装了Python2、Python2.6、Python3及Python3.5。其中两个来自操作系统,一个用于项目,另外一个服务于出于其他原因安装的无关软件。虽然都是Python,但此Python非彼Python。
如果你想安装Python包,你应该使用「pip」(PipInstallsPackages)。但由于系统上有一堆Python,你要注意使用正确版本的pip。否则,「pip」可能运行「pip2」,而不是你需要的「pip3.7」。(如果名称不存在,你需要为pip3.7指定明确的真实路径)
一位队友建议我配置自己的环境,这样的话每种软件都可以使用Python3.5的base环境。在我需要用Python3.6开展另一个项目之前,这种做法是非常行得通的,但是需要Python3.6就得创建另外一个环境。两个项目,两版Python,一点都不会混,真的(用生命在假笑)。
pip安装程序将文件放置在用户的本地目录。安装系统级的库时不用pip。Gawd不允许你在运行「sudopip」时出错,因为那会毁了你的整个电脑!运行sudo可能会使一些软件包在系统级别安装,有些是为错误版本的Python安装的,而你的主目录中的一些文件可能最终归root所有,因此未来的非sudopip安装可能会因权限问题而失败。不要这样做。
这些pip模块由谁来维护呢?当然是社区。也就是说,没有明确的所有者,也没有强制性的来源链或责任链。今年早些时候,PyPI的一个版本中发现了一个窃取SSH凭证的后门。这也是意料之中。(出于同样的原因,我不用Node.js和npm;我不信任他们的社区项目。)
3.句法
我非常主张代码的可读性要强。乍一看,Python的可读性似乎不错。但当你开始创建大型代码库的时候你就不会这么想了。
大多数编程语言使用某种符号来标识范围——函数的开始和结束位置、条件语句中包含的操作、变量的定义范围等。C语言、Java、JavaScript、Perl和PHP都用{...}来定义范围,Lisp使用(...)。Python呢?它用空格!如果你要定义复杂代码的范围,你可以缩进接下来的几行代码,缩进结束时,该范围也截止。
Python手册说,你可以用任意数量的空格或制表符来定义范围。但是,每次缩进最好使用四个空格!如果你想缩进两次进行嵌套,使用八个空格!Python社区已经对此进行标准化,即使Python手册中并没有明文规定。这个社区就喜欢用四个空格。所以,除非你不打算将自己的代码向任何人展示,否则的话每次缩进最好用四个空格。
我第一次看到Python代码时,觉得用缩进来定义范围还挺好的,但这么做有一个巨大的缺陷。你可以进行深度嵌套,但这么做使得每一行都会很长,导致不得不在文本编辑器中换行。较长的函数和条件语句可能会使开始和结束范围很难匹配。而且当你不小心把三个空格当成四个空格,还容易出现计算错误,进而花几个小时来调试和追踪。
对于其它语言,我已经养成了调试代码不带任何缩进的习惯。这样,我可以快速浏览代码,然后轻松地识别和删除调试代码。但Python呢?任何没有适当缩进的代码都会产生缩进错误。
4.includes
大部分编程语言都有办法导入其它代码块。比如,C语言用「#include」,PHP语言可以用「include、include_once、require、require」。而Python用的是「import」。
Python可以导入整个模块、模块的一部分或模块中的特定函数。C语言?你可以查看「/usr/include/」。Python的话,最好用「python-v」列出所有路径,然后从列表中搜索每个目录和子目录中的每个文件。我有些朋友很喜欢Python,但我看到他们想导入东西时,总得浏览标准模块。
导入功能还允许用户重命名导入的代码。它们基本上定义了一个自定义的命名空间。乍一看,你会觉得挺不错的,但这最终会影响可读性和长期支持。重命名对于较小的脚本来说还是不错的,但对于长期项目来说真的不适用。那些使用1-2个字母作为命名空间(比如「importnumpyasn」),而且还不按约定俗成的方式来命名的,简直应该拉出去枪毙!
这还不是最糟糕的。大部分编程语言include代码的时候就只是导入代码而已。如果有一个带有构造函数的全局对象,有些语言,如面向对象的C++可能会执行代码。类似地,有些PHP代码可能会定义全局变量,所以导入可以运行代码——但这种做法通常被认为很糟糕。相比之下,很多Python模块包含在导入期间运行的初始化函数。你不知道在运行的是什么,它要干什么,你甚至可能不会注意到。除非存在命名空间冲突,如果这样就好玩了,你得花很多时间来寻找原因。
5.命名法
在其它语言中,数组(array)直接称之为'arrays',但是在Python中,它们被称为'lists'。关联数组在某些地方被称为'hash'(Perl),但是Python将其称为「字典」(dictionary)。Python似乎完全按照自己的节奏来,不使用计算机科学和信息科学领域的常见术语。
此外,Python库的命名也有问题。PyPy、PyPi、NumPy、SciPy、SymPy、PyGtk、Pyglet、PyGame……(前两个库的发音一样,但是它们的功能完全不同)。我理解「py」表示Python,但是它们就不能统一出现在前面或后面吗?
一些常见库放弃了类似双关语的「Py」命名约定,包括matplotlib、nose、Pillow和SQLAlchemy。虽然有一些命名可能暗示其目的(如SQLAlchemy包含SQL,所以它可能是一个SQL接口),但是其它的可能只是随机的单词。如果你不知道「BeautifulSoup」这个库是干什么的,那么你能从命名看出来它是一个HTML/XML解析器吗?不过,BeautifulSoup有很完善的文档且易于使用,如果每一个Python模块都这样,我也就不抱怨了,但是大多数Python库的文档非常烂。
总的来说,我认为Python是一个具有不一致命名约定的函数库集合。我经常抱怨开源项目的命名非常可怕。除非你知道这些项目在干什么,否则你从命名本身中什么都看不出来。除非你知道在寻找什么样的库,不然只能通过别人偶然提及的名字或偶然的机会发现一些库。大多数Python库加重了这种现象,也加重了Python的负面体验。
6.奇怪的操作
每种语言都有自己比较奇特的操作。C语言中使用&和*获取地址空间和值的命名法非常奇怪。C语言中还有用++和—实现increment/decrement的捷径。Bash语言中,在引用特定字符(如用于正则表达式的圆括号和句号)时需要一直考虑「什么时候使用转义符(\)」。JavaScript兼容性有问题(并非每个浏览器都支持所有有用的功能)。但Python的奇怪操作比我见过的其他语言都多。如:
在C语言中,双引号里的是字符串,单引号里的是字符。
在PHP和Bash中,两种引号都能包含字符串。但是,双引号里的字符串可以嵌入变量。相比之下,单引号的字符串是文字;任何嵌入的类似变量的名称都不可扩展。
在JavaScript中,单引号和双引号没什么区别。
在Python中,单引号和双引号也没有什么区别。但是,如果你想让字符串跨行,就得用三重引号,如"""string"""或'''string'''。如果你想用二进制,那你需要优先选择带有b(b'binary')或r(r'raw')的字符串。有时你要用str(string)把字符串转换为字符串,或使用string.encode('utf-8')将其转换为utf8格式。
如果你一开始认为PHP和JavaScript中的=、==、===有点奇怪,那等你用Python中的引号时可能不会这么想了。
7.通过对象Reference传递
大多数编程语言的函数参数传递是传值。如果函数改变了值,结果不会传递回调用代码。但正如我解释过的,Python偏偏要有所不同。Python默认使用pass-by-object-reference来传递函数参数。这意味着改变源变量可能最终会改变值。
这是面向程序、函数和对象的编程语言之间的最大区别。如果每个变量都由对象引用来传递,并且变量的任何变化都会改变所有的引用,那你可能使用的都是全局对象。通过不同的命名调用相同的对象不会改变对象,所以实际上它就是全局的。此外,正如C的程序员早就学到的,全局变量太恶心了,别用。
在Python中,你必须通过值来传递变量,例如「a=b」只是给相同的对象空间分配了另一个命名,但并没有复制b的值给a。如果你真的想要复制b的值,你需要使用一个copy函数,通常是「a=b.copy()"的形式。然而,注意我说的是「通常」。不是所有数据类型都有一个「copy」原型,或者copy函数可能是不完整的。在这种情况下,你可以使用单独的「copy」库:"a=copy.deepcopy(b)"。
8.本地命名
用所用的库或函数的名字来命名程序是常见的编程技巧。例如,如果我用一个叫做「libscreencapture.so」的C库来测试一个截屏程序,我会将该程序命名为「screencapture.c」并编译为「screencapture.exe」。
gcc-oscreencapture.exescreencapture.c-lscreencapture
在C、Java、JavaScript、Perl、PHP等语言中,这通常很有效,因为这些语言可以轻易地辨别本地程序和资源库,它们有不同的路径。但Python呢?还是算了吧,千万别这样做。为什么?Python会假定你首先要导入本地代码。如果我有一个名为「screencapture.py」的程序使用了「importscreencapture」,那么它将导入自己而不是系统库。至少,你应该调用本地程序「myscreencapture.py」吧。
并非一无是处
Python是一门非常流行的编程语言,有很多粉丝。甚至我的很多朋友都很喜欢Python。多年来,我和他们讨论过这些问题,每次他们都点头表示同意。他们并不反对Python存在这些问题,只是认为这不足以浇灭他们对这种语言的热情。
我的朋友经常提到那些非常酷的Python库。我同意一些库非常有用。例如,BeautifulSoup是我用过最好的HTML解析器之一,NumPy使多维数组和复杂的数学更容易实现,而TensorFlow对于机器学习非常有用。但是,我不会因为喜欢TensorFlow或SciPy而用Python创建单片程序。我不打算为了这些「蝇头小利」而放弃可读性和可维护性,这不值得。
通常当我写一篇关于某个主题的批评时,我也会尝试写一些积极的东西。但我没办法列出关于Python的好的方面,因为我真的认为Python很糟糕。
找对方法很重要,在学习的过程中很多人都会有学半天啥都没学会的感觉的,重点是看看能不能继续坚持往下学,因此,你现在就要想清楚是放弃还是继续。
如果选择继续学习,那就换一种学习模式,不知道你目前是怎么自学的,但是我建议自学还是找视频教程来学习比较好,一来你可以看老师的演示操作,二来自己可以跟着动手实践,如果有错误的地方也更容易第一时间发现问题。
如果你本身就是在看视频教程来自学,却学了没啥用的话,可能是找的视频教程不适合你,你可以再多看看其他视频教程,总有能让你学会的一套视频教程。
python学习路线图
给你一份python学习路线图,对照着图内的知识架构逐步学习,希望能够帮到你
如果需要视频教程也可以找我,都可以免费分享给你
比如实时性要求高的系统开发,因为Python在执行效率上相对较低。同时,对于喜欢强类型编程语言或者更喜欢静态类型检查的开发者来说,Python可能不太适合。
VNPY作为C++底层为主的量化交易系列产品,采用C++底层开发,可以大幅都降低Python策略开发的工作,VNPY在PYTHON应用层复制了整个底层的东西,比较适合作为PYTHON程序员去扩展。
由于底层C++部分,避免了单进程python的GIL锁问题,在此架构上还可以采用无锁队列获得的更高的事件驱动后的并发性能。VNPY是属于高性能的C++架构。
稍有阅历的程序员都知道,Python不适合做大项目。
谁否认这一点,谁就是不科学。从就事论事的角度来看,多行情接入,多市场套利时,速度要求较高,尤其是异步IO的问题可以大幅度提高响应时间。
关于python不适合开发的领域,为什么不建议用python的介绍到此结束,希望对大家有所帮助。