4.调用函数

(1)Python 内置了很多有用的函数,我们可以直接调用:
abs()  ##########求绝对值
cmp()   #########比较大小
fact()   #############递归函数实现


练习:
############实现递归函数####################################################

# n! = 1x2x3x4x.......(n-1)xn= (n-1)!xn = (n-2)!x(n-1)xn
1!    =     1
2!    =     (2-1)! x 2                      =    fact(2-1) x 2
3!    =     (3-1)! x 3 = (2-1)! x 2 x 3    =    fact(3-1) x 3   =  fact(1)x 2 x3
###########
代码:
def fact(n): 
    if not isinstance(n,int):
        print 'input int num'
    if n==1:
        return 1   ###递归结束条件,当n==1时,结束
    return fact(n-1)*n
print fact(10)
print fact(1)
注意:

1:在写递归函数时要有一个明确的结束条件。
2:在递归时,问题规模要越来越小。
3:递归函数效率不高,函数调用是通过栈的数据结构实现的,每调用一次,栈就会多一层,最多999层,否则会出现栈溢出。
截图:
wKioL1lmVvOT7nOgAACifIVB7LY976.png-wh_50
#################################实现二分效果############################
当n=10时
返回值为
5
2
1

代码:
def fun(n):   ##########n是形式参数
    if not isinstance(n, int):
        print 'input int num'
    print n
    b = int(n/2)
    if b >0:
        return fun(b)
fun (10)

截图:
wKiom1lmV0GQO220AACfDtQ5MN0437.png-wh_50

(2)数据类型转换函数:
int(), float(), str(),unicode(),bool()

5.理解函数名
函数名与变量名类似,其实就是指向一个函数对象的引用;
给这个函数起了一个“别名”:函数名赋给一个变量空函数


6.变量的作用域
局部变量:只能在函数内部使用的变量
全局变量:在整个程序中使用的变量
global关键字:强制将局部变量转换为全局变量

代码分析:

b=2     #############全局变量,在整个代码中生效。
def a():
    b=1   ###########局部变量,只在函数内生效。
    print b
a()
print b

截图:虽然给b赋值为1,但因为是局部变量所以输出b为2

wKioL1lmV1qzWcVSAABzvAOnxmU274.png-wh_50
代码分析:

b=2
def a():  #############全局变量,在整个代码中生效。
    global b  ##########声明变量
    b=1     ###########局部变量,只在函数内生效。
    print b
a()
print b
截图:
wKioL1lmV2eBYn94AABspMIhkIQ596.png-wh_50

##################函数式编程#############################
面向对象编程语言:java ,c++,python
面向过程编程语言:C
面向函数编程语言:(lisp,erlang)
截图:
wKiom1lmWKbjJn3cAADOGG70eXc811.png-wh_50






##############高级特性#############

1.列表生成式
列表生成式是Python 内置的非常简单却强大的可以用来创建list的生成式
方法一:for循环
方法二:列表生成式

(1)思考:

要生成 list [1, 2, 3, 4, 5, 6, 7] 可以用 range(1, 8)
但如果要生成 [1x1, 2x2, 3x3, ..., 7x7] 怎么做?

代码:

list1=[]     ###########建一个空列表接收执行结果
list = range(1,8)######建立一个列表
for x in list:  #####list1 中的值来源
    a =x*x
    list1.append(a)   ###list1列表值的增加
print list1

截图:
wKiom1lmV4rQUqTPAACMI8gY5-s453.png-wh_50


wKiom1lmWNDCnlsLAABtqdstKr4484.png-wh_50

(2)思考:

列表生成式可以嵌套if语句和for语句么?
- 生成100以内所有偶数的平方;
- 生成‘ABC’与‘123’的全排列;

wKioL1lo5v_CuB5_AACYcqKIK0Y652.png-wh_50

wKiom1lo5wDx6aJvAAB5hWsbRXo299.png-wh_50

wKioL1lo5wHx46VyAACuMvQS-5A629.png-wh_50

wKiom1lo5wKzC-8kAAB3cGriDNM090.png-wh_50


wKiom1lo5yeiPKybAAByoXym4bA251.png-wh_50

(3)思考
列表生成式也可以使用两个变量来生成 list么?
- 生成字典的的内容,格式为‘key=value’,返回其列表
格式;
- 将list中所有的字符串变为小写字母;

wKioL1lo5yjibMqfAACehh8Bb18783.png-wh_50

wKioL1lo5ymjcSYQAACfUPe3Jv0682.png-wh_50


2.迭代
可以通过 for 循环来遍历这个 list 或 tuple,这种遍历我们称为迭代(Iteration)
只要是可迭代对象,无论有无下标,都可以迭代,比如 dict就可以迭代:

(1)如何判断一个对象是可迭代对象呢?

方法是通过 collections 模块的 Iterable 类型判断迭代

from collections import Iterable########导入 collections 模块的 Iterable 类型

