您好,登錄后才能下訂單哦!
怎么在Python中模擬實現(xiàn)指針?針對這個問題,這篇文章詳細介紹了相對應(yīng)的分析和解答,希望可以幫助更多想解決這個問題的小伙伴找到更簡單易行的方法。
在Python中模擬實現(xiàn)指針
因為Python中的指針本身不存在,但并不意味著無法使用指針。實際上有多種方法可以在Python中模擬指針。
這里用兩種方法來實現(xiàn):
使用可變類型作為指針【Python中的變量】
使用自定義Python對象【Python中的對象】
使用可變類型作為指針
您已經(jīng)了解了可變類型。因為這些對象是可變的,所以您可以將它們視為指向模擬指針行為的指針。假設(shè)您要復(fù)制以下c代碼:
void add_one (int * x ) { * x + = 1 ; }
此代碼采用指向整數(shù)(*x)的指針,然后將該值遞增1。這是一個練習(xí)代碼的主要功能:
#include <stdio.h> int main(void) { int y = 2337; printf("y = %d\n", y); add_one(&y); printf("y = %d\n", y); return 0; }
在上面的代碼中,分配2337給y,打印出當(dāng)前值,將值遞增1,然后打印出修改后的值。執(zhí)行此代碼的輸出如下:
y = 2337 y = 2338
在Python中復(fù)制此類行為的一種方法是使用可變類型??紤]使用列表并修改第一個元素:
>>> def add_one (x ): ... x [ 0 ] + = 1 ... >>> y = [ 2337 ] >>> add_one (y ) >>> y [ 0 ] 2338
在這里,add_one(x)訪問第一個元素并將其值增加1。使用一種list方法,最終結(jié)果似乎已修改了該值。那么Python中的指針確實存在嗎?好吧,這是唯一可能的,因為它list是一種可變類型。如果您嘗試使用a tuple,則會收到錯誤消息:
>>> z = (2337,) >>> add_one(z) Traceback (most recent call last): File "<stdin>", line 1, in <module> File "<stdin>", line 2, in add_one TypeError: 'tuple' object does not support item assignment
上面的代碼演示了這tuple是不可變的。因此,它不支持項目分配。list不是唯一可變的類型。在Python中模仿指針的另一種常見方法是使用a dict。
假設(shè)您有一個應(yīng)用程序,您希望每次發(fā)生有趣事件時都要跟蹤它。實現(xiàn)此目的的一種方法是創(chuàng)建一個dict并使用其中一個項目作為計數(shù)器:
>>> counters = {"func_calls": 0} >>> def bar(): ... counters["func_calls"] += 1 ... >>> def foo(): ... counters["func_calls"] += 1 ... bar() ... >>> foo() >>> counters["func_calls"] 2
在此示例中,counters字典用于跟蹤函數(shù)調(diào)用的數(shù)量。打電話后foo(),計數(shù)器已2按預(yù)期增加。所有因為dict是可變的。
請記住,這只是模擬指針行為,并不直接映射到C或C ++中的真指針。也就是說,這些操作比在C或C ++中更昂貴。
使用Python對象
該dict選項是在Python中模擬指針的好方法,但有時記住您使用的密鑰名稱會很繁瑣。如果您在應(yīng)用程序的各個部分使用字典,則尤其如此。這是自定義Python類可以真正幫助的地方。
要構(gòu)建最后一個示例,假設(shè)您要跟蹤應(yīng)用程序中的指標。創(chuàng)建一個類是抽象討厭細節(jié)的好方法:
class Metrics (object ): def __init __ (self ): self 。_metrics = { “func_calls” : 0 , “cat_pictures_served” : 0 , }
此代碼定義了一個Metrics類。該類仍然使用a dict來保存實際數(shù)據(jù),該數(shù)據(jù)位于_metrics成員變量中。這將為您提供所需的可變性?,F(xiàn)在您只需要能夠訪問這些值。一個很好的方法是使用屬性:
class Metrics(object): # ... @property def func_calls(self): return self._metrics["func_calls"] @property def cat_pictures_served(self): return self._metrics["cat_pictures_served"]
這段代碼利用了@property。如果您不熟悉裝飾器,可以在Python裝飾器上查看這個Primer。@property這里的裝飾器允許您訪問func_calls,cat_pictures_served就像它們是屬性一樣:
>>> metrics = Metrics() >>> metrics.func_calls 0 >>> metrics.cat_pictures_served 0
您可以將這些名稱作為屬性訪問這一事實意味著您抽象出這些值在a中的事實dict。您還可以更明確地了解屬性的名稱。當(dāng)然,您需要能夠增加這些值:
class Metrics(object): # ... def inc_func_calls(self): self._metrics["func_calls"] += 1 def inc_cat_pics(self): self._metrics["cat_pictures_served"] += 1
這里再介紹兩種新方法:
inc_func_calls() inc_cat_pics()
這些方法會修改指標中的值dict。您現(xiàn)在有一個類可以修改,就像您正在修改指針一樣:
>>> metrics = Metrics() >>> metrics.inc_func_calls() >>> metrics.inc_func_calls() >>> metrics.func_calls 2
在這里,您可以在應(yīng)用程序中的各個位置訪問func_calls和調(diào)用inc_func_calls(),并在Python中模擬指針。當(dāng)您需要在應(yīng)用程序的各個部分中頻繁使用和更新指標時,這非常有用。
注意:特別是在這個類中,make inc_func_calls()和inc_cat_pics()explicit而不是使用@property.setter阻止用戶將這些值設(shè)置為任意int或無效的值,如dict。
class Metrics(object): def __init__(self): self._metrics = { "func_calls": 0, "cat_pictures_served": 0, } @property def func_calls(self): return self._metrics["func_calls"] @property def cat_pictures_served(self): return self._metrics["cat_pictures_served"] def inc_func_calls(self): self._metrics["func_calls"] += 1 def inc_cat_pics(self): self._metrics["cat_pictures_served"] += 1
關(guān)于怎么在Python中模擬實現(xiàn)指針問題的解答就分享到這里了,希望以上內(nèi)容可以對大家有一定的幫助,如果你還有很多疑惑沒有解開,可以關(guān)注億速云行業(yè)資訊頻道了解更多相關(guān)知識。
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。