内容简介:第二章 python基础(二)
第九节 函数
-
函数就是完成特定功能的一个语句组,这组语句可以作为一个单位使用,并且给它取一个名字。
-
可以通过函数名在程序的不同地方多次执行(这通常叫做函数调用),却不需要在所有地方都重复编写这些语句。
自定义函数
- 用户自己编写的
预定义的 Python 函数
- 系统自带的一些函数,还有一些和第三方编写的函数,如其他 程序员 编写的一些函数,对于这些现成的函数用户可以直接拿来使用。
为什么使用函数
-
降低编程的难度
- 通常将一个复杂的大问题分解成一系列更简单的小问题,然后将小问题继续划分成更小的问题,当问题细化为足够简单时,我们将可以分而治之。这时,我们可以使用函数来处理特定的问题,各个小问题解决了,大问题也就迎刃而解了。
-
代码重用
- 我们定义的函数可以在一个程序的多个位置使用,也可以用于多个程序。此外,我们还可以把函数放到一个模块中供其他程序员使用,同时,我们也可以使用其他程序定义的函数。这就避免了重复劳动,提供了工作效率。
函数定义和调用
-
当我们自己定义一个函数时,通常使用def语句,其语法形式如下所示:
def 函数名 (参数列表): #可以没有参数函数体 def add(a, b): print a + b
-
调用函数的一般形式是:
函数名(参数列表) add(1, 2)
形式参数和实际参数
-
在定义函数时函数后面圆括号中的变量名称叫做“形式参数”,或简称为“形参”
-
在调用函数时,函数名后面圆括号中的变量名称叫做“实际参数”,或简称为“实参”
缺省参数(默认参数)
-
默认参数只能从右至左给定,如果需要第一个参数给默认值,其他参数不给,那么把第一个参数移到最后一个即可。
def add(a, b = 2): print a + b add(3) #result : 5
局部变量和全局变量
-
Python中的任何变量都有其特定的作用域。
-
在函数中定义的变量一般只能在该函数内部使用,这些只能在程序的特定部分使用的变量我们称之为局部变量。
-
在一个文件顶部定义的变量可以供该文件中的任何函数调用,这些可以为整个程序所使用的变量称为全局变量。
x = 100 #全局变量,可以在文件任何地方调用 def func(): x = 200 #局部变量,只能在函数内部调用 print x func() #输出200 print x #输出100
global语句
-
强制声明为全局变量
x = 100 def func(): global x #强制声明x为全局变量,导致值被覆盖 x = 200 func() print x #输出200
函数返回值
-
函数被调用后会返回一个指定的值
-
函数调用后默认返回None
-
return返回值
-
返回值可以是任意类型
-
return执行后,函数终止
-
区分返回值和打印
def add(a, b): return a + b ret = add(1, 2) #将函数返回结果赋值给变量ret print ret #输出3
向函数传入元组和字典
-
func (*args)
def func(x, y): print x, y t = (1, 2) func(*t)
-
func (**kw)
def func(name='jack', age=30): print name,age d = {'age': 22, 'name' : 'mike'}; func(**d)
处理多余实参
-
def func(*args, **kw)
def func(x, *args, **kw): print x print args print kw func(1, 2, 3, 4, 5, y=10, z=20) #输出 1 (2, 3, 4, 5) {'y': 10, 'z': 20}
lambda表达式
-
匿名函数
-
lambda函数是一种快速定义单行的最小函数,是从Lisp借用来的,可以用在任何需要函数的地方。
lambda x,y:x*y
- 使用Python写一些执行脚本时,使用lambda可以省去定义函数的过程,让代码更加精简。
- 对于一些抽象的,不会别的地方再复用的函数,有时候给函数起个名字也是个难题,使用lambda不需要考虑命名的问题。
-
使用lambda在某些时候让代码更容易理解。
-
lambda基础
-
lambda语句中,冒号前是参数,可以有多个,用逗号隔开,冒号右边的返回值。lambda语句构建的其实是一个函数对象
g = lambda x:x**2 print g <function <lambda> at 0x0000000002643A58>
lambda应用实例
-
reduce为逐次操作list里的每项,接收的参数为2个,最后返回的为一个结果。
sum = reduce(lambda x,y:x*y, range(1,6)) print sum
switch语句
- switch语句用于编写多分支结构的程序,类似与if...elif...else语句。
- switch语句表达的分支结构比if...elif...else语句表达的更清晰,代码的可读性更高。
- 但是python并没有提供switch语句
switch实现
- python可以通过字典实现switch语句的功能。
-
实现方法分为两步
- 首先,定义一个字典
- 其次,调用字典的get()获取相应的表达式
函数调用
-
通过字典调用函数
def add(a, b): return a + b def sub(a, b): return a - b def mul(a, b): return a * b def div(a, b): return a / b operator = {'+': add, '-': sub, '*': mul, '/': div} #通过字典实现switch语句的功能 def calc(a, o, b): return operator.get(o)(a, b) print calc(4, '+', 2) print calc(4, '-', 2) print calc(4, '*', 2) print calc(4, '/', 2)
第十节 内置函数
help函数可以用来查看函数的用法
help(range) #输出结果 Help on built-in function range in module __builtin__: range(...) range(stop) -> list of integers range(start, stop[, step]) -> list of integers Return a list containing an arithmetic progression of integers. range(i, j) returns [i, i+1, i+2, ..., j-1]; start (!) defaults to 0. When step is given, it specifies the increment (or decrement). For example, range(4) returns [0, 1, 2, 3]. The end point is omitted! These are exactly the valid indices for a list of 4 elements.
常用函数
-
abs(number)
: 绝对值 -
max(iterable[, key=func])
: 最大值 -
min(iterable[, key=func])
: 最小值 -
len(collection)
: 取得一个序列或集合的长度 -
divmod(x, y)
: 求两个数的商和模,返回一个元组(x//y, x%y) -
pow(x, y[, z])
: 求一个数的幂运算 -
round(number[, ndigits])
: 对一个数进行指定精度的四舍五入 -
callable(object)
: 判断一个对象是否可调用 -
isinstance(object, class-or-type-or-tuple)
:判断对象是否为某个类的实例 -
cmp(x, y)
: 比较两个数或字符串大小 -
range(start [,stop, step])
: 返回一个范围数组,如range(3), 返回[0,1,2] -
xrange(start [,stop, step])
: 作用与range相同,但是返回一个xrange生成器,当生成范围较大的数组时,用它性能较高
类型转换函数
-
type()
type(object) -> the object's type type(name, bases, dict) -> a new type
-
int()
int(x=0) -> int or long int(x, base=10) -> int or long
-
long()
long(x=0) -> long long(x, base=10) -> long
-
float()
float(x) -> floating point number
-
complex()
complex(real[, imag]) -> complex number
-
str()
str(object='') -> string
-
list()
list() -> new empty list list(iterable) -> new list initialized from iterable's items
-
tuple()
tuple() -> empty tuple tuple(iterable) -> tuple initialized from iterable's items
-
hex()
hex(number) -> string
-
oct()
oct(number) -> string
-
chr()
chr(i) -> character
-
ord()
ord(c) -> integer
string函数
-
str.capitalize()
>>> s = "hello" >>> s.capitalize() 'Hello'
-
str.replace()
>>> s = "hello" >>> s.replace('h', 'H') 'Hello'
-
str.split()
>>> ip = "192.168.1.123" >>> ip.split('.') ['192', '168', '1', '123']
序列处理函数
-
len()
>>>l = range(10) >>> len(l) 10
-
max()
>>>l = range(10) >>> max(l) 9
-
min()
>>>l = range(10) >>> min(l) 0
-
filter()
>>>l = range(10) >>> filter(lambda x: x>5, l) [6, 7, 8, 9]
-
zip()
>>> name=['bob','jack','mike'] >>> age=[20,21,22] >>> tel=[131,132] >>> zip(name, age) [('bob', 20), ('jack', 21), ('mike', 22)] >>> zip(name,age,tel) [('bob', 20, 131), ('jack', 21, 132)] #如果个数不匹配会被忽略
-
map()
>>> map(None, name, age) [('bob', 20), ('jack', 21), ('mike', 22)] >>> map(None, name, age, tel) [('bob', 20, 131), ('jack', 21, 132), ('mike', 22, None)] #个数不匹配时,没有值的会被None代替 >>> a = [1,3,5] >>> b = [2,4,6] >>> map(lambda x,y:x*y, a, b) [2, 12, 30]
-
reduce()
>>> reduce(lambda x,y:x+y, range(1,101)) 5050
lambda -> 列表表达式
-
map的例子,可以写成
print map(lambda x:x*2+10, range(1,11)) print [x*2+10 for x in range(1,11)]
-
非常的简洁,易懂。filter的例子可以写成:
print filter(lambda x:x%3==0, range(1,11)) print [x for x in range(1,11) if x%3 == 0]
第十一节 模块
简介
- 模块是python组织代码的基本方式
- python的脚本都是用扩展名为py的文本文件保存的,一个脚本可以单独运行,也可以导入另一个脚本中运行。当脚本被导入运行时,我们将其称为模块(module)
包
- python的模块可以按目录组织为包
-
创建一个包的步骤是:
- 建立一个名字为包名字的文件夹
-
在该文件夹下创建一个
__init__.py
文件 - 根据需要在该文件夹下存放脚本文件、已编译扩展及子包
-
import pack.m1, pack.m2, pack.m3
模块
-
模块名与脚本的文件名相同
-
例如我们编写了一个名为
items.py
的脚本,则可在另外一个脚本中用import items
语句来导入它
-
例如我们编写了一个名为
总结
- 模块是一个可以导入的python脚本文件
-
包是一堆目录组织的模块和子包,目录下的
__init__.py
文件存放了包的信息 -
可以用
import, import as, from import
等语句导入模块和包#假设有一个模块名为calc.py import calc import calc as calculate from calc import add
第十二节 正则表达式
目标
- 掌握正则表达式的规则
案例
- 一个小爬虫
简介
-
正则表达式(或re)是一种小型的、高度专业化的编程语言,(在python中)它内嵌在python中,并通过re模块实现
- 可以为想要匹配的相应字符串集指定规则
- 该字符集可能包含英文语句、e-mail地址、命令或任何你想搞定的东西
- 可以问诸如“这个字符串匹配该模式吗”
- “在这个字符串中是否有部分匹配该模式呢?”
- 你也可以使用re以各种试来修改或分割字符串
- 正则表达式模式被编译成一系列的字节码,然后由C编写的匹配引擎执行
-
正则表达式语言相对小型和受限(功能有限)
- 并非所有字符串处理都能用正则表达式完成
字符匹配
-
普通字符
- 大多数字母和数字一般都会和自身匹配
- 如正则表达式test会和字符串"test"完全匹配
-
元字符
. ^ $ * + ? {} [] \ | ()
-
[]
-
常用来指定一个字符集:
[abc] [a-z]
-
元字符在字符集中不起作用:
[akm$]
-
补集匹配不在区间范围内的字符:
[^5]
import re regExp = r't[0-9]p' print re.findall(regExp, 't1p t2p')
-
常用来指定一个字符集:
-
^
- 匹配行首。除非设置MULTILINE标志,它只是匹配字符串的开始。在MULTILINE模式里,它也可以匹配字符串中的每个换行。
-
$
- 匹配行尾,行尾被定义为要么是字符串尾,要么是一个换行字符后面的任何位置。
-
\
- 反斜杠后面可以加不同的字符以表示不同特殊意义
-
也可以用于取消所有的元字符:
\[
或\\
\d 匹配任何十进制数,它相当于[0-9] \D 匹配任何非数字字符,它相当于[^0-9] \s 匹配任何空白字符,它相当于[\t\n\r\f\v] \S 匹配任何非空白字符,它相当于[^\t\n\r\f\v] \w 匹配任何字母数字字符,它相当于[a-zA-Z0-9] \W 匹配任何非字母数字字符,它相当于[^a-zA-Z0-9]
-
重复
- 正则表达式第一功能是能够匹配不定长的字符集,另一个功能就是可以指定正则表达式的一部分的重复次数。
-
*
- 指定前一个字符可能被匹配零次或更多次,而不是只有一次。匹配引擎会试着重复尽可能多的次数(不超过整数界定范围,20亿)
-
+
- 表示匹配一次或更多次
- 注意 和+之间的不同: 匹配零或更多次,所以可以根本不出现,而+则要求至少出现一次
-
?
- 匹配一次或零次,你可以认为它用于标识某事物是可选的
-
{m,n}
-
其中
m
和n
是十进制整数。该限定符的意思是至少有m个重复,至多到n个重复 - 忽略m会认为下边界是0,而忽略n的结果将是上边界为无穷大(实现上是20亿)
-
{0,}
等同于*
,{1,}
等同于+
,而{0,1}
则与?
相同。如果可以的话,最好使用*
,+
或?
-
其中
-
使用正则表达式
-
re
模块提供了一个正则表达式引擎的接口,可以让你将REstring编译成对象并用它们来进行匹配 -
编译正则表达式
>>> import re >>> p = re.compile('ab*') >>> print p <_sre.SRE_Pattern object at 0x00000000004D1CA8>
-
re.compile()
也可以接受可选择的标志参数,常用来实现不同的特殊功能和语法变更p = re.compile('ab*', re.IGNORECASE)
反斜杠的麻烦
-
字符串前加
"r"
反斜杠就不会被任何特殊方式处理字符 阶段 \section 要匹配的字符串 \\section 为re.compile取消反斜杠的特殊意义 "\\\\section" 为"\\section"的字符串实值(string literals)取消反斜杠的特殊意义
执行匹配
-
'RegexObject'实例有一些方法和属性,完整的列表可查阅Python Library Reference
方法/属性 作用 match() 决定RE是否在字符串刚开始的位置匹配 search() 扫描字符串,找到这个RE匹配的位置 findall() 找到RE匹配的所有子串,并把它们作为一个列表返回 finditer() 找到RE匹配的所有子串,并把它们作为一个迭代器返回 如果没有匹配到的话,match()和search()将返回None。 如果成功的话,就会返回一个'MatchObject'实例。
-
MatchObject实例方法
方法/属性 作用 group() 返回被RE匹配的字符串 start() 返回匹配开始的位置 end() 返回匹配结束的位置 span() 返回一个元组包含匹配(开始,结束)的位置
-
实际程序中,最常见的作法是将'MatchObject'保存在一个变量里,然后检查它是否为None
p = re.compile('ab*', re.I) m = p.match('aaaabcccccabcc') if m: print 'Match found : ', m.group() else: print 'No match'
-
模块级函数
-
re模块也提供了顶级函数调用如
match()、search()、sub()、subn()、split()、findall()
等 -
查看模块的所有属性和方法:
dir(re)
编译标志-flags
标志 含义 DOTALL, S 使.匹配包括换行在内的所有字符 IGNORECASE, I 使匹配对大小写不敏感 LOCALE, L 做本地化识别(local-aware)匹配.法语等 MULTILINE, M 多行匹配,影响^和$ VERBOSE, X 能够使用REs的verbose状态,使之被组织得更清晰易懂 charref = re.compile(r""" ( [0-9]+[^0-9] #Decimal form | 0[0-7]+[^0-7] #Octal form | x[0-9a-fA-F]+[^0-9a-fA-F] #Hexadecimal form ) """, re.VERBOSE)
分组()
email = r"\w+@\w+(\.com|\.cn)"
一个小爬虫
-
下载贴吧或空间中所有图片
import re import urllib def getHtml(url): page = urllib.urlopen(url) html = page.read() return html def getImg(html): reg = r'src="(.*?\.jpg)" width' imgre = re.compile(reg) imglist = re.findall(imgre, html) x = 0 for imgurl in imglist: urllib.urlretrieve(imgurl, '%s.jpg' % x) x++ getImg(getHtml(url))
以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,也希望大家多多支持 码农网
猜你喜欢:本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。