Python中可變變量與不可變變量詳解
前言:
C++不同于Python
的顯著特點(diǎn),就是有指針和引用,這讓我們?cè)谡{(diào)用參數(shù)的時(shí)候更加清晰明朗。但Python
中沒有指針和引用的概念,導(dǎo)致很多時(shí)候參數(shù)的傳遞和調(diào)用的時(shí)候會(huì)產(chǎn)生疑問:我到底是復(fù)制了一份新的做操作還是在它指向的內(nèi)存操作?
這個(gè)問題根本上和可變、不可變變量有關(guān),我想把這個(gè)二者的區(qū)別和聯(lián)系做一個(gè)總結(jié),以更深入地理解Python
內(nèi)部的操作。我本身非科班出身,如有不當(dāng)之處敬請(qǐng)批評(píng)指正。
一 、常見的變量分類
1、變量的創(chuàng)建
在了解可變、不可變變量的基本定義之前,我們需要明白變量是如何被創(chuàng)建的。
x = 1
python
解釋器會(huì)判斷1在內(nèi)存中是否存在,若不存在,python
會(huì)分配內(nèi)存,在內(nèi)存中創(chuàng)建數(shù)字1,然后看變量x是否存在,若不存在就創(chuàng)建x,最后把1賦值給x。
y = 1
當(dāng)繼續(xù)輸入上行代碼時(shí),1已經(jīng)在內(nèi)存中被創(chuàng)建了,現(xiàn)在是否需要重新創(chuàng)建一個(gè)1,然后賦值給y呢?還是直接將剛才就創(chuàng)建好的1賦值給y呢?答案是后者。我們可以通過id或者is來判斷是否在內(nèi)存中是同一個(gè)地址。
print(id(x) == id(y)) # or print(x is y)
但當(dāng)我們換成一個(gè)列表來嘗試呢?
a = [1,2,3] b = [1,2,3] print(id(a) == id(b))
答案卻和上面的結(jié)果相反,也就是說內(nèi)存中即使有了x的[1,2,3],python
中要?jiǎng)?chuàng)建把[1,2,3]賦給y的時(shí)候并沒有把x指向的那個(gè)賦過去,而是重新在內(nèi)存中開辟了一塊新的空間,創(chuàng)建了一個(gè)新的[1,2,3]!這就引出了可變和不可變變量。
字面意思
按照我的個(gè)人理解,可變變量(mutable variable
)就是內(nèi)存中內(nèi)容可以被修改的變量,而不可變變量(immutable variable
)就是內(nèi)存中內(nèi)容不可以被修改的變量。
聽起來比較抽象。我們可以把變量名理解為一個(gè)指針或者引用,他們都指向了內(nèi)存中的一塊空間。比如上節(jié)中x和y同時(shí)指向了1的那塊空間,a指向了[1,2,3]的那部分。那么如何理解內(nèi)存中的內(nèi)容可以被修改呢?對(duì)于一個(gè)int型的變量,我創(chuàng)建了1,那么這之后*任何在這個(gè)作用域中所有被賦為1 的變量都會(huì)指向它,而外部沒有方法來把這個(gè)內(nèi)存中的內(nèi)容改成2或者其他值*。而對(duì)于列表來說,那塊[1,2,3]我隨時(shí)可以把他改為[1,2,3,4],這就是內(nèi)存中內(nèi)容可以被修改。
二、變量分類
所有的變量都可以按可變、不可變變量來分類,那么我將常用的一些變量類型進(jìn)行分類。
1、、常見的不可變變量
- 整型
- 浮點(diǎn)型
- 布爾型
- 復(fù)數(shù)
- 字符串
- 元組
2、常見的可變變量
- 列表
- 集合
- 字典
- 其他迭代器
三、拷貝的差別
copy
和deepcopy
都表示拷貝,那么二者的區(qū)別就在于可變、不可變對(duì)象。copy
和deepcopy
對(duì)于不可變對(duì)象來說是沒有區(qū)別的,都是把指向內(nèi)存已有的空間的引用進(jìn)行拷貝;但對(duì)于可變對(duì)象,copy是拷貝指向內(nèi)存已有空間的引用,而deepcopy
才是新開辟一塊空間,將原來的內(nèi)容完全拷貝,然后返回新的空間的引用。
四、參數(shù)傳遞的差別
參數(shù)傳遞的過程也是很容易出現(xiàn)疑惑的過程。C++
中的參數(shù)傳遞很明確,引用就是引用,形參就是形參,但Python
中不是,因?yàn)?code>python中沒有明確的指針、引用。
對(duì)不可變變量,傳遞進(jìn)函數(shù)后由于作用域改變,函數(shù)內(nèi)部有新的空間,因此會(huì)產(chǎn)生形參,將原來的不可變變量進(jìn)行復(fù)制,然后在函數(shù)內(nèi)部進(jìn)行后續(xù)操作。
對(duì)可變變量,本身內(nèi)容就可以被修改,那么在函數(shù)內(nèi)部也允許修改本身,因此傳遞進(jìn)函數(shù)的是該內(nèi)存空間的引用,對(duì)該參數(shù)操作,相應(yīng)的在主函數(shù)也會(huì)被修改。
到此這篇關(guān)于Python中可變變量與不可變變量詳解的文章就介紹到這了,更多相關(guān)Python中可變變量與不可變變量?jī)?nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Python定義函數(shù)時(shí)參數(shù)有默認(rèn)值問題解決
這篇文章主要介紹了Python定義函數(shù)時(shí)參數(shù)有默認(rèn)值問題解決,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2019-12-12基于Python-Pycharm實(shí)現(xiàn)的猴子摘桃小游戲(源代碼)
這篇文章主要介紹了基于Python-Pycharm實(shí)現(xiàn)的猴子摘桃小游戲,本文通過實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2021-02-02Python+OpenCV實(shí)現(xiàn)旋轉(zhuǎn)文本校正方式
今天小編就為大家分享一篇Python+OpenCV實(shí)現(xiàn)旋轉(zhuǎn)文本校正方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2020-01-01Python實(shí)戰(zhàn)之大魚吃小魚游戲的實(shí)現(xiàn)
這篇文章主要介紹了如何利用Python制作一個(gè)經(jīng)典游戲之大魚吃小魚,文中的示例代碼講解詳細(xì),對(duì)我們學(xué)習(xí)Python有一定幫助,需要的可以參考一下2022-04-04Python3 使用pip安裝git并獲取Yahoo金融數(shù)據(jù)的操作
這篇文章主要介紹了Python3 使用pip安裝git并獲取Yahoo金融數(shù)據(jù)的操作,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2021-04-04Python一行代碼識(shí)別增值稅發(fā)票實(shí)現(xiàn)示例
這篇文章主要為大家介紹了Python一行代碼識(shí)別增值稅發(fā)票實(shí)現(xiàn)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-03-03python使用循環(huán)實(shí)現(xiàn)批量創(chuàng)建文件夾示例
這篇文章主要介紹了python使用循環(huán)實(shí)現(xiàn)批量創(chuàng)建文件夾示例,需要的朋友可以參考下2014-03-03使用jupyter Nodebook查看函數(shù)或方法的參數(shù)以及使用情況
這篇文章主要介紹了使用jupyter Nodebook查看函數(shù)或方法的參數(shù)以及使用情況,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2020-04-04