isinstance('hello',Iterable)    ######判断字符串是否是迭代
Out[9]: True

isinstance(1,Iterable)          ######判断×××是否是迭代
Out[10]: False

isinstance([1,2,3],Iterable)   ######判断列表是否是迭代
Out[11]: True

isinstance({1,2,3},Iterable)  ######判断集合是否是迭代
Out[12]: True

isinstance({"name":"zhang"},Iterable)######判断字典是否是迭代
Out[13]: True

isinstance((1,2,3),Iterable)   ######判断元组是否是迭代
Out[14]: True

(2)枚举方法,显示为索引元素对。
代码:
shopinfo =[
    ('Iphone',1000),
    ('book',200),
    ('fentiao',3500)
]

for i ,v in enumerate(shopinfo):
    print i,v
截图:


wKioL1lmWTuSctdQAAC1nUo__do444.png-wh_50


(3)for 循环里,同时引用了两个变量。
代码:
shopinfo =[
    ('Iphone',1000),
    ('book',200),
    ('fentiao',3500)
]

for k,v in shopinfo:
    print k,v

截图:

wKioL1lmWQ3SWWiKAACykGvaSPM082.png-wh_50


3.生成器


(1)为什么需要生成器?
通过列表生成式,我们可以直接创建一个列表,受到内存限制,列表容量肯定是有限的;
创建一个包含 100 万个元素的列表,占用很大的存储空间;列表生成如果需要前几个元素,浪费空间

(2)生成器是什么?
在循环的过程中不断推算出后续的元素呢?这样就不必创建完整的list,从而节省大量的空间。在 Python 中,这种一
边循环一边计算的机制,称为生成器(Generator)

(3)怎么创建生成器?把一个列表生成式的 [] 改成 ()

使用g.next()方法依次读取元素(麻烦)
截图:

wKiom1lmWhOB9T_rAABTXtOov50016.png-wh_50


使用 for 循环(推荐)
代码:
l= (i for i in range(10)) ############列表生成式
g= (i for i in range(10))  ##########生成器
from collections import Iterable 
isinstance(g,Iterable)  #####查看生成器是否迭代
Out[4]: True
type(g)              #########查看g的类型
Out[5]: generator
for i in g:     #####3使用 for 循环
    if i < 5:
        print i
       
0
1
2
3
4

截图:

wKiom1lmWbiCCYIkAABx-T1idzo688.png-wh_50
(4)python编程:

著名的斐波拉契数列(Fibonacci),除第一个和第二个数
外,任意一个数都可由前两个数相加得到:1, 1, 2, 3,5, 8, 13, 21,...


wKioL1lmWkGTsZIGAABSLmUwXtE859.png-wh_50

代码:
def fib(max):
     n,a,b=0,0,1
     while n < max:
         print b
         a,b = b,a+b
         n +=1
fib(4)

截图:

wKiom1lmWoGDWsZKAACjHIVzVe4001.png-wh_50




(4)手动实现生成器:

########yield关键字#########
练习:通过改变以下代码,然后观察结果,了解yield关键字
def hello():
    print 'a'
    yield 1
    print 'b'
    yield 2
    print 'c'
    yield 3
a = hello()
print type(a)
print a.next()
print a.next()
print a.next()
截图多个:

wKiom1lmWqeRwgkbAACjd-JoVgo204.png-wh_50

wKioL1lmWqigefVuAACwQsZysoY218.png-wh_50

wKioL1lmWqmiAtGeAACdu6b4BnI268.png-wh_50

wKiom1lmWqrCBxFDAAChrccoRVs958.png-wh_50

wKiom1lmWquSSg8YAADGbsfsVi0177.png-wh_50


wKioL1lmWt-QVCIyAAC0YK5Hon8675.png-wh_50


斐波拉契数列使用yield关键字截图:

wKiom1lmWuLC8m7AAACyi0_Tls8441.png-wh_50

(5)异步I/O模型epoll    http nginxtomcat

消费者代码:
def consumer(name):
    print '%s 准备吃粉条了!' %(name)
    while True:
       fentiao = yield
       print('粉条[%s]做出来了,被[%s]吃了')%(fentiao,name)
g = consumer("xiaobai")
g.next()
g.send('孜然味')
截图:

wKiom1lmWyPCgmKcAAE2kleQkvk736.png-wh_50


生产者代码:
import time
def producer(name):
    c1 = consumer('xiaobai')
    c2 = consumer('heidong')
    c1.next()
    c2.next()
    print '开始制作粉条晚餐了.....'
    for i in range(1,6):
        time.sleep(1)
        print '[%s]做了两份粉条,两个人一起吃'%(name)
        c1.send(i)
        c2.send(i)
producer('diner')

截图:
wKiom1lmWyWQkxXoAAFykpUXQFs566.png-wh_50 

wKioL1lmW1nhU6lJAAHC84xoy70609.png-wh_50