目錄
4.12、傳參如果爲不可變對象,利用全局變量可以改變外部不可變對象的值
4.14、採用複製的方法可以使傳參爲可變類型,但是不影響函數外部變量。
1、函數的好處
➢函數是重用的程序段,允許給一塊語句一個名稱
➢ 在程序的任何地方使用這個名稱任意多次地運行這個語句塊,此方 式被稱爲調用函數。
➢ 之前的示例已經使用了許多內建的函數,比如len和range
➢ 通過改變函數的參數,可以最大程度的複用代碼
2、自定義函數
你可以定義一個函數,以下爲簡單的原則:
- 函數代碼塊要以def關鍵字開頭,後面是函數名稱和括號()
- 任何傳入的參數和自變量必須放在括號內,圓括號之間可以用於定義參數。
- 函數的第一行語句可以用來選擇性的使用文檔字符串用於存放函數說明
- 函數內容以:開始,並且縮進
- return結束函數,選擇性的返回一個值給調用方,不帶return表達式的則返回None
2.1、語法
def 函數名(參數):
函數體
示例:
>>> def func(a,b):
... return a-b
...
>>> func(9,2)
7
>>>
問題:函數和方法的區別?
- 函數:在類外面(class)外部定義的可執行函數,都是函數
- 方法:在類內部,與類和實例有綁定關係的函數,都是方法
注意事項:
- 函數的名字最好不要和內置函數的名字一致,這樣有可能在使用內置函數時,會出現一些錯誤。
3、函數的調用
定義完一個函數後,怎麼調用該函數?請看下方的例子
#coding=utf-8
'''定義一個函數,該函數主要是用來打印一句話'''
def func(s):
return s
#調用該函數,直接輸入函數名
func("i am a good boy")
結果爲空:
============================== RESTART: E:\b.py ==============================
>>>
原因:這是因爲在函數體內,沒有輸入print,則無法打印該函數,一共有2種改變方式,第一種爲print寫在函數體內,第二種爲print寫在調用函數的時候。
方法一:print寫在函數體內
#coding=utf-8
'''定義一個函數,該函數主要是用來打印一句話'''
def func(s):
print(s)
return
func("i am a good boy")
方法2:print寫在調用函數的時候:
#coding=utf-8
'''定義一個函數,該函數主要是用來打印一句話'''
def func(s):
return s
print(func("i am a good boy"))
結果:
============================== RESTART: E:\b.py ==============================
i am a good boy
>>>
3.1、函數體內輸入print和return有什麼區別?
- 首先函數體是允許沒有返回值的,也就是函數體內沒有return,這樣做的結果就是該函數不能被後續的程序中使用。
- return只是返回值,如果想打印結果,還是必須得有print輸出的,如果只有return,則仍然需要print,另外,函數體內如果有return語句則在後續程序中可以調用該返回值。
注意事項:
- 1個函數體內可以有多個return語句,但是隻會執行第一個return語句。
- 當調用函數的時候,如果函數體內沒有print,則在調用函數的時候,也需要輸入print才能打印出來結果
- 在使用函數調用參數的時候,最好是判斷一下參數的類型,判斷類型只能使用isinstance
4、參數傳遞
4.1、可更改和不可更改類型
在python中,類型屬於變量,變量是沒有類型的。
- 不可變類型:字符串、元組、數字
- 可變類型:列表、字典、集合
python中函數的參數傳遞:
- 不可變類型:類似c++的值傳遞,如整數、字符串、元組、 func(a)傳遞的只是a的值,並沒有影響a對象本身
- 可變類型:類似c++的引用傳遞,如列表、字典、 func(la)傳遞的是la這個對象,通過函數修改la後,同樣la也是受影響的。
4.11、傳遞一個參數爲不可變對象
示例1:外部的不可變對象和傳參都是同一個值時:
#coding=utf-8
'''定義一個函數,外部的不可變對象和傳參爲同一個值時'''
a="i am a good boy!"
def func(a):
a+="hello world"
return a
print(func(a))
print(a)
結果:
============================== RESTART: E:\b.py ==============================
i am a good boy!hello world
i am a good boy!
>>>
示例2:外部不可變對象和傳參不爲同一個值時,重新賦值
#coding=utf-8
a=10
def func(b):
b=20
return b
print(func(a))
print(a)
結果:
============================== RESTART: E:\b.py ==============================
20
10
>>>
總結:在函數內部引入不可變對象,不能改變函數外該對象的值。
4.12、傳參如果爲不可變對象,利用全局變量可以改變外部不可變對象的值
局部變量:定義在函數內部的變量擁有一個局部作用域,只能在被聲明的函數內部訪問
全局變量:定義在函數外部的擁有全局作用域,可以在全程序訪問,用global代表全局變量。
示例:使用global關鍵字,則可以將不可變對象在函數內外都改變
#coding=utf-8
'''用global關鍵字來改變不可變對象'''
#如果沒有gloabl關鍵字,查看數值
a=10
def changint(a):
a+=1
return a
print(changint(a))
print(a)
print("---------------")
#如果有global關鍵字,查看數值
b=20
def changint_2():
global b
b-=13
return b
print(changint_2())
print(b)
結果:
============================== RESTART: E:\b.py ==============================
11
10
---------------
7
7
>>>
總結:傳入不可變對象,如果想要函數內外都變化,可以採用全局變量的方式。
4.13、傳遞參數爲可變變量
結果:引入可變變量,在函數內修改了參數,那麼在調用該函數的函數裏,原始數據也改變了。
示例1:外部的可變變量和傳參都是同一個值時
#coding=utf-8
"""外部變量傳遞的是一個可變變量"""
a={1:"a",2:"b",3:"c",4:"d"}
def changdict(a):
a[1]="hello"
return a
print(changdict(a))
print(a)
結果:
============================== RESTART: E:\b.py ==============================
{1: 'hello', 2: 'b', 3: 'c', 4: 'd'}
{1: 'hello', 2: 'b', 3: 'c', 4: 'd'}
>>>
示例2:外部的可變變量和傳參不一致時
#coding=utf-8
"""外部變量傳遞的是一個可變變量"""
c=[1,2,3,4,5]
def changelist(d):
d.append("a")
return d
print(changelist(c))
print(c)
結果:
============================== RESTART: E:\b.py ==============================
[1, 2, 3, 4, 5, 'a']
[1, 2, 3, 4, 5, 'a']
>>>
4.14、採用複製的方法可以使傳參爲可變類型,但是不影響函數外部變量。
示例:通過複製的方法,改變其中一個變量,另一個不會改變
#如果是直接賦值的方式,則兩個變量是相同的,id地址也相同
>>> a=[1,2,3]
>>> b=a
>>> id(a)
2114062603656
>>> id(b)
2114062603656
>>> a.append("a")
>>> a
[1, 2, 3, 'a']
>>> b
[1, 2, 3, 'a']
>>> id(a)
2114062603656
>>> id(b)
2114062603656
>>>
#如果採用的是複製的方法,兩個變量的id地址不一樣
>>> a
[1, 2, 3, 'a']
>>> b=a[:]
>>> id(a)
2114062603656
>>> id(b)
2114062566216
>>> a.pop(0)
1
>>> a
[2, 3, 'a']
>>> b
[1, 2, 3, 'a']
>>>
#coding=utf-8
"""外部變量傳遞的是一個可變變量,但是採用複製的方法傳參,則不會改變外部變量"""
c=[1,2,3,4,5]
def changelist(d):
d.append("a")
return d
print(changelist(c[:]))
print(c)
結果:
============================== RESTART: E:\b.py ==============================
[1, 2, 3, 4, 5, 'a']
[1, 2, 3, 4, 5]
>>>
4.15、總結
- 不可變對象:所有的數字、字符串、元組
- 可變:集合,字典、列表、實例
- 參數傳不可變對象的時候,函數內外變量值是獨立的,不會改變函數外部的變量值
- 參數傳可變對象的時候,函數內外變量值是關聯的,會改變函數外部的變量值。
- 傳入可變對象,如果想要不改變外部變量,則採用複製的方法,則可以不改變外部變量
- 傳入不可變對象,如果想要函數內外都改變,則可以使用全局變量的方式。
4.2、參數
- 無參參數
- 必須參數
- 關鍵字參數
- 不定長參數
- 默認參數
4.21、無參參數
示例:
#coding=utf-8
def printstr():
print("i am a boy")
printstr()
4.22、必備參數
必備參數需要以正確的順序傳入參數,調用時的數量和聲明的數量必須保持一致,否則會報錯。
示例:
#coding=utf-8
def sum(a,b,c):
result=0
result=a+b*c
return result
print(sum(1,2,3))
print(sum())
print(sum(1,2,3,4,5,6))
結果:
============================== RESTART: E:\b.py ==============================
7
Traceback (most recent call last):
File "E:\b.py", line 9, in <module>
print(sum())
TypeError: sum() missing 3 required positional arguments: 'a', 'b', and 'c'
>>>
4.23、命名參數(關鍵字參數)
關鍵字參數和函數的調用關係緊密,函數調用使用關鍵字參數來確定傳入的參數值,使用關鍵字參數允許函數調用時和聲明時不一致。
示例:
#coding=utf-8
def information(name,age,sex):
print("名字爲:",name)
print("年齡爲:",age)
print("性別爲:",sex)
return
print(information(sex="女",age="18",name="耿值"))
結果:
============================== RESTART: E:\b.py ==============================
名字爲: 耿值
年齡爲: 18
性別爲: 女
None
>>>
注意事項:
傳參時,命名參數必須在非命名參數的後面,否則會報錯。
4.24、缺省參數(默認參數)
把推薦值作爲默認值比較好
示例:
#coding=utf-8
def information(age,sex,name="孫"):
print("名字爲:",name)
print("年齡爲:",age)
print("性別爲:",sex)
return
print(information(sex="女",age="18"))
print(information(sex="女",age="18",name="helloword"))
結果:
============================== RESTART: E:\b.py ==============================
名字爲: 孫
年齡爲: 18
性別爲: 女
None
名字爲: helloword
年齡爲: 18
性別爲: 女
None
>>>
注意事項:
- 默認參數必須放在沒有默認值的最後放,否則會報錯。
- 默認參數建議必須指向不可變對象。
- 一旦調用默認參數時,重新賦值,則按照重新賦值的那個對象計算。
4.25、不定長參數
當不確定輸入的參數是幾個時,可以使用不定長參數
- *arg:以元組的形式導入,存放所有未命名的變量參數。
- **kw:以字典的形式導入,存放所有未命名的變量參數。
示例1:*arg代表一個元組,存放所有的未命名參數
#coding=utf-8
def func(a,*arg):
result=a
print(arg)
for j in arg:
result+=j
return result
print(func(1,2,3,4,5,6,7))
結果:
============================== RESTART: E:\b.py ==============================
(2, 3, 4, 5, 6, 7)
28
>>>
示例2:**kw代表一個字典
#coding=utf-8
def func(a,**kw):
result=a
for k,v in kw.items():
if not isinstance(v,int):
return None
result+=v
return result
print(func(1,e="a",b="c"))
print("-------")
print(func(1,e=2,c=4))
結果:
============================== RESTART: E:\b.py ==============================
None
-------
7
>>>
4.26、函數返回多個值
如果你想返回多個值,將它放到一個容器中就可以了
示例:
>>> def sum(a,b):
... return a,b
...
>>> sum(1,2)
(1, 2)
>>>