|
| 1 | +>所以你们要效法神,好像蒙慈爱的儿女一样。也要凭爱心行事,正如基督爱我们,为我们舍了自己,当作馨香的供物与祭物献与神。至于淫乱并一切污秽,或是贪婪,在你们中间连提都不可,方合圣徒的体统。(EPHESIANS 5:1-3) |
| 2 | +
|
| 3 | +#标准库(2) |
| 4 | + |
| 5 | +python标准库内容非常多,有人专门为此写过一本书。在本教程中,由于我的原因,不会将标准库进行完整的详细介绍,但是,我根据自己的理解和喜好,选几个呈现出来,一来显示标准库之强大功能,二来演示如何理解和使用标准库。 |
| 6 | + |
| 7 | +##sys |
| 8 | + |
| 9 | +这是一个跟python解释器关系密切的标准库,上一节中我们使用过`sys.path.append()`。 |
| 10 | + |
| 11 | + >>> import sys |
| 12 | + >>> print sys.__doc__ |
| 13 | + |
| 14 | +显示了sys的基本文档,看第一句话,概括了本模块的基本特点。 |
| 15 | + |
| 16 | + This module provides access to some objects used or maintained by the |
| 17 | + interpreter and to functions that interact strongly with the interpreter. |
| 18 | + |
| 19 | +在诸多sys函数和变量中,选择常用的(应该说是我觉得常用的)来说明。 |
| 20 | + |
| 21 | +###sys.argv |
| 22 | + |
| 23 | +sys.argv是变量,专门用来向python解释器传递参数,所以名曰“命令行参数”。 |
| 24 | + |
| 25 | +先解释什么是命令行参数。 |
| 26 | + |
| 27 | + $ python --version |
| 28 | + Python 2.7.6 |
| 29 | + |
| 30 | +这里的`--version`就是命令行参数。如果你使用`python --help`可以看到更多: |
| 31 | + |
| 32 | + $ python --help |
| 33 | + usage: python [option] ... [-c cmd | -m mod | file | -] [arg] ... |
| 34 | + Options and arguments (and corresponding environment variables): |
| 35 | + -B : don't write .py[co] files on import; also PYTHONDONTWRITEBYTECODE=x |
| 36 | + -c cmd : program passed in as string (terminates option list) |
| 37 | + -d : debug output from parser; also PYTHONDEBUG=x |
| 38 | + -E : ignore PYTHON* environment variables (such as PYTHONPATH) |
| 39 | + -h : print this help message and exit (also --help) |
| 40 | + -i : inspect interactively after running script; forces a prompt even |
| 41 | + if stdin does not appear to be a terminal; also PYTHONINSPECT=x |
| 42 | + -m mod : run library module as a script (terminates option list) |
| 43 | + -O : optimize generated bytecode slightly; also PYTHONOPTIMIZE=x |
| 44 | + -OO : remove doc-strings in addition to the -O optimizations |
| 45 | + -R : use a pseudo-random salt to make hash() values of various types be |
| 46 | + unpredictable between separate invocations of the interpreter, as |
| 47 | + a defense against denial-of-service attacks |
| 48 | + |
| 49 | +只选择了部分内容摆在这里。所看到的如`-B, -h`之流,都是参数,比如`python -h`,其功能同上。那么`-h`也是命令行参数。 |
| 50 | + |
| 51 | +`sys.arg`在python中的作用就是这样。通过它可以向解释器传递命令行参数。比如: |
| 52 | + |
| 53 | + #!/usr/bin/env python |
| 54 | + # coding=utf-8 |
| 55 | + |
| 56 | + import sys |
| 57 | + |
| 58 | + print "The file name: ", sys.argv[0] |
| 59 | + print "The number of argument", len(sys.argv) |
| 60 | + print "The argument is: ", str(sys.argv) |
| 61 | + |
| 62 | +将上述代码保存,文件名是22101.py(这名称取的,多么数字化)。然后如此做: |
| 63 | + |
| 64 | + $ python 22101.py |
| 65 | + The file name: 22101.py |
| 66 | + The number of argument 1 |
| 67 | + The argument is: ['22101.py'] |
| 68 | + |
| 69 | +将结果和前面的代码做个对照。 |
| 70 | + |
| 71 | +- 在`$ python 22101.py`中,“22101.py”是要运行的文件名,同时也是命令行参数,是前面的`python`这个指令的参数。其地位与`python -h`中的参数`-h`是等同的。 |
| 72 | +- sys.argv[0]是第一个参数,就是上面提到的`22101.py`,即文件名。 |
| 73 | + |
| 74 | +如果我们这样来试试,看看结果: |
| 75 | + |
| 76 | + $ python 22101.py beginner master www.itdiffer.com |
| 77 | + The file name: 22101.py |
| 78 | + The number of argument 4 |
| 79 | + The argument is: ['22101.py', 'beginner', 'master', 'www.itdiffer.com'] |
| 80 | + |
| 81 | +如果在这里,用`sys.arg[1]`得到的就是`beginner`,依次类推。 |
| 82 | + |
| 83 | +###sys.exit() |
| 84 | + |
| 85 | +这是一个方法,意思是退出当前的程序。 |
| 86 | + |
| 87 | + Help on built-in function exit in module sys: |
| 88 | + |
| 89 | + exit(...) |
| 90 | + exit([status]) |
| 91 | + |
| 92 | + Exit the interpreter by raising SystemExit(status). |
| 93 | + If the status is omitted or None, it defaults to zero (i.e., success). |
| 94 | + If the status is an integer, it will be used as the system exit status. |
| 95 | + If it is another kind of object, it will be printed and the system |
| 96 | + exit status will be one (i.e., failure). |
| 97 | + |
| 98 | +从文档信息中可知,如果用`sys.exit()`退出程序,会返回SystemExit异常。这里先告知读者,还有另外一退出方式,是`os._exit()`,这两个有所区别。后者会在后面介绍。 |
| 99 | + |
| 100 | + #!/usr/bin/env python |
| 101 | + # coding=utf-8 |
| 102 | + |
| 103 | + import sys |
| 104 | + |
| 105 | + for i in range(10): |
| 106 | + if i == 5: |
| 107 | + sys.exit() |
| 108 | + else: |
| 109 | + print i |
| 110 | + |
| 111 | +这段程序的运行结果就是: |
| 112 | + |
| 113 | + $ python 22102.py |
| 114 | + 0 |
| 115 | + 1 |
| 116 | + 2 |
| 117 | + 3 |
| 118 | + 4 |
| 119 | + |
| 120 | +需要提醒读者注意的是,在函数中,用到return,这个的含义是终止当前的函数,并返回相应值(如果有,如果没有就是None)。但是sys.exit()的含义是退出当前程序,并发起SystemExit异常。这就是两者的区别了。 |
| 121 | + |
| 122 | +如果使用`sys.exit(0)`表示正常退出。如果读者要测试,需要在某个地方退出的时候有一个有意义的提示,可以用`sys.exit("I wet out at here.")`,那么字符串信息就被打印出来。 |
| 123 | + |
| 124 | +###sys.path |
| 125 | + |
| 126 | +`sys.path`已经不陌生了,前面用过。它可以查找模块所在的目录,以列表的形式显示出来。如果用`append()`方法,就能够向这个列表增加新的模块目录。如前所演示。不在赘述。不理解的读者可以往前复习。 |
| 127 | + |
| 128 | +###sys.stdin, sys.stdout, sys.stderr |
| 129 | + |
| 130 | +这三个放到一起,因为他们的变量都是类文件流对象,分别表示标准UNIX概念中的标准输入、标准输出和标准错误。与python功能对照,sys.stdin获得输入(用raw_input()输入的通过它获得,python3.x中是imput()),sys.stdout负责输出了。 |
| 131 | + |
| 132 | +>流是程序输入或输出的一个连续的字节序列,设备(例如鼠标、键盘、磁盘、屏幕、调制解调器和打印机)的输入和输出都是用流来处理的。程序在任何时候都可以使用它们。一般来讲,stdin(输入)并不一定来自键盘,stdout(输出)也并不一定显示在屏幕上,它们都可以重定向到磁盘文件或其它设备上。 |
| 133 | +
|
| 134 | +还记得`print()`吧,在这个学习过程中,用的很多。它的本质就是`sys.stdout.write(object + '\n')`。 |
| 135 | + |
| 136 | + >>> for i in range(3): |
| 137 | + ... print i |
| 138 | + ... |
| 139 | + 0 |
| 140 | + 1 |
| 141 | + 2 |
| 142 | + |
| 143 | + >>> import sys |
| 144 | + >>> for i in range(3): |
| 145 | + ... sys.stdout.write(str(i)) |
| 146 | + ... |
| 147 | + 012>>> |
| 148 | + |
| 149 | +造成上面输出结果在表象上如此差异,原因就是那个`'\n'`的有无。 |
| 150 | + |
| 151 | + >>> for i in range(3): |
| 152 | + ... sys.stdout.write(str(i) + '\n') |
| 153 | + ... |
| 154 | + 0 |
| 155 | + 1 |
| 156 | + 2 |
| 157 | + |
| 158 | +从这看出,两者是完全等效的。如果仅仅止于此,意义不大。关键是通过sys.stdout能够做到将输出内容从“控制台”转到“文件”,称之为重定向。这样也许控制台看不到(很多时候这个不重要),但是文件中已经有了输出内容。比如: |
| 159 | + |
| 160 | + >>> f = open("stdout.md", "w") |
| 161 | + >>> sys.stdout = f |
| 162 | + >>> print "Learn Python: From Beginner to Master" |
| 163 | + >>> f.close() |
| 164 | + |
| 165 | +当`sys.stdout = f`之后,就意味着将输出目的地转到了打开(建立)的文件中,如果使用print(),即将内容输出到这个文件中,在控制台并无显现。 |
| 166 | + |
| 167 | +打开文件看看便知: |
| 168 | + |
| 169 | + $ cat stdout.md |
| 170 | + Learn Python: From Beginner to Master |
| 171 | + |
| 172 | +这是标准输出。另外两个,输入和错误,也类似。读者可以自行测试。 |
| 173 | + |
| 174 | +关于对文件的操作,虽然前面这这里都涉及到一些。但是,远远不足,后面我会专门讲授对某些特殊但常用的文件读写操作。 |
| 175 | + |
| 176 | +##copy |
| 177 | + |
| 178 | +在[《字典(2)》](./117.md)中曾经对copy做了讲授,这里再次提出,即是复习,又是凑数,以显得我考虑到了这个常用模块,还有: |
| 179 | + |
| 180 | + >>> import copy |
| 181 | + >>> copy.__all__ |
| 182 | + ['Error', 'copy', 'deepcopy'] |
| 183 | + |
| 184 | +这个模块中常用的就是copy和deepcopy。 |
| 185 | + |
| 186 | +为了具体说明,看这样一个例子: |
| 187 | + |
| 188 | + #!/usr/bin/env python |
| 189 | + # coding=utf-8 |
| 190 | + |
| 191 | + import copy |
| 192 | + |
| 193 | + class MyCopy(object): |
| 194 | + def __init__(self, value): |
| 195 | + self.value = value |
| 196 | + |
| 197 | + def __repr__(self): |
| 198 | + return str(self.value) |
| 199 | + |
| 200 | + foo = MyCopy(7) |
| 201 | + |
| 202 | + a = ["foo", foo] |
| 203 | + b = a[:] |
| 204 | + c = list(a) |
| 205 | + d = copy.copy(a) |
| 206 | + e = copy.deepcopy(a) |
| 207 | + |
| 208 | + a.append("abc") |
| 209 | + foo.value = 17 |
| 210 | + |
| 211 | + print "original: %r\n slice: %r\n list(): %r\n copy(): %r\n deepcopy(): %r\n" % (a,b,c,d,e) |
| 212 | + |
| 213 | +保存并运行: |
| 214 | + |
| 215 | + $ python 22103.py |
| 216 | + original: ['foo', 17, 'abc'] |
| 217 | + slice: ['foo', 17] |
| 218 | + list(): ['foo', 17] |
| 219 | + copy(): ['foo', 17] |
| 220 | + deepcopy(): ['foo', 7] |
| 221 | + |
| 222 | +读者可以对照结果和程序,就能理解各种拷贝的实现方法和含义了。 |
| 223 | + |
| 224 | +------ |
| 225 | + |
| 226 | +[总目录](./index.md) | [上节:标准库(1)](./210.md) | [下节:标准库(3)](./222.md) |
| 227 | + |
| 228 | +如果你认为有必要打赏我,请通过支付宝:**qiwsir@126.com**,不胜感激。 |
0 commit comments