可愛的豆子——使用Beans思想讓Python代碼更易維護

我曾經(jīng)是一個對Java非常反感的人诱渤,因為Java的語法非常啰嗦蚌铜。而用慣了動態(tài)類型的Python再使用靜態(tài)類型的Java就會覺得多出了很多的工作量。

因為工作的關(guān)系饺谬,我開始使用Java來做項目捂刺。在這個過程中,我發(fā)現(xiàn)Java在某些方面確實和Python不一樣。

有一句話說的好:

語言決定了世界觀族展。

當我Java用的越來越多的時候森缠,我漸漸發(fā)現(xiàn)我不是那么討厭它了。

今天我要講的仪缸,是我從Java里面學到的贵涵,一個被稱為JavaBeans的東西。

In computing based on the Java Platform, JavaBeans are classes that encapsulate many objects into a single object (the bean). They are serializable, have a zero-argument constructor, and allow access to properties using getter and setter methods.

一句話概括起來: 當一些信息需要使用類似于字典套字典套列表這種很深的結(jié)構(gòu)來儲存的時候恰画,請改用類來儲存宾茂。

在Python里面,我以前會寫這樣的代碼:

person_list = [{
        'name': 'kingname',
        'age': 23,
        'sex': 'male'
        'detail': {
                    'address': 'xxx',
                    'work': 'engineer',
                    'salary': 100000
            }
},
{
        'name': 'xiaoming',
        'age': 65,
        'sex': 'male'
        'detail': {
                    'address': 'yyy',
                    'work': 'pm',
                    'salary': 0.5
            }
}]

由于Python動態(tài)類型的特點拴还,字典里面的value經(jīng)常是包含了各種類型刻炒,有時候,字典里面包含了字典自沧,里面的字典里面還有列表,這個內(nèi)部字典里面的列表里面又包含了字典……

當我剛剛開始寫Java代碼的時候树瞭,也會保留了這個壞習慣拇厢,于是我定義的一個變量類似于這樣:

public Map<String, List<Map<String, Map<String, Object>>>> info = .....

并且由于Java是靜態(tài)類型語言,有時候Map里面的Value類型還不一致晒喷,需要使用Object來代替孝偎,等要使用的時候再做類型轉(zhuǎn)換。

對于這樣的寫法凉敲,真可謂是寫代碼一時爽衣盾,調(diào)試代碼火葬場。我過幾天讀自己的代碼爷抓,自己都不知道這個字典里面有哪些內(nèi)容势决,也不知道它們有哪些類型,必須到定義的地方去看蓝撇。

我的Mentor看了我的Java代碼以后果复,讓我去用一下JavaBeans,于是我的世界瞬間就簡潔多了渤昌。后來我將JavaBeans的思想用到Python中虽抄,果然Python代碼也變得好看多了。

使用上面person_list這個復雜的結(jié)構(gòu)為例独柑,我用JavaBeans的思想迈窟,在Python里面重構(gòu)它:

class Person(object):
    def __init__(self, name='', age=0, sex='', detail=None):
        self._name = name
        self._age = age
        self._sex = sex
        self._detail = detail
    
    @property
    def name(self):
        return self._name
    
    @name.setter
    def name(self, new_name):
        self._name = new_name
    
    @property
    def age(self):
        return self._age
    
    @age.setter
    def age(self, new_age):
        self._age = new_age
    
    @property
    def sex(self):
        return self._sex
    
    @sex.setter
    def sex(self, new_sex):
        self._sex = new_sex
    
    @property
    def detail(self):
        return self._detail
    
    @detail.setter
    def detail(self, new_detail):
        self._detail = new_detail
class Detail(object):
    def __init__(self, address='', work='', salary=0):
        self._address = address
        self._work = work
        self._salary = salary
    
    @property
    def address(self):
        return self._address
    
    @address.setter
    def address(self, new_address):
        self._address = new_address
    
    @property
    def work(self):
        return self._work
    
    @work.setter
    def work(self, new_work):
        self._work = new_work
    
    @property
    def salary(self):
        return self._salary
    
    @salary.setter
    def salary(self, new_salary):
        self._salary = new_salary

從這里可以看到,我把字典變成了類忌栅。于是车酣,當我想保存我自己的信息和小明的時候,我就可以這樣寫:

detail_kingname = Detail(address='xxx', work='engineer', salary=10000),
kingname = Person(name='kingname', age=23, sex='male', detail=detail_kingname)

detail_xiaoming = Detail(address='yyy', work='pm', salary=0.5),
xiaoming = Person(name='xiaoming', age=65, sex='male', detail=detail_xiaoming)

person_list = [kingname, xiaoming]

這樣寫,雖然說代碼量確實翻了不止一倍骇径,但是當我們后期維護的時候或者遇到問題來調(diào)試代碼躯肌,我們就能發(fā)現(xiàn)這樣寫的好處。

舉一個很簡單的例子破衔,在寫了代碼一年以后清女,我已經(jīng)對這段代碼沒有多少印象了,現(xiàn)在我得到了變量person_list, 我想查看每個人的工資晰筛。首先嫡丙,由于PersonDetail這兩個類是已經(jīng)定義好的,分別放在Person.pyDetail.py兩個文件中读第,于是我點開它們曙博,就知道,原來工資是保存在Detail這個類中的怜瞒,關(guān)鍵詞是salary, 而Detail又是保存在Person中的父泳,關(guān)鍵詞是detail

所以要查看每個人的工資吴汪,我可以這樣寫:

for person in person_list:
    detail = person.detail
    salary = detail.salary
    print(salary)

但是如果我使用的是最上面字典的那種方式惠窄,那么情況就沒有這么簡單了。因為我不知道工資是在這個字典的什么地方漾橙。于是我首先要找到person_list是在哪里初始化的杆融,然后看它里面有什么。在這個例子中霜运,我是一次性把整個列表字典初始化完成的脾歇,直接找到列表初始化的地方就知道,原來這個person_list下面有很多個字典淘捡,字典有一個key 叫detail,這個detail的value本身又是一個字典藕各,它下面的keysalary保存了工資的信息。這似乎還比較方便焦除。但是如果字典里面的信息不是一次性初始化完成的呢座韵?萬一detail這一個key是后面再加的呢?于是又要去找detail初始化的地方……

第二個好處踢京,使用Beans的時候誉碴,每個關(guān)鍵字是定義好的,salary就只能叫做salary瓣距,如果寫成了salarv, 集成開發(fā)環(huán)境會立刻告訴你黔帕,Detail沒有salarv這個屬性。但是如果使用字典的方式蹈丸,我在給字典賦值的時候成黄,一不小心:

detail['salarv'] = 0.5

由于這里的salarv是字符串呐芥,所以集成開發(fā)環(huán)境是不會報錯的,只有等你運行的時候,嘗試讀取detail['salary']里面的值奋岁,Python會告訴你:

Traceback (most recent call last):
  File "xxx.py", line 1, in <module>
KeyError: 'salary'

總結(jié)

將JavaBeans的思想用在Python中思瘟,避免字典套字典這種深層嵌套的情況,對于一些需要反復使用的字典闻伶,使用類來表示滨攻。這樣做,別人讀代碼的時候會更加的容易蓝翰,自己開發(fā)的時候光绕,也會避免出現(xiàn)問題。

本文首發(fā)地址: http://kingname.info/2016/06/19/bean-in-python/ 轉(zhuǎn)載請注明出處畜份。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末诞帐,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子爆雹,更是在濱河造成了極大的恐慌停蕉,老刑警劉巖,帶你破解...
    沈念sama閱讀 218,607評論 6 507
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件钙态,死亡現(xiàn)場離奇詭異谷徙,居然都是意外死亡,警方通過查閱死者的電腦和手機驯绎,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,239評論 3 395
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來谋旦,“玉大人剩失,你說我怎么就攤上這事〔嶙牛” “怎么了拴孤?”我有些...
    開封第一講書人閱讀 164,960評論 0 355
  • 文/不壞的土叔 我叫張陵,是天一觀的道長甲捏。 經(jīng)常有香客問我演熟,道長,這世上最難降的妖魔是什么司顿? 我笑而不...
    開封第一講書人閱讀 58,750評論 1 294
  • 正文 為了忘掉前任芒粹,我火速辦了婚禮,結(jié)果婚禮上大溜,老公的妹妹穿的比我還像新娘化漆。我一直安慰自己,他們只是感情好钦奋,可當我...
    茶點故事閱讀 67,764評論 6 392
  • 文/花漫 我一把揭開白布座云。 她就那樣靜靜地躺著疙赠,像睡著了一般。 火紅的嫁衣襯著肌膚如雪朦拖。 梳的紋絲不亂的頭發(fā)上圃阳,一...
    開封第一講書人閱讀 51,604評論 1 305
  • 那天,我揣著相機與錄音璧帝,去河邊找鬼捍岳。 笑死,一個胖子當著我的面吹牛裸弦,可吹牛的內(nèi)容都是我干的祟同。 我是一名探鬼主播,決...
    沈念sama閱讀 40,347評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼理疙,長吁一口氣:“原來是場噩夢啊……” “哼晕城!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起窖贤,我...
    開封第一講書人閱讀 39,253評論 0 276
  • 序言:老撾萬榮一對情侶失蹤砖顷,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后赃梧,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體滤蝠,經(jīng)...
    沈念sama閱讀 45,702評論 1 315
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,893評論 3 336
  • 正文 我和宋清朗相戀三年授嘀,在試婚紗的時候發(fā)現(xiàn)自己被綠了物咳。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 40,015評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡蹄皱,死狀恐怖览闰,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情巷折,我是刑警寧澤压鉴,帶...
    沈念sama閱讀 35,734評論 5 346
  • 正文 年R本政府宣布,位于F島的核電站锻拘,受9級特大地震影響油吭,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜署拟,卻給世界環(huán)境...
    茶點故事閱讀 41,352評論 3 330
  • 文/蒙蒙 一婉宰、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧推穷,春花似錦芍阎、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,934評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽轮听。三九已至,卻和暖如春岭佳,著一層夾襖步出監(jiān)牢的瞬間血巍,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,052評論 1 270
  • 我被黑心中介騙來泰國打工珊随, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留述寡,地道東北人。 一個月前我還...
    沈念sama閱讀 48,216評論 3 371
  • 正文 我出身青樓叶洞,卻偏偏與公主長得像鲫凶,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子衩辟,可洞房花燭夜當晚...
    茶點故事閱讀 44,969評論 2 355

推薦閱讀更多精彩內(nèi)容