| 導航:起始頁 > Dive Into Python > 自省的威力 > 全部放在一起 | << >> | ||||
深入 Python :Dive Into Python 中文版Python 從新手到專家 [Dip_5.4b_CPyUG_Release] |
|||||
最后一行代碼是唯一還沒有解釋過的,它完成全部的工作。但是現在工作已經簡單了,因為所需要的每件事都已經按照需求建立好了。所有的多米諾骨牌已經就位,到了將它們推倒的時候了。
下面是 apihelper.py 的關鍵
print "\n".join(["%s %s" %
(method.ljust(spacing),
processFunc(str(getattr(object, method).__doc__)))
for method in methodList])注意這是一條命令,被分隔成了多行,但是并沒有使用續行符 (\)。還記得我說過一些表達式可以分割成多行而不需要使用反斜線嗎?列表解析就是這些表達式之一,因為整個表達式包括在方括號里。
現在,讓我們從后向前分析。
for method in methodList
告訴我們這是一個列表解析。如你所知 methodList 是 object 中所有你關心的方法的一個列表。所以你正在使用 method 遍歷列表。
>>> import odbchelper >>> object = odbchelper>>> method = 'buildConnectionString'
>>> getattr(object, method)
<function buildConnectionString at 010D6D74> >>> print getattr(object, method).__doc__
Build a connection string from a dictionary of parameters. Returns string.
| 在 info 函數中,object 是要得到幫助的對象,作為一個參數傳入。 | |
| 在你遍歷 methodList 時,method 是當前方法的名稱。 | |
| 通過 getattr 函數,你可以得到 object 模塊中 method 函數的引用。 | |
| 現在,很容易就可以打印出方法的 doc string 。 |
接下來令人困惑的是 doc string 周圍 str 的使用。你可能記得,str 是一個內置函數,它可以強制將數據轉化為字符串。但是一個 doc string 應該總是一個字符串,為什么還要費事地使用 str 函數呢?答案就是:不是每個函數都有 doc string ,如果沒有,這個 __doc__ 屬性為 None。
>>> >>> def foo(): print 2 >>> >>> foo() 2 >>> >>> foo.__doc__>>> foo.__doc__ == None
True >>> str(foo.__doc__)
'None'
| 在 SQL 中,你必須使用 IS NULL 代替 = NULL 進行 null 值比較。在 Python,你可以使用 == None 或者 is None 進行比較,但是 is None 更快。 | |
現在你確保有了一個字符串,可以把這個字符串傳給 processFunc,這個函數已經定義是一個既可以壓縮空白也可以不壓縮空白的函數。現在你看出來為什么使用 str 將 None 轉化為一個字符串很重要了。processFunc 假設接收到一個字符串參數然后調用 split 方法,如果你傳入 None ,將導致程序崩潰,因為 None 沒有 split 方法。
再往回走一步,你再一次使用了字符串格式化來連接 processFunc 的返回值 和 method 的 ljust 方法的返回值。ljust 是一個你之前沒有見過的新字符串方法。
>>> s = 'buildConnectionString' >>> s.ljust(30)'buildConnectionString ' >>> s.ljust(20)
'buildConnectionString'
幾乎已經完成了。有了 ljust 方法填充過的方法名稱和來自調用 processFunc 方法得到的 doc string (可能壓縮過),你就可以將兩者連接起來并得到單個字符串。因為對 methodList 進行了映射,最終你將獲得一個字符串列表。利用 "\n" 的 join 函數,將這個列表連接為單個字符串,列表中每個元素獨占一行,接著打印出結果。
上述就是最后一個令人困惑的地方了。但是現在你應該已經理解這段代碼了。
print "\n".join(["%s %s" %
(method.ljust(spacing),
processFunc(str(getattr(object, method).__doc__)))
for method in methodList])<< 使用 lambda 函數 |
| 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | |
小結 >> |