Python基础:27执行环境
一:可调用对象
可调用对象,是任何能通过函数操作符“()”来调用的对象。Python 有4 种可调用对象:函数,方法,类,以及一些类的实例。
1:函数
python 有 3 种不同类型的函数对象。
a:内建函数(BIFs),是用c/c++写的,编译过后放入python 解释器,然后把它们作为内建名字空间的一部分加载进系统。这些函数在_bulitin_模块中。
内建函数属性如下表:
bif.__doc__ |
文档字符串(或None) |
bif.__name__ |
字符串类型的文档名字 |
bif.__self__ |
设置为None(保留给built-in 方法) |
bif.__module__ |
存放bif 定义的模块名字(或None) |
可以用dir()列出函数的所有属性:
>>> dir(type)
['__call__', '__class__', '__cmp__', '__delattr__','__doc__','__getattribute__', '__hash__', '__init__', '__module__','__name__','__new__', '__reduce__', '__reduce_ex__','__repr__', '__self__', '__setattr__','__str__']
因为内建函数(BIFs)和内建方法(BIMs)属于相同的类型,所以对BIF或者BIM 调用type()的结果都是:
>>> type(dir)
<type 'builtin_function_or_method'>
注意这不能应用于工厂函数,因为type()正好会返回产生对象的类型:
>>> type(int)
<type 'type'> >>> type(type)
<type 'type'>
b:用户定义的函数(UDF),通常是用python 写的,定义在模块的最高级,因此会作为全局名字空间的一部分装载到系统中。函数也可在其他的函数体内定义。
用户自定义函数属性如下表:
udf.__doc__ |
文档字符串(也可以用udf.func_doc) |
udf.__name__ |
字符串类型的函数名字(也可以用 udf.func_name) |
udf.func_code |
字节编译的代码对象 |
udf.func_defaults |
默认的参数元组 |
udf.func_globals |
全局名字空间字典; 和从函数内部调用globals(x)一样 |
udf.func_dict |
函数属性的名字空间 |
udf.func_doc |
(见上面的udf.__doc__) |
udf.func_name |
(见上面的udf.__name__) |
udf.func_closure |
包含了自由变量的引用的单元对象元组(自用变量在UDF 中使用,但在别处定义) |
用户自定义的函数是“函数“类型的,如:
>>> def foo(): pass
>>> type(foo)
<type 'function'>
c:通过lambda 来创建函数的对象除了没有命名之外,享有和用户自定义函数相同的属性;__name__或者func_name 属性给定为字符串"<lambda>":
>>> lambdaFunc = lambda x: x * 2
>>>type(lambdaFunc)
<type 'function'> >>> lambdaFunc.__name__
'<lambda>'
一旦函数声明以后(且函数对象可用),程序员也可以自定义函数属性。所有的新属性变成udf.__dict__对象的一部分。
2:方法
a:内建方法(BIM)
内建方法的属性如下表:
bim.__doc__ |
文档字串 |
bim.__name__ |
字符串类型的函数名字 |
bim.__self__ |
绑定的对象 |
只有内建类型(BIT)有BIM。BIM 和BIF 两者也都享有相同属性。不同之处在于BIM 的__self__属性指向一个Python对象,而BIF 指向None:
>>> [1,2,3].append.__self__
[1,2,3]
对于内建方法,type()工厂函数给出了和BIF 相同的输出:
>>>type([].append)
<type'builtin_function_or_method'>
b:用户定义的方法(UDM)
UDM包含在类定义之中,无论UDM是否绑定,所有的UMD 都是相同的类型——“实例方法“,如下例:
>>> class C(object):
... def foo(self): pass
... >>> c = C() >>>type(C.foo)
<type'instancemethod'> >>> type(c.foo)
<type'instancemethod'>
下表展示了UDM的属性:
udm.__doc__ |
文档字符串 |
udm.__name__ |
字符串类型的方法名字(与umd.im_func.__name__相同) |
udm.__module__ |
定义udm 的模块的名字(或none) |
udm.im_class |
方法相关联的类 |
udm.im_func |
方法的函数对象(见UDFs) |
udm.im_self |
如果绑定的话为相关联的实例,如果非绑定位为none |
3:类
“调用”类的结果便是创建了实例,即所谓的实例化。
4:类的实例
python 给类提供了名为__call__的特别方法,该方法允许程序员创建可调用的对象(实例)。
默认情况下,__call__()方法是没有实现的,这意味着大多数实例都是不可调用的。然而,如果在类定义中覆盖了这个方法,那么这个类的实例就成为可调用的了。调用这样的实例对象等同于调用__call__()方法。任何在实例调用中给出的参数都会被传入到__call()__中。例子如下:
>>> class C(object):
... def __call__(self, *args):
... print "I'm callable! Called with args:\n", args
...
>>> c = C()
>>> callable(c)
True
>>> c()
I'm callable! Called with arguments:
() >>> c(3, 'no more, no less')
I'm callable! Called with arguments:
(3, 'no more, no less')
二:代码对象
每个可调用对象的核心都是代码对象,由语句,赋值,表达式,以及其他可调用对象组成。
一般说来,代码对象可以作为函数或者方法调用的一部分来执行,也可用exec 语句或内建函数eval()来执行。
如果要执行python代码,那么该代码必须先要转换成字节编译的代码(又称字节码)。这才是真正的代码对象。然而,它们不包含任何关于它们执行环境的信息,这便是可调用对象存在的原因,它被用来包装一个代码对象并提供额外的信息。
函数对象仅是代码对象的包装,方法则是函数对象的包装。
三:可执行对象内建函数
1:callable
callable()是一个布尔函数,确定一个对象是否可以通过函数操作符(())来调用。如果函数可调用便返回True,否则便是False:
>>> callable(dir) #内建函数
True >>> callable(1) #integer #整数
False >>> def foo(): pass
... >>> callable(foo) #用户自定义函数
True >>> callable('bar') #字符串
False >>> class C(object): pass
... >>> callable(C) #类
True
2:compile
compile()函数允许在运行时刻动态生成代码对象,然后就可以用exec语句或者内建函数eval()来执行这些对象或者对它们进行求值。
exec 和eval()都可以执行字符串格式的Python 代码。当执行字符串形式的代码时,每次都必须对这些代码进行字节编译处理。compile()函数提供了一次性字节代码预编译,以后每次调用的时候,都不用编译了。
compile 的三个参数都是必需的,第一参数代表了要编译的python代码。第二个字符串,虽然是必需的,但通常被置为空串。该参数代表了存放代码对象的文件的名字(字符串类型)。最后的参数是个字符串,它用来表明代码对象的类型。有三个可能值:’eval’, 'single', ’exec’
'eval' 可求值的表达式[和eval()一起使用],若第一个参数是语句的话,则会返回错误,比如:
>>> astr = "print'hello ,world'"
>>> compile(astr, '','eval')
Traceback (most recent calllast):
File "<stdin>", line 1, in <module>
File "", line 1
print 'hello ,world'
^
SyntaxError: invalid syntax
'single' 单一可执行语句[和exec 一起使用],如果有多条语句的话,则只会编译第一句。
'exec' 可执行语句组[和exec 一起使用]。例子如下:
>>> eval_code = compile('100 + 200', '', 'eval')
>>> eval(eval_code)
300 >>> single_code = compile('print "Hello world!"', '','single')
>>> single_code
<code object ? at 120998, file "", line 0> >>> exec single_code
Hello world! >>> exec_code = compile("""
... req = input('Count how many numbers? ')
... for eachNum in range(req):
... print eachNum
... """, '', 'exec') >>> exec exec_code
Count how many numbers? 6
0
1
2
3
4
5
3:eval
eval()对表达式求值,不能处理语句。第一个参数可以为字符串或内建函数complie()创建的预编译代码对象。第二个和第三个参数,都为可选的,分别代表了全局和局部名字空间中的对象。如果给出这两个参数,globals 必须是个字典,locals可以是任意的映射对象。
如果都没给出这两个参数,分别默认为globals()和locals()返回的对象,如果只传入了一个全局字典,那么该字典也作为locals 传入。例子如下:
>>> eval('100 + 200')
300
在这种情况下,eval()接收一个字符串并把"100+200"作为表达式求值,当进行整数加法后,给出返回值300。
eval()函数的工作方式:对表达式两端的引号视而不见,接着假设“如果我是python 解释器,我会怎样去观察表达式呢?”,换句话说,如果以交互方式输入相同的表达式,解释器会做出怎么样的反应呢?按下回车后的结果应该和eval()返回的结果相同。
4:exec
exec 语句执行代码对象或字符串形式的python代码。类似地,用compile()预编译重复代码有助于改善性能。
exec 语句只接受一个参数,下面便是它的通用语法:exec obj
被执行的对象(obj)可以只是原始的字符串,比如单一语句或是语句组,它们也可以预编译成一个代码对象。例子如下:
>>> exec """
... x = 0
... print 'x is currently:', x
... while x < 5:
... x += 1
... print 'incrementing x to:', x
... """ x is currently: 0
incrementing x to: 1
incrementing x to: 2
incrementing x to: 3
incrementing x to: 4
incrementing x to: 5
exec 还可以接受有效的python 文件对象。如果我们用上面的多行代码创建一个叫xcount.py 的文件,那么也可以用下面的方法执行相同的代码:
>>> f = open('xcount.py')
>>> exec f
x is currently: 0
incrementing x to: 1
incrementing x to: 2
incrementing x to: 3
incrementing x to: 4
incrementing x to: 5
5:input
input()是eval()和raw_input()的组合,等价于eval(raw_input())。
类似于raw_input(),input()有一个可选的参数,该参数代表了给用户的字符串提示。该字符串默认为空串。
从功能上看,input 不同于raw_input(),因为raw_input()总是以字符串的形式,逐字地返回用户的输入。input()履行相同的的任务;而且,它还把输入作为python 表达式进行求值。这意味着input()返回的数据是对输入表达式求值的结果:一个python 对象。例子如下:
>>> aString = raw_input('Enter a list: ')
Enter a list: [ 123, 'xyz', 45.67 ] >>> aString
"[ 123, 'xyz', 45.67 ]" >>> type(aString)
<type 'str'> >>> aList = input('Enter a list: ')
Enter a list: [ 123, 'xyz', 45.67 ]
>>> aList
[123, 'xyz', 45.67]
>>> type(aList)
<type 'list'>
虽然用户输入字符串,但是input()把输入作为python 对象来求值并返回表达式的结果。
四:执行其他Python程序
1:execfile()
通过exec语句来读取python脚本的内容并执行,例子如下:
f = open(filename, 'r')
exec f
f.close()
这3行可以调用execfile()来换掉:execfile(filename)
在某些情况下,可能需要用不同全局和局部的名字空间集合,而不是默认的集合来执行模块。execfile() 函数的语法非常类似于eval()函数的:
execfile(filename, globals=globals(), locals=locals())
类似eval(),globals 和locals 都是可选的,如果不提供参数值的话,默认为执行环境的名字空间。如果只给定globals,那么locals 默认和globals 相同。
2:将模块作为脚本执行
python2.4 里加入了一个新的命令行选项-m, 允许从shell 或DOS 提示符,直接把模块作为脚本来执行。
模块是标准库的一部分,安装在site-packages 里,或者仅仅是包里面的模块,那直接运行该模块脚本就不是那么容易了。比如,想运行免费的python web 服务器,以便创建和测试你自己的web 页面和CGI 脚本。则必须在命令行敲入如下的东西:
$ python /usr/local/lib/python2x/CGIHTTPServer.py
Serving HTTP on 0.0.0.0 port 8000 ...
如果它是第三方的,则不得不深入到site-packages 去找到它真正定位的地方。
如果不给出完全的路径名,可以用python -c
命令行开关,从命令行运行一个模块,并让python 的导入机制做这种跑腿工作:
$ python -c "import CGIHTTPServer; CGIHTTPServer.test()"
该选项允许指定想要运行的python 语句。虽然这样可以工作,但是__name__模块不是‘__main__’,而是你正在使用的模块。解释器通过import 装载了你的模块,并不是它当作脚本。因此,所有在if __name__ == '__main__' 之下的代码是不会执行的,所以不得不手动地调用模块的test()函数。
要想同时要两者的优点——能够在类库中作为脚本执行模块,而不是作为导入的模块。这就是-m 参数的动机。现在可以像这样运行脚本:
$ python -m CGIHTTPServer
五:执行其他非Python程序
也可以执行非python 程序。这些程序包括了二进制可执行文件,其他的shell 脚本等等。
1:os.system
一个非常简单的函数,接收字符串形式的系统命令并执行它。当执行命令的时候,python的运行是挂起的。当我们的执行完成之后,将会以system()的返回值形式给出退出状态,python 的执行也会继续。
system()保留了现有的标准文件,包括标准的输出,意味着执行任何的命令和程序显示输出都会传到标准输出上。
system()通常和不会产生输出的命令一起使用,通过退出状态显示成功或失败,0 表示成功,非零表示其他类型的错误。例子如下:
>>> import os
>>> result = os.system('cat /etc/motd') Have a lot of fun...
>>> result
0 >>> result = os.system('uname -a')
Linux solo 2.2.13 #1 Mon Nov 8 15:08:22 CET 1999 i586 unknown >>> result
0
六:结束执行
1:sys.exit() 和 SystemExit
立即退出程序并返回调用程序的主要方式是sys模块中的exit()函数。语法为:
sys.exit(status=0)
当调用sys.exit()时,就会引发systemExit()异常。除非对异常在一个try 语句和合适的except子句中进行捕获,否则解释器会用给定的状态参数退出,如果没有给出的话,该参数默认为0。
SystemExit 是唯一不看作错误的异常。它仅仅表示要退出python。
2:os.kill
os 模块的kill()函数模拟传统的unix函数来发送信号给进程。kill()参数是进程标识数(PID)和你想要发送到进程的信号。发送的典型信号为SIGINT、SIGQUIT或SIGKILL,来使进程终结。
Python基础:27执行环境的更多相关文章
- Python基础学习之环境搭建
Python如今成为零基础编程爱好者的首选学习语言,这和Python语言自身的强大功能和简单易学是分不开的.今天我们将带领Python零基础的初学者完成入门的第一步——环境搭建.本文会先来区分几个在P ...
- 1. Python 基础概述 和 环境安装
目录 Python 推荐书籍 开发环境 - Pyenv pyenv 使用 设置Python版本 virtualenv 虚拟环境 pip 通用配置 pip导出和导入 Jupyter 安装和配置 安装 j ...
- javascript基础进阶——执行环境及作用域链
概念 执行环境 执行环境定义了变量或函数有权访问的其他函数,决定了他们各自的行为.每个执行环境都有一个与之关联的变量对象. 变量对象 环境中定义的所有变量和函数都保存在这个对象中. 全局执行环境 全局 ...
- python基础(27):类成员的修饰符、类的特殊成员
1. 类成员的修饰符 类的所有成员在上一步骤中已经做了详细的介绍,对于每一个类的成员而言都有两种形式: 公有成员,在任何地方都能访问 私有成员,只有在类的内部才能方法 私有成员和公有成员的定义不同:私 ...
- Python基础---控制执行流程
一.if语句 1.if语句 作用:让程序根据条件选择性地执行某条语句或某些语句 说明:if语句又叫条件语句,也叫分支语句 语法: if 真值表达式1: 语句块1 elif 真值表达式2: 语句块2 . ...
- python基础001----Python+pycharm环境搭建
一.Python下载安装 1.python下载-----下载地址:https://www.python.org/downloads/windows/ 在python的官网下载python版本,需要下载 ...
- python基础27 -----python进程终结篇-----IO模型
一.IO模型 1.IO模型分类 1.阻塞IO--------blocking IO 2.非阻塞IO------nonblocking IO 3. 多路复用IO------- multiplexing ...
- python网上开发执行环境
http://www.tutorialspoint.com/execute_python_online.php
- python 模块的执行环境
随机推荐
- char类型和int类型之间的转换
在视屏课程第二章里,我们已经学习了一些常用的数据类型转换.然而,有一些时候我们会经常会遇到将char类型转换成int类型,或者需要将int类型转换为char类型的情况. 这里,我们来探讨一下这种不常用 ...
- 如何用git将项目代码上传到github - CSDN博客
配置Git 我们先在电脑硬盘里找一块地方存放本地仓库,比如我们把本地仓库建立在C:\MyRepository\1ke_test文件夹下 进入1ke_test文件夹 鼠标右键操作如下步骤: 1)在本地仓 ...
- Yann LeCun清华演讲:深度学习与人工智能的未来
2017年3月22日下午,Facebook人工智能研究院院长.纽约大学终身教授Yann LeCun在清华大学大礼堂为校内师生以及慕名而来的业内人士呈现了一场主题为<深度学习与人工智能的未来(De ...
- css 垂直+水平居中
垂直+水平居中是一个老生常谈的问题了,现在就固定高度和不固定高度两种情况去讨论 1.父盒子固定高度[定位] 实现1: father-box: position:relative child-box:p ...
- ATM系统和购物车系统 不需要文件支撑
目录 ATM系统 购物车系统 ATM系统 #coding=utf8 #Version:python 3.6.4 #Tools:Python 2019.9.7 _data_ = '2019/9/7/01 ...
- 实现移动端上拉加载和下拉刷新的vue插件(mescroll.js)
做一个简单的移动端展示项目,后台分页后前端加载,实现上拉加载下一页,找了下,还是用这个mescroll.js插件好一点 1.npm安装 npm install --save mescroll.js / ...
- AudioToolbox.framework框架学习
http://quding0308.iteye.com/blog/1596710 AudioFile AudioFileStream类 提供了一个接口,用来解析一个流音频文件. //创建一个new s ...
- java 操作CLOB类型数据
clob类型,但对于这个类型处理起来还是比较麻烦的,varchar2长度为4000bytes,如果varchar2能满足楼主的需求,建议使用varchar2,下面提供了在Java 中读取clob类型的 ...
- PHPCMS V9双语站建设切换
PHPCMS V9要做双语,很多同学都是迷茫的,在此特地分享我的双语制作步辶 我这种模式是把两个站点都改为HTML静态模式才可以实现 双语切换可分为两种模式: 1.解析二级域名来切换双语 解析二级域名 ...
- JavaScript--预解析在IE存在的问题
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...