西西河

主题:【原创】Python简介 -- 请尽量

共:💬45 🌺35 新:
分页树展主题 · 全看 下页
  • 家园 【原创】Python简介

    Python简介

    首先,讲一下Python的创始人Guido van Rossum的一句名言:There is only one way to do it, the right way。这个思想对Python语言的出现和发展影响很大,这也是Python迷们经常放在嘴边的一句话。

    Python是一种解释性的编程语言。就象Java一样,源代码必须首先由编译器转换成字节瘁(byte code),然后再由解释器来执行字节码。和Java不一样的是,Python的编译器和解释器都是一个程序。因此,源代码也可以直接交给这个编译器/解释器来执行。其实,源代码还是先转换成了字节码,只是没有存在硬盘上,而是直接执行了。某些情况下,这种方式要比Java的“编辑-编译-修改-再编译-执行”方式效率要高,特别是在写一些小规模的程序时。

    Python程序的结构、设计与使用方法和“主流”的计算机编程语言还是很接近的。这是一个优点,降低了门槛,易于初学者上手。

    Python是一种面向对象的编程语言。所有的内置(built-in)数据类型都是类:整数(int)、浮点(float)、串(string)、布尔(boolean)、mapping、sequence,等等。经常你会看到一些老鸟写的程序里有类似这样的代码:idx = "book.txt".find("txt") 乍一看,怎么字符串常量还能有方法呢?其实,如果想到Python的字符串常量也是其类型的实例(instance),也就是对象,那么这样用当然也就不奇怪了。

    既然是面向对象的编程语言,当然就支持封装和继承。在Python里,类的成员和方法都是公开的(public)。如果变量名是由连续两个下划线(underscore)起头的,比如:__count,__copy_by_size等等,编译器在生成字节码时会把类型名加上,比如:__Employee_count。这通常被叫做“mangle”。其实,Python的“私有”成员更多是防止与子类的成员产生名字冲突,而不是试图控制对类成员和类方法的存取。在实际使用中,这种控制是很弱的,可以被轻易绕过。

    Python没有“被保护”(protected)成员的概念。在实际使用中,程序员通常在变量名前加上一个下划线作为一种提示。这只是一种惯例,语言规则本身和编译器并不强制执行。

    Python似乎对下划线情有独钟,很多地方都把下划线放在特殊位置上。在下面还会看到更多的例子。

    Python的这种存取控制模式一般来说不会引起什么问题,但在大型的library或framework的项目中,有时还是会让人感到不便,特别是具有C++和Java背景的程序员会发现无法应用有些design patterns。

    和所有其他面向对象语言一样,在子类中定义的非私有成员和方法重载父类中同名的成员和方法。和C++、Java不一样的是,在定义类方法时,对象实例(C++中的this)必须被显式地(explicitly)放在方法形参表的第一个。在C++中,这个对象实例是被编译器自动加上去的。另外,Python程序的惯例是用self,并且这个不由编译器强制。这和在C++和Java中,this是保留字是不同的。在调用类方法时,这个变量又不能出现在实参表里。这和C++与Java又一致了。

    在Python类定义中,类构造器(constructors)必须用 __init__命名,析构器(destructors)必须用 __del__命名。Python类的构造器不会自动掉用父类的构造器,子类必须在其构造器中显式地调用父类的构造器。子类可以选择调用父类构造器的时机,比C++和Java又要灵活一些。相应地,子类的析构器也需要显式地调用父类的析构器。

    Python程序中的变量没有固定的类型,也就是常说的动态类型。在一个变量out of scope之前,其所“包含”的值类型可以被改变。所以,Python程序中的变量也不用事先声明,随用随生成好了。这在写小程序的时候很方便,但是对于大一些的项目,特别是需要多个人合作完成的软件,就会带来麻烦,因为没有编译器来帮你发现使用未声明的变量,或是变量类型不符。通常的做法是在使用变量前检查其是否为“空”(None),因为第一次使用的变量总是指向“空”这个特殊的对象,直到被赋值。当然,这种检查会影响performance。对于类型不符,比较常见的办法是给变量一个可以看出其类型的名字,指望使用者能够注意。这就简直就是一个悖论,依靠人来防止因为人的不可靠而产生的错误。

    Python使用引用计数(reference counting)来简化内存管理,程序员基本上不用关心内存管理的问题,但是要注意避免循环引用(cyclic reference)。变量生成时,其所指对象的引用计数为一。每次变量出现在等号的右边,或者出现在方法或函数调用实参表里,其所指对象的引用计数加一。当一个变量out of scope的时候,其所指对象的引用计数会被减一。如果计数值为零,对象的析构器会被调用。

    Python有限度地支持运算符重载。比如说,可以为一个用户自定义的矩阵类型重载加、减、乘、除,那么使用这个矩阵类型的代码就可以用更加直观的+、-、*、/等操作符来直接进行矩阵的算术运算。

    Python同时还是一种过程式(procedural)的编程语言,有条件判断、循环、函数等常见的控制结构。不像Java,类对Python程序不是必须的。一个程序可以写出来完全没有类的定义,从头到尾都是free functions和函数调用(function calls)。这点上,Python和C++类似。

    Python的函数和类方法支持overload。因为变量是没有类型的,所有overload resolution只能靠区分形参数目。

    Python支持异常(exceptions)。和C++、Java一样,Python的异常使得当前stack frame中所有的变量out of scope,并且中断程序的执行,将异常升级(escalate)。这点上和C++及Java类似。

    大概最有争议性的是Python对源代码格式的要求。不像C家族的编程语言,Python不是自由格式的。Python的scope是靠行首缩进来界定的,而不是匹配的括号。比方说,如果一个类的定义起始于第一列,那么,类中所有成员及方法必须出现在第一列以后,并且处于同一层次的语句必须出现在相同的列上。这个特点的初衷是为了维护程序的可读性,也确实达成了目的。大部分的Python源代码都是排列得整整齐齐的,风格基本接近。但我个人认为有一点矫枉过正了。

    每一个Python源代码文件可以包含一个或多个的类、free functions。多个源文件在一个文件系统目录(directory)下可以成为一个模块(module),只要这个目录中有一个名为__init__.py的文件存在。这个文件甚至可以是空的。模块可以被其他Python代码引入(import),用类似于Java的“import graphic.2D.text”。模块也是Python最常见的代码重用形式。Python的编译器和解释器会在缺省的和指定的路径中搜索被引入的模块。

    Python的名字空间有一点古怪,不太容易说清清楚。对于初学者来说,记住在函数和类方法中存取全局变量是一定要事先用“global foo”声明。当然,尽量少用全局变量这个金科玉律对python也是适用的。

    除了可以用Python语言自身外,其他语言也可以用来写模块,这体现了Python很强的可扩展性。最常见的是C和C++。其实,Python的很多基本模块就是用C写成的。通常来说,C写成的模块要比Python写的快很多,通常是几个数量级的区别。另外,很多的已有的C/C++动态库也可以通过这种办法成为Python的模块。这样,既增加了Python的应用范围,又把Python的易于使用和C/C++的高效、高性能就很好地结合起来了。这大概是Python日益流行的原因之一吧。

    随着Python编译器/解释器一起发行的有大概上百个模块,涵盖了从字符串匹配,xml parsing,操作系统功能到电子邮件处理等等各个领域。由于这些模块大部分是由来自世界各地的Python使用者贡献的,在早期也没有比较正式的命名规范,每个人都有自己的风格。对于习惯了Java严谨命名规范的人来说,Python看起来就太不“专业”了。这应该也是其他open source软件的一个特点吧,如果不是问题的话。

    此外,Python还可以被用作嵌入式的解释器(embedded interpretor)。Python的运行时环境runtime environment有很清晰的C接口,整个编译器/解释器可以被很容易地嵌入到C或者C++的程序中,加上上面所说的由Python到C的接口,Python就具有了类似微软的VBA的能力。这对大型的软件系统是很有吸引力的。OpenOffice就有一个Python接口。

    在2.2版本发布后,Python语言本身的发展逐渐转向了对大型软件项目的支持。一些新的language features被加了进来,比如generator、类方法、静态方法、property、method decorator等等。Python community同时也非常注意借鉴其他编程语言的优点。

    Python编译器/解释器的正是发行版本(released by Python.org and blessed by Guido van Rossum)是由C实现的。其实Python编译器/解释器还有其他语言的,如Java(Jython)、C#(IronPython)。另外,还有一帮人已经花了好几年时间试图写一个可以解释执行Perl和Python字节码的运行环境,叫Parrot。Perl 6已经决定采用它来作解释器了。

    最后,Python这个名字来自于六十年代英国的一个很有名的喜剧系列Monty Python (http://www.bbc.co.uk/dna/h2g2/A687945)。据说Python语言的创造者是个great fan。

    元宝推荐:Highway,

    本帖一共被 1 帖 引用 (帖内工具实现)
    • 家园 Python能代替java吗?这是我一直没搞清的问题,

      我正在选择学习下一门主要语言,正在JAVA和PYTHON之间犹豫。这两门我都只会一点皮毛,我已经会不少的perl,比较能体会PYTHON的优点。

      当然我知道目前PYTHON远远不能和JAVA相提并论,问题是这个趋势未来会不会转变?从直观来说,python加C是很多问题的一个好的解决方案。

      • 家园 我的看法

        如果你的工作主要是基于文件或字符串的处理,大概没有比Perl和Python更好的语言了。

        我的工作主要是写Java程序,但在一些阶段花在Shell脚本,Perl上的时间反而占的很多。Build,Test和Harness的很多程序都是Unix Shell写的,当然也用了很多的awk, sed之类的utilities。用到后来觉得很不爽,各种奇怪的语法很难记住,逻辑控制流和数据处理断裂。Python可以说是最让人爽心悦目的。

        • 家园 体会很接近,虽然我是一名C/C++程序员。我的问题是

          python当然比PERL强,但这点差别不足以让我花大力气去学PYTHON,如果PYTHON将来有机会取代JAVA那我就有必要下这个决心了。

          人老了,学啥都慢。不是那种学个新语言只要一俩个月的年纪了,力气不加了,得悠着点:)

      • 家园 您还是学习JAVA吧。

        从您比较精通PERL来看,您应该不是做硬件底层开发的,既然如此,那JAVA是更加当仁不让。看看IBM每年为JAVA砸下去的美金就知道了。

        • 家园 说得不错,但我的问题是日常工作中有选择python和PERL

          的机会,没有大规模用java的机会。我是做协议的,和硬件关系不多,但还是很强调效率的,日常工作中用c/c++比较多。把各个模块粘起来,过去一般用PERL多,我注意到最近python多起来了。

      • 家园 python是所谓第四代语言

        讲求的是简单明了,比如同样写一个摄像头驱动,C要三,四百行,java至少要100行,pytho三句话就搞定了。现在的趋势是给定一个现有框架才能做实际开发。python有没有可用的框架我不知道,而Java的框架很健全。

        我个人不看好python。

        • 家园 python各方面框架不少的

          五花八门的,邮件列表上时不时就看见一些人在说着不知所云的东西,尽管大家说的都是python

        • 家园 三句话怎么搞定摄像头驱动?

          估计还是用了库文件调用。那样的话,什么语言不是三句话搞定?

          PYTHON还是可以看好的,就像电脑普及到每个人一样,PYTHON也可以普及到每个普通人,而其它语言不能。至于框架,好的框架层出不穷,现有的JAVA的框架,也完全可以照抄给PYTHON用。更何况现在有JPYTHON,理论上可以利用一切JAVA资源。再想想PYTHON与生俱来的与C的紧密结合性。。。

          • 家园 这是个例子表明第四代语言的特点

            简单,好用,平面,高效。而且我确实见过3句话写出的驱动,用在手机上。之所以做到这点就是因为很多控制逻辑是预定好的,不用像C,Java那样还要自己实现。

            Java有极为健全的开发框架,Sun一直在完善它。大部分的商业应用都是用Java,你说可以移植到python上,是可以,不过没人这么做。

            python社区先想想怎么和ruby斗再说。

            • 家园 再来

              而且我确实见过3句话写出的驱动,

              这表明您不是亲手自己做了一遍,所以可能理解有误。我对软硬件编程都有所了解,还是不相信还有这样写驱动的(每个硬件都有一整套的规范,不可能有这么简单的描述)。我还是宁愿相信,所谓三句话调用是指调用库函数使得这个摄像头能工作而已,而非真的写驱动。您可不可以设法找到这三句代码,然后我去试试。

              用在手机上。

              这个恰恰说明了脚本语言的嵌入特性的优点。仅此而已。

              之所以做到这点就是因为很多控制逻辑是预定好的,不用像C,Java那样还要自己实现

              总要有语言在最底层进行描述和规范和实现让硬件工作。如果PYTHON自己没做这个事情,那么还是有别的软硬件在做这个事情。至于调用, C和java也一样会。

              不好意思,我不是在搞人身攻击啊。也许您对某些IT工作甚为精通,但是我认为您也许没有能够理解什么是“计算机语言”以及各种语言的特点。

              • 再来
                家园 我想你完全误解我的意思

                我的意思是python有其自身的特点,简单好用,但是可能不适合商业应用,也不能像Java那样得到广泛的使用。这个原因就在于自身缺乏足够的支持,包括可伸缩的框架,不同的设计模式等等。这些对于实际的开发来讲极为重要,是必不可缺的。Java从一开始设计时就考虑到这些,在开发中就能够对于不同的应用都提供足够的支持,这点是Java最终超过C、C++的地方。你没看见现在微软拼命支持.net么,难道仅仅因为C#好用?

                不好意思,我不是在搞人身攻击啊。也许您对某些IT工作甚为精通,但是我认为您也许没有能够理解什么是“计算机语言”以及各种语言的特点

                我认为我无需反驳你这点。我原先也像你一样,狂热的支持各种新奇的语言,使用各种trick来编程。但这说明我那时不是真正的开发者,因为使用什么语言来实现并不要紧,只要能够高效的专注于自己的应用就行了。

                希望我码那么多字能够解释清我的观点。

                • 家园 也许是误解了

                  我的意思是python有其自身的特点,简单好用,但是可能不适合商业应用

                  简单好用没问题。不适合商业应用,现在难说,将来更难说。我前几天没事下了一个openspark的源代码,发现里面还有不少python文件代码呢。看来JAVA的祖师爷SUN还挺新潮的。

                  因为使用什么语言来实现并不要紧,只要能够高效的专注于自己的应用就行了

                  这个没问题。只是你拿PYTHON三句话写驱动做例子来说明PYTHON的特点,难免让人浮想联翩。

                  最后握个爪,有机会继续交流:)

分页树展主题 · 全看 下页


有趣有益,互惠互利;开阔视野,博采众长。
虚拟的网络,真实的人。天南地北客,相逢皆朋友

Copyright © cchere 西西河