Python高級編程1-閉包,迭代器,裝飾器,生成器

從新導入

import imp
imp.reload(模塊)

循環導入

程序會掛掉

a.py

import b
b.bTest()

def aTest():
    print("a")

b.py

import a
a.aTest():

def bTest():
    print("b")

==,is

a = [11,22,33]
b = [11,22,33]

a==b 爲 true
a is b 爲 false

c = a
c is a 爲true

== 內容是否相同

is 指向是否同一個東西(地址是否相同)

附加

a= 100
b = 100
a is b -- true
有範圍限制

深拷貝,淺拷貝

淺拷貝

a = [11,22,33]
b = a #a指向的地址賦值給b,這就是淺拷貝

深拷貝

import copy

a = [11,22,33]
c = copy.deepcopy(a)

此時a,b的ID不一樣,指向的地址不相同

a = [11,22,33] 
b = [44,55,66]
c = [a,b]

d = c #淺拷貝
e = copy.deepcopy(d) #深拷貝,遞歸拷貝

#e[0] = [11,22,33]
a.append(44) #a=[11,22,33,44]
c[0] = [11,22,33,44]
e[0] = [11,22,33]

copy

f = copy.copy(d)  #只拷貝第一層,不會遞歸拷貝

若d爲不可變類型,如元組時,則拷貝爲淺拷貝(其地址所指向的對象爲同一個內容,其ID相同)

進制,位運算

進制轉換

二進制
a = bin(18)

八進制
a = oct(18)

十六進制
a = hex(18)

十進制
int(數,進制數)
int("0x12",16)

位運算

左移

a = a<<1

右移

a = a>>1

按位與

7&8

按位或

7|8

按位異或

7^8

按位取反

a = ~a

私有化

class Test(object):
    def __init__(self):
        self.num = 100 #可以直接使用

t = Test()
t.num #直接使用

在屬性名加兩個_,後使屬性私有化

名字重整

私有屬性名字重整

t = Test()
dir(t) #可以查看一下

_名字

禁止from xxx import * 來導入
但是 import xxx 還是能使用的

property

class Test(object):
    def __init__(self):
        self.__num = 100

    def getNum(self):
        return self.__num

    def setNum(self,num):
        self.__num = num

    __num = property(getNum,setNum)



t = Test()
t.num = 1 #相當於t.setNum(1)
print(t.num) #相當於t.getNum()

使用裝飾器(相當於註解)

class Test(object):
    def __init__(self):
        self.__num = 100

    @property #1)聲明瞭num. 2)聲明瞭getter
    def num(self):
        return self.__num

    @num.setter #聲明setter
    def num(self,num): #命名必須爲property所聲明的名字:num
        self.__num = num


t = Test()
t.num = 1 #相當於t.setNum(1)
print(t.num) #相當於t.getNum()

迭代器

使用for來迭代

for temp in list

可迭代對象

list,tuple,dict,set,str

generator:
    a = (x for x in range(10))

判斷是否可迭代

from collections import Iterable

isinstance("abc",Iterable) #判斷是否可迭代對象

列表不是可迭代對象,但是可以迭代,只是不可以使用next(list).

生成可迭代對象

iter(list)

閉包

一個函數裏定義一個函數,並且在內部函數使用了外部函數的變量,稱該整體爲閉包

def test(num1):

    def test_in(num2):
        print(num1+num2)

    return test_in

ret = test(100) #把100存在num1
ret(1)  #打印101
ret(100) #打印200
ret(200) #打印300

裝飾器

def w1(func):
    def inner():
        print("--w1--")
        func() 
    return inner

def f1():
    print("---f1---")

f1 = w1(f1)
f1()

使用@

@w1
def f1():
    print("---f1---")

什麼時候執行裝飾器

def w1(func):
    print("--正在裝飾--")
    def inner():
        print("--w1--")
        func() 
    return inner

@w1
def f1():
    print("---f1---")

等價於執行
f1 = w1(f1) 
打印:--正在裝飾--

兩個裝飾器

@w1
@w2
def f1():
    print("---f1---")

等價於
    f1 = w1(w2(f1))

傳遞不定長參數 ###

@w1
def f1():
    print("---f1---")

什麼時候執行裝飾器

def w1(func):
    print("--正在裝飾--")
    def inner(*args,**kwargs):
        print("--w1--")
        func(*args,**kwargs) #此處的*爲解包,使其爲最初始調用的形式傳遞 
    return inner

@w1
def f1(*args,**kwargs):
    print("---f1---")

有返回值的函數的裝飾器

def w1(func):
    print("--正在裝飾--")
    def inner():
        print("--w1--")
        a = func()
        print("----")
        return a 
    return inner

@w1
def f1():
    print("---f1---")   
    return "abc"

通用裝飾器

def w1(func):
    def inner(*args,**kwargs):
        print("--w1-start--")
        ret = func(*args,**kwargs) #此處的*爲解包,使其爲最初始調用的形式傳遞
        print("--w1-end--")
        return ret 
    return inner

怎麼通用呢?

1)可變參數,隨你怎麼傳,只要合規定的來

2)有返回值

帶有參數的裝飾器

def func_arg(arg):
    def func(f):
        def func_in():
            f()
    print("arg=%s"%arg)
    return func

@func_arg("hello")
def f1():
    pass

作用域

查看全局變量

globals()

查看局部變量

locals()

def f():
    a=100
    print(locals())

局部變量使用優先級高於全局變量

查看內嵌

dir(buildin)

變量使用順序

局部–>全局–>內嵌

動態

動態添加屬性

class Person(object):
    def __init__(self,name,age):
        self.age = age
        self.name = name

a = Person()
a.addr = "asdf"
print(a.addr) #給對象添加屬性,不會影響類

Person.addr = "aaaa" #給類添加屬性

動態添加方法

對象綁定普通方法

def func(self):
    pass

import types
p1.func = types.MethodType(func,p1)#給對象添加方法

xxx = types.MethodType(func,p1)
xxx() 等價於 p1.func()

類綁定靜態方法

@staticmethod
def func():
    pass

P.func = func

類綁定類方法

@classmethod
def func(cls):
    pass

P.func = func() 

slots

插槽,限制屬性

class Person():
    __slots__ = ("name","age")

p = Person()
p.name = "asdf"

p.a = 10 #拋錯

生成器

列表生成式

a = [x for x in range(10)]

end

生成器說明:什麼時候用,什麼時候生成

保存的是一種算法.

創建生成器

a = (x for x in range(10))

使用

next(a)

yield 創建生成器

def func():
    for x in rang(10):
        print("---1---")
        yield x #執行到這裏會停止下來,把值並返回
        print("---2---") #下一次從這裏開始執行

x = func() #返回值爲一個生成器
next(x)

使用for循環遍歷生成器

for x in a:
    pass

對生成器的操作

a.next()等價於next(a)

send

def func():
    for x in rang(10):
        temp = yield x #執行到這裏會停止下來,把值並返回
        print("---%s---"%temp)

x = func() #返回值爲一個生成器
x.send("kkk") #把參數傳遞到temp   

x.send(None)等價於next

實現多線程任務

def thread1():
    while True:
        print("---1---")
        yeild None

def thread2():
    while True:
        print("---2---")
        yeild None

t1 = thread1()
t2 = thread2()

while True:
    t1.__next__()
    t2.__next__()
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章