Python 實用技巧

1. 和時間有關的函數和用法html

  1. 導入 time 模塊python

    import timec++

  2. 設置時間格式git

    TIMEFORMAT = "%Y-%m-%d %H:%M:%S"程序員

  3. time.time() 用於取當前時間,爲一個小數,表明從 epoch: 1970 年 1 月 1 日 00:00:00 開始到當前的秒數。github

    >>> time.time()web

    1180759620.859正則表達式

  4. time.localtime() 用於返回咱們熟悉的用 tuple 存儲的時間數據庫

    >>> time.localtime()express

    (2007, 6, 2, 12, 47, 7, 5, 153, 0)

  5. time.strftime() 用於按照咱們以前所定義的時間格式來返回時間

    >>> time.strftime( TIMEFORMAT, time.localtime() )

     ‘2007-06-02 12:54:31′

  6. 表示時間的tuple數組結構

索引(Index) 屬性(Attribute) 值(Values)
0 tm_year(年) 好比2011
1 tm_mon(月) 1 - 12
2 tm_mday(日) 1 - 31
3 tm_hour(時) 0 - 23
4 tm_min(分) 0 - 59
5 tm_sec(秒) 0 - 61
6 tm_wday(weekday) 0 - 6(0表示週日)
7 tm_yday(一年中的第幾天) 1 - 366
8 tm_isdst(是不是夏令時) 默認爲-1

  7. time.mktime(time.localtime())

    使用mktime函數,傳入tuple數組,能夠返回對應的時間戳。

2. Python 讀寫文件

  1. 讀文件

    input = open('data', 'r')

    record = input.readline()

    input.close()

    使用 input.read() 能夠將文件內容讀做一個大字符串進行返回

  2. 寫文件,'w' 參數表明將原有文件清空後再寫入,'a' 參數表示向文件追加

    output = open('data', 'w')

    output.write("test")

    output.close()

3. Python 續行符 '\'

  1. 第一種是直接用回車,可是不是很安全。

  2. 第二種是在當前行的尾部加上 '\' 符,在下一行繼續輸入,此時後續的行能夠以任何方式縮進,不用遵照python的嚴格縮進規則。通常在小括號、中括號、大括號裏定義的內容不須要用'\'分割,直接回車便可。  

4. 使用 Python 命令執行文件時的參數傳遞

  python 命令後的內容共同組成參數列表實現參數傳遞,能夠經過 sys 模塊的 argv 變量訪問到。

  例如: python kfk_setter.py video-meta video2feeds -1

      print sys.argv

  結果:['kfk_setter.py', 'video-meta', 'video2feeds', '-1'] 參數是以字符串的形式傳遞

5. 字符串鏈接的三種方式

  1. 直接經過加號(+)操做符鏈接 例如:website = 'python' + 'tab' + '.com'

    因爲python中字符串屬於不可變的對象,所以每次執行一個+操做就會生成一個新的字符串,所以連續相加的字符串不少時效率較低。

  2. join 方法

    listStr = ['python', 'tab', '.com']
    website = ''.join(listStr)

    對多個字符進行鏈接時效率高,只會有一次內存的申請。並且若是是對list的字符進行鏈接的時候,這種方法必須是首選。

  3. 字符串格式化

    website = '%s%s%s' % ('python', 'tab', '.com')

    這種方式很是經常使用

6. Python中的eval()、exec()及其相關函數

  1. eval() 與 exec() 函數的形式和功能相似,都是經過傳遞全局變量和局部變量參數來實現字符串或者code對象的執行。區別在於,eval() 是用來計算指定表達式的值,也就是說它執行的python語句只能是單個表達式(不支持任意形式的賦值運算),而不是是複雜的邏輯,eval() 函數有返回值;exec() 函數能夠動態運行代碼段,exec() 函數的返回值永遠爲 None。

  2. eval() 函數

    1. 函數形式 eval(expression, globals = None, locals = None)

      其中:expression 爲表達式參數,能夠爲字符串,也能夠是由 compile() 函數建立的 code 對象實例。若是它是一個字符串,它會被看成一個(使用globals和locals參數做爲全局和本地命名空間的)Python表達式進行分析和解釋。

         globals 爲可選參數,表示全局變量空間(存放全局變量),必須是一個字典對象。

         locals 表示局部變量空間(存放局部變量),若是被提供,能夠是任何映射對象。若是該參數被忽略,那麼它將會取與globals相同的值。

         上述兩個參數能夠本身賦予新的變量名和值,也能夠用當前已經定義變量進行映射,對後者的更改會產生實際效果(在 exec() 函數中才能進行更改)

         若是 globals 和 locals 參數都被忽略,那麼它們將取 eval() 函數被調用環境下的全局變量空間和局部變量空間。

     返回值:若是 expression 是一個 code 對象,且建立該 code 對象時,compile() 函數的 mode 參數爲 'exec',那麼返回值爲 None;不然若是 expression 語句是一個輸出語句,如 print,那麼返回爲 None;其餘狀況下 expression 表達式的結果就是 eval() 函數的返回值。

    2. 用法示例

      self.filter_exp = data.get('ucp_trespassing_field', {}).get('surface_type', '') != 'ARTICLE_SURFACE'

      eval('#coding=%s\n%s' % ('utf8', self.filter_exp), {}, local_vars) 在 expression 表達式中聲明瞭編碼類型和具體表達式的內容經過 self.filter_exp 變量(邏輯表達式)進行傳遞,local_vars 爲字典定義的局部空間

  3. exec() 函數

    1. exec(object [, globals [, locals ]])

      參數說明:obeject 爲須要執行的 Python 代碼,能夠是字符串或者code對象;後面參數同上

      返回值:exec() 函數的返回值始終爲 None

    2. 用法示例

mapped_data = {}
mapped_data['url'] = 'http://baijiahao.baidu.com/u?app_id=%s' % data['id']
mapped_data['status'] = 'publish' if data['status'] == 'pass' else 'unpublish'

mapped_data_dict['data'] = mapped_data
mapping_code_conf

      self.mapping_code = compile(file(mapping_code_conf).read(), '', 'exec')

      exec(self.mapping_code, {}, {'data': data, 'mapped_data_dict': mapped_data_dict, 'json':json, 'mongo_reader': self.mongo_reader, 'convert_time': self._convert_time, 'cgi': cgi, 'time': time, 'hashlib': hashlib, 'parse_html': self.parse_html, 'random': random, 're': re})

      須要 exec 執行的代碼寫在 mapping_code_conf 文件中(不帶有格式),而後使用 compile() 函數進行解析生成 self.mapping_code 對象,最後使用 exec() 函數調用,並賦給局部變量

  4. global() 函數

    返回一個表示當前全局標識符表的字典。這永遠是當前模塊的字典(在一個函數或方法內部,這是指定義該函數或方法的模塊,而不是調用該函數或方法的模塊)

  5. local() 函數

    更新並返回一個表示當前局部標識符表的字典。自由變量在函數內部被調用時,會被locals()函數返回;自由變量在類累不被調用時,不會被locals()函數返回。

    總結:

      1. globals()函數以字典的形式返回的定義該函數的模塊內的全局做用域下的全部標識符(變量、常量等)

      2. locals()函數以字典的形式返回當前函數內的局域做用域下的全部標識符

      3. 若是直接在模塊中調用globals()和locals()函數,它們的返回值是相同的

  6. compile() 函數

    compile(source, filename, mode[, flags[, dont_inherit]])

    將源碼編譯爲 code 對象或者 AST 對象,code對象可以經過exec()函數來執行或者經過eval()函數進行計算求值。

    參數說明:

      1. source:字符串或AST(Abstract Syntax Trees)對象,表示須要進行編譯的Python代碼

      2. filename:指定須要編譯的代碼文件名稱,若是不是從文件讀取代碼則傳遞一些可辨認的值(一般是用'<string>')

      3. mode:用於標識必須當作那類代碼來編譯;若是source是由一個代碼語句序列組成,則指定mode='exec';若是source是由單個表達式組成,則指定mode='eval';若是source是由一個單獨的交互式語句組成,則指定mode='single'。

    若是是用 file(filename).read() 做爲source參數,從代碼文件中讀取代碼,filename 參數爲 '' 便可。

  更多示例能夠查看:http://www.cnblogs.com/yyds/p/6276746.html?utm_source=itdadao&utm_medium=referral

7. 在 Python 函數內若是須要對函數外的不可變對象進行更改,須要在函數內用 global 關鍵字聲明某個變量是函數外的變量。

  在函數傳遞過程當中是混合傳遞,若是參數是可變對象,那麼就是地址傳遞;若是參數是不可變對象,那麼就是值傳遞。

  Python 中的可變對象包括列表和字典,不可變對象包括數值、字符串和元祖。

8. 日誌記錄和 logging 模塊使用

  logger 爲日誌對象,是 logging 模塊中最基礎的對象,用 logging.getLogger(name) 方法進行初始化,name 能夠不填。一般 logger 的名字咱們對應模塊名,如聊天模塊、數據庫模塊、驗證模塊等。

  日誌對象須要設置日誌等級,日誌對象只有調用比當前日誌等級高的信息輸出函數纔會輸出。日誌等級關係以下:從上到下,等級依次增長。

    1. DEBUG:debug 級輸出

    2. INFO:info 級輸出,重要信息

    3. WARNING:warning 級輸出,警告信息

    4. ERROR:error 級輸出,錯誤信息

    5. CRITICAL:critical 級輸出,嚴重錯誤信息

  初始化日誌對象模版:

import logging
from logging.handlers import RotatingFileHandler
log = logging.getLogger(name)
#初始化日誌對象,名字能夠任意,也可爲空
log.setLevel(logging.INFO)
#設置日誌等級,決定其能夠調用的日誌輸出函數,只能調用比等級高的
format = logging.Formatter("%(asctime)s - %(levelname)s - %(message)s")
#日誌輸出格式化對象,表示時間-日誌等級-日誌內容
fh = RotatingFileHandler(logfile, maxBytes=(1048576*500), backupCount=7)
#要進行日誌輸出必須要有一個handler,這裏使用RotatingFileHandler,參數logfile爲指定日誌文件地址
fh.setFormatter(format)
log.addHandler(fh)

log.info("info msg")

   1. Handler

    用來指定日誌內容輸出的定向,包括 StreamHandler (標準輸出)、FileHandler (日誌文件輸出,默認追加)、RotatingFileHandler(指定日誌文件的路徑和名字,設置每一個文件的最大字節數和文件個數,自動更新最新的日誌到日誌文件中,保存指定數量的過往日誌)。

    一個 logger 對象能夠指定多個 Handler,用於將日誌定向到不一樣的輸出。同時能夠從每一個 Handler 指定日誌級別,用於分級別輸出。

    日誌輸出格式也由 Handler 設置。有不少表明特定意義的字段,網上自查。

    1. StreamHandler 的設置

      import sys

      fh = logging.StreamHandler(sys.stderr)

9. 字典中 key/value 值中出現的 u'string' 表示該字符串已是用 Unicode 編碼表示的。

10. Json: JavaScript Object Notation (JS 對象標記)

  1. Json 是一種輕量級的數據交換格式

    它的本質是字符串,使用 Json 格式生成的字符串易於人閱讀和編寫,並且易於機器解析和生成。這是一種徹底獨立於編程語言的數據交換格式,並且因爲 JavaScipt 中,任何數據都是對象,所以 Json 表示的值能夠是數值、字符串、邏輯值、數組(用[]方括號包圍)、對象(用{}花括號包圍)。

    Json 的對象是包含在{}內的,能夠由多個鍵/值對組成,在 Json 中,字符串都是由雙引號""包圍起來的,數字就直接是數字的形式。

    Json 的數組也能夠包含多個對象。

  2. Json 的特質

    1. Json 是純文本

    2. Json 具備自我描述性(人類可讀)

    3. Json 具備層次結構(值中存在值)

  3. 相比 XML 的不一樣之處

    1. 沒有結束標籤

    2. 更簡潔,讀寫速度更快,能夠用來提高網絡傳輸速度

    3. 不使用保留字

  4. 在 Python 中使用 Json

import json

test = {'a':123, 'b': 'dag'}
a = json.dumps(test)
#使用 json.dumps() 函數生成對象對應的 json 字符串
b = json.loads(a)
#使用 json.loads() 函數將 json 字符串進行解析,恢復爲 dict 類型對象
View Code

    注意在 json 中全部的字符串都是由雙引號("")包圍,與 python 中字典對象中的字符串由單引號('')包圍不一樣。 

  5. Json是採用Unicode編碼,不方便顯示的字符(如中文漢字)就直接用Unicode編碼進行存儲

11. repr() 與 str() 函數的區別

  repr() 將 python 對象轉化爲字符串是給機器看的,支持各類數據類型,用 eval() 函數能夠從新解析出原數據。

  str() 轉換爲字符串是方便人閱讀的,不具備解析爲原數據的功能。

12. handler

  Handler主要用於異步消息的處理:當發出一個消息以後,首先進入一個消息隊列,發送消息的函數即刻返回,而另一個部分在消息隊列中逐一將消息取出,而後對消息進行處理,也就是發送消息和接收消息不是同步的處理。 這種機制一般用來處理相對耗時比較長的操做。

13. 函數中的 *args,**args 參數

  這二者爲 Python 函數中的可變參數,能夠選擇性傳入,*args 表示任意多個無名參數,是一個 tuple;**args 表示關鍵字參數,是一個 dict。若是同時使用 *args 和 **args 參數時,必須 *args 參數在 **args 參數前面。

14. 字符串編碼問題

  經常使用的字符串編碼包括:utf-8,gb2312,cp936,gbk等。

  在python中使用unicode編碼做爲字符串的內部編碼類型,所以若是須要實現上述編碼類型字符串之間的相互轉換,須要首先使用decode進行解碼,將本來編碼的字符串轉換爲unicode編碼,而後再使用encode函數進行編碼。簡單來講,decode()是將其餘類型的編碼轉換爲unicode編碼,encode()將unicode編碼轉換爲其餘類型編碼。

u = '中文' #指定字符串類型對象u
str = u.encode('gb2312') #以gb2312編碼對u進行編碼,得到bytes類型對象str
u1 = str.decode('gb2312')#以gb2312編碼對字符串str進行解碼,得到字符串類型對象u1
u2 = str.decode('utf-8')#若是以utf-8的編碼對str進行解碼獲得的結果,將沒法還原原來的字符串內容

  另外,文件中的字符串默認編碼類型與文件的編碼類型一致:

  如 str = '中文',若是是在utf-8編碼的文件中初始化,該字符串就是utf-8編碼;若是是在gb2312編碼的文件中,那該字符串就是gb2312編碼。這種狀況下須要先進行解碼,再進行其餘類型的編碼。若是顯示聲明編碼類型 str = u'中文',則該字符串的編碼類型就被指定爲unicode編碼,而與文件的編碼形式無關。

15. xrange() 與 range() 的區別

  xrange() 與 range() 的用法和做用相同,區別在於實現的過程,range() 會一次生成完整的列表,而 xrange() 是返回一個生成器。若是須要生成一個很大的數字列表時,xrange() 的性能更好,由於不用一開始就開闢很大的內存空間。

16. sys 模塊

  1. 標準輸入流、標準輸出流、標準錯誤流

    stdin,stdout,stderr 是內建在每一個 UNIX 系統中的管道,當其被調用時信息自動進入對應的管道。

    sys.stdout 和 sys.stderr 能夠看做是文件對象,調用其 write() 函數能夠向標準輸出流和標準錯誤流打印信息(默認爲屏幕),也能夠用文件對象對其從新賦值,以實現輸出重定向。

import sys

sys.stdout.write('hope')    #向屏幕打印 'hope'
save = sys.stdout    #保存原有的輸出對象
file = open('out.txt', 'w')    #打開一個文件對象
sys.stdout = file    #對其進行賦值
sys.stdout.write('test')    #向文件中輸出 'test'

    實際上 print 語句就是在須要輸出的內容後加一個換行符,再調用 sys.stdout.write() 函數進行輸出。

17. list 列表

  1. del 語句刪除列表中的元素

    del list[0]  #刪除列表中的第一個元素

    del list[:]  #刪除列表中全部元素

    list.remove(obj)  #移除列表中某個值的第一個匹配項

  2. list.extend(seq) 在列表的尾部一次性追加參數列表 seq 的多個值

  3. enumerate() 函數能夠將一個可遍歷的數據對象(如列表、元組或字符串)組合爲一個索引序列,同時列出數據和數據下標,通常用在 for 循環當中。

    for i, j in enumerate(list)

      print i, j  #能夠同時輸出元素在列表中的索引和元素自己

18. Socket 編程

  1. TCP/UDP 協議

    TCP/IP 協議是一個協議簇,裏面包含應用層、傳輸層、網絡層、網絡訪問層等多種協議,因爲 TCP 和 IP 協議是其中比較重要的,所以用此命名。

    1. TCP(Transmission Control Protocol)

      是面向鏈接的,在收發數據前雙方須要創建可靠通訊,通過「三次握手」。對應的是可靠性要求高的應用,支持的應用層協議有 Telnet(遠程登陸)協議、FTP、SMTP(簡單消息傳輸協議)。

    2. UDP(User Datagram Protocol)

      是面向無鏈接的,在傳輸數據以前源端和終端不須要創建鏈接,在接收端,UDP 把每一個消息放在消息隊列中,應用程序每次從消息中讀一個消息段。UDP 是盡最大努力交付的,不保證可靠交付,面向報文傳輸。其支持的應用層協議有:NFS(網絡文件系統)、SNMP(簡單網絡管理協議)、DNS(域名系統)、TFTP(通用文件傳輸協議)。Ping 命令就使用了 UDP 協議。

  2. Socket 含義

    網絡上的兩個程序經過一個雙向的通訊鏈接實現數據的交換,這個鏈接的一端稱爲一個socket(插座、套接字)。
    創建網絡通訊鏈接至少要一對端口號(socket)。socket本質是編程接口(API),對TCP/IP的封裝,TCP/IP也要提供可供程序員作網絡開發所用的接口,這就是Socket編程接口;HTTP是轎車,提供了封裝或者顯示數據的具體形式;Socket是發動機,提供了網絡通訊的能力。
    Socket 與 端口的區別在於,端口只是 Socket 的一部分,爲了區分不一樣應用進程間的網絡通訊和鏈接,主要有3個參數:通訊的目的IP地址、使用的傳輸層協議(TCP 或 UDP)和使用的端口號。Socket的原意是「插座」。經過將這3個參數結合起來,與一個「插座」Socket綁定,應用層就能夠和傳輸層經過套接字接口,區分來自不一樣應用程序進程或網絡鏈接的通訊,實現數據傳輸的併發服務。
    一個端口只能被一個程序佔用,不能多個程序同時佔用一個端口,可是同一個程序的多個 Socket 能夠與同一個端口創建鏈接。
    在 LINUX 系統中,一切皆文件,對於文件採用打開、讀寫、關閉模式來操做。Socket 能夠看做是這種模式的一個實現,Socket 模塊是對服務器端和客戶端 Socket 進行打開、讀寫和關閉。兩個程序經過網絡進行交互就使用 Socket,Socket 進行兩件事情:創建鏈接、傳遞數據。
  3. Python socket 模塊
    1. 導入 socket 模塊
      import socket
    2. 初始化 socket
      sk = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
      函數原型爲 socket.socket([family[, type[, proto]]])
      第一個參數爲地址簇類型:
        socket.AF_INET  爲ipv4地址(默認)
        socket.AF_INET6  爲ipv6地址
        socket.AF_UNIX  只能用於單一的Unix系統進程間通訊
      第二個參數爲 Socket 類型:
         socket.SOCK_STREAM  流式socket ,  for  TCP (默認)
        socket.SOCK_DGRAM   數據報式socket ,  for  UDP
          socket.SOCK_RAW 原始套接字,普通的套接字沒法處理ICMP、IGMP等網絡報文,而SOCK_RAW能夠;其次,SOCK_RAW也能夠處理特殊的IPv4報文;此外,利用原始套接字,能夠經過IP_HDRINCL套接字選項由用戶構造IP頭。
        socket.SOCK_RDM 是一種可靠的UDP形式,即保證交付數據報但不保證順序。SOCK_RAM用來提供對原始協議的低級訪問,在須要執行某些特殊操做時使用,如發送ICMP報文。SOCK_RAM一般僅限於高級用戶或管理員運行的程序使用。
        socket.SOCK_SEQPACKET 可靠的連續數據包服務
      第三個參數爲協議類型:
        0  默認 與特定的地址家族相關的協議,若是是  0  ,則系統就會根據地址格式和套接類別,自動選擇一個合適的協議
    3. 與地址創建鏈接
      sk.connect(ip_port)
      其中ip_port爲一個元組,代表 Socket 須要鏈接的 ip 地址和端口號,例如:ip_port = ('13.243.23.21', 3004)
    4. 創建與 Socket 相連的文件對象
      sk_file = sk.makefile(mode = 'w')
    5. 經過文件對象傳輸數據
      sk_file.write("test")  與文件對象操做一致,就能夠實現向指定 ip_port 傳輸數據
    6. 關閉 Socket 對象
      sk.close()
    7. 設置發送超時,鏈接自動斷開
      socket.setdefaulttimeout(timeout)
19. Url 編碼
  1. 爲何要進行 Url 編碼
    按照標準,Url 只容許一部分 ASCII 碼字符(數字字母和部分字符),其餘的字符(如漢字,空格)是不符合標準的,因此若是 Url 中包含其餘字符,就須要進行 Url 編碼。
    URL 中傳參數的部分(query String),格式是:name1=value1&name2=value2&name3=value3
    假如你的 name 或者 value 值中有 & 或者 = 等符號,就固然會有問題,全部 Url 中的參數字符串須要先進行 Url 編碼,將特殊字符以及 & = 進行編碼後再與 Url 總體進行鏈接。 
    Url 編碼的方式是把須要編碼的字符轉化爲 %xx 的形式,一般 Url 編碼是基於 utf-8 的(與瀏覽器平臺有關)。
  2. urllib 模塊編程
    1. 導入 urllib 模塊
      import urllib
    2. Url 編碼
      urllib.quote('http://www.baidu.com')
      編碼後的結果爲:'http%3A//www.baidu.com'
    3. Url 解碼
      與 Url 編碼的做用相反,將 Url 編碼後的地址解碼爲原先的地址
      urllib.unquote('http%3A//www.baidu.com')
      解碼結果恢復爲:'http://www.baidu.com'
    urllib 模塊其餘函數參考: http://www.cnblogs.com/sysu-blackbear/p/3629420.html
20. 正則表達式
  1. 導入模塊
    import re
  2. 方法
    1. sub()
      使用re替換string中每個匹配的子串後返回替換後的字符串。

      格式:

        re.sub(pattern, repl, string, count)

  待完善,參考:http://www.cnblogs.com/tina-python/p/5508402.html

21. yield 語句生成器

  好比須要打印一個數列,能夠先經過函數生成完整的序列,而後使用 for 循環對序列的迭代進行打印。可是若是序列很大,會形成內存的大量佔用,此時若是使用 generator (生成器)進行迭代序列中的每個元素會優化不少。

  yield 語句就是將須要返回的數據(數據是什麼類型,就會按照什麼樣的類型進行循環迭代,能夠爲列表,也能夠爲元素)做爲生成器進行返回,方便代碼的其餘部分對該函數的返回內容進行迭代,迭代完該函數會自動從 yield 語句執行完成的地方繼續執行,保持本來的局部變量,好像並無被外部代碼迭代同樣。生成器函數執行時遇到 return 語句,會返回 StopIteration 錯誤。生成器自動包含 next() 函數返回迭代的下一個數。

  經過類也能夠定義 self.__iter__() 和 next() 函數造成生成器。

22. heapq 模塊

  上述模塊是用來申請堆內存的,生成小根堆的結構。能夠建立一個空列表做爲堆空間,也能夠經過 heapify() 函數將一個現存的列表轉換爲堆空間。

  1. heappush(heap, item)

    向堆空間中插入元素,heap 爲以前建立的列表名

  2. heappop(heap)

    出堆並返回最小的元素,可使用 heap[0] 來察看最小的元素(小根堆根結點上的值,若是值爲列表,那麼會優先按照第一個元素的大小比較排序)

  經過堆空間可以進行本地的緩存,實現輪詢機制。

23. 靜態方法、類方法、實例方法

  類中的靜態方法聲明前須要在前一行加上 @staticmethod 標識符,以表示下面的成員函數是靜態函數。靜態函數不須要傳遞和類有關的參數。

  類方法聲明前須要加上 @classmethod 標識符,類方法須要加隱藏參數 cls 表示該類。

  實例方法須要加隱藏參數 self 表示某個實例。

  三者的區別:

    1. 類方法和靜態方法皆能夠訪問類的靜態變量(類變量),但不能訪問實例變量。

    2. 類的實例能夠訪問類方法、靜態方法和實例方法,可是類只能訪問類方法和靜態方法,訪問實例方法須要顯式傳遞實例參數。類方法和靜態方法由多個實例和類共享。

24. sorted() 函數使用

  sorted(iterable[, cmp[, key[, reverse]]])

  iterable 爲可迭代對象,例如:

vocab = vectorizer.vocabulary_
#vocab爲一個字典,經過items()能夠返回由鍵值對元祖組成的列表,itemgetter()爲一個操做符函數,表示取調用其對象的特定元素
X_vocab = sorted(vocab.items(), key=itemgetter(1))

25. set() 集合操做

  Python 的集合由集合對象來實現,能夠用一個順序結構來進行初始化。

x = set('test')
#x爲set(['t', 'e', 's'])
x.add('l')
#在集合中添加一項
x.update('hope')
#在集合中添加多項
x.remove('t')
#在集合中移除元素

26. 轉義字符

Escape Sequence Meaning Notes
\newline Ignored  
\\ Backslash (\)  
\' Single quote (')  
\" Double quote (")  
\a ASCII Bell (BEL)  
\b ASCII Backspace (BS)  
\f ASCII Formfeed (FF)  
\n ASCII Linefeed (LF)  
\N{name} Character named name in the Unicode database (Unicode only)  
\r ASCII Carriage Return (CR)  
\t ASCII Horizontal Tab (TAB)  
\uxxxx Character with 16-bit hex value xxxx (Unicode only) (1)
\Uxxxxxxxx Character with 32-bit hex value xxxxxxxx (Unicode only) (2)
\v ASCII Vertical Tab (VT)  
\ooo Character with octal value ooo (3,5)
\xhh Character with hex value hh (4,5)

27. 內置函數 zip()

  內置函數接受一系列可迭代的對象做爲參數,將對象中對應的元素組成一個個元組的形式,而後返回這些元組組成的列表。zip(*a) 實現反過程,由元組列表返回對應的迭代對象序列。

a = [1, 2, 3]
b = [4, 5, 6]
c = [4, 5, 6, 7, 8]
zipped = zip(a, b)
#zipped 爲 [(1, 4), (2, 5), (3, 6)]
zip(a, c)
#結果爲 [(1, 4), (2, 5), (3, 6)]
zip(*zipped)
#進行解壓,結果爲 [(1, 2, 3), (4, 5, 6)]

28. 路徑及文件判斷

  1. os.path.exists(path)  判斷一個目錄是否存在

  2. os.makedirs(path)  多層建立目錄,若是上級目錄不存在會自動建立

  3. os.mkdir(path)  建立目錄

29. 將多維列表打平爲一維

from compiler.ast import flatten
flatten(a)

 30. cx_Freeze

  因爲 python 文件的執行必須依賴解釋器的存在,所以若是咱們須要在沒有解釋器的機器上執行 python 程序,就須要對本來的 python 文件進行打包,轉換爲 exe 可執行文件。

  打包命令爲:cxfreeze hello.py --target-dir dist  #dist爲打包後存放的目錄

  hello.py 是咱們要打包的模塊,注意只能一個模塊,即啓動模塊;全部 .py 文件都不能有中文字符,不然會出現編碼異常;發佈後,可執行文件執行路徑不能有中文(最好也不要有空格);啓動執行的文件中不要有下面這種判斷,不然可執行文件執行會沒有任何效果。 

  if __name__ == "__main__": 
    main()

  因此最好使用腳本去調用可執行文件。

31. Python 編碼

  1. 剛開始的時候使用的 ASCII 編碼,將每一個字符用一個字節表示。後面因爲各國語言的加入,造成了統一的編碼集 Unicode 編碼,最經常使用的是用兩個字節表示一個字符。可是這樣的編碼方式在網絡傳輸以及存儲上會使用大量的空間(尤爲是全是英文字符的狀況下,英文字符對應的 Unicode 編碼爲在本來的 ASCII 編碼前加一個全 0 字節),全部衍生出了 utf-8 可變長編碼,UTF-8編碼把一個Unicode字符根據不一樣的數字大小編碼成1-6個字節,經常使用的英文字母被編碼成1個字節,漢字一般是3個字節,只有很生僻的字符纔會被編碼成4-6個字節。

  搞清楚了ASCII、Unicode和UTF-8的關係,咱們就能夠總結一下如今計算機系統通用的字符編碼工做方式:

  在計算機內存中,統一使用Unicode編碼,當須要保存到硬盤或者須要傳輸的時候,就轉換爲UTF-8編碼。

  用記事本編輯的時候,從文件讀取的UTF-8字符被轉換爲Unicode字符到內存裏,編輯完成後,保存的時候再把Unicode轉換爲UTF-8保存到文件:  

rw-file-utf-8

  

 

 

 

 

 

 

 

 

  瀏覽網頁的時候,服務器會把動態生成的Unicode內容轉換爲UTF-8再傳輸到瀏覽器:

web-utf-8

  

 

 

 

 

 

 

 

 

  因此你看到不少網頁的源碼上會有相似<meta charset="UTF-8" />的信息,表示該網頁正是用的UTF-8編碼。

  2. 在 Python 中,u'\u674e\u535a' 表示 Unicode 編碼,'\xe6\x9d\x8e\xe5\x8d\x9a' 表示 utf-8 編碼。編碼之間的轉換用 encode() 函數實現,函數參數指定編碼類型,用於將字符串按照指定的編碼方式編碼,在編碼集沒法對原字符串中的某些字符編碼時會報錯;相對應的函數爲 decode(),用於將用某種類型編碼獲得的字符串用該種類型的編碼進行解碼獲得內存所使用的 Unicode 碼。

  3. json.dumps() 函數

    函數帶有默認參數 ensure_ascii = True, 會將全部的非 ASCII 碼字符轉義爲\uXXXX 序列,使得輸出的結果中只包含 ASCII 碼字符。若是 ensure_ascii 碼爲 False,表示原輸入中含有用 ASCII 碼沒法編碼的實例,因此不會轉義爲上述的這種形式,會按照 encoding 參數指定的編碼方式進行編碼,默認的方式是 'UTF-8' 編碼。

    好比 json.dumps('李博', encoding="utf-8", ensure_ascii=False) 編碼結果爲 '"\xe6\x9d\x8e\xe5\x8d\x9a"' 可以按照 UTF-8 編碼的方式進行打印。

32. 在 Python 中安裝 XGBoost 模塊

  1. 第一種方式:使用 anaconda 的安裝器

    conda install -c anaconda py-xgboost

  2. 第二種方式:按照 XGBoost 官網的介紹流程,編譯安裝適用於多種語言的 XGB 模塊。

    1. 因爲最新版本的 XGBoost 模塊依賴於支持 C++ 11 的編譯器,所以首先須要安裝高版本的 g++ 編譯器(g++-4.8 或更高)

      1. 首先在網上下載 gcc 的編譯器文件包 http://gcc.parentingamerica.com/releases/gcc-4.8.5/

      2. 解壓並建立同級目錄 gcc-build,進入上述目錄並執行:

# ../gcc-4.8.5/configure --prefix=/usr/local/gcc-4.8.5 --enable-threads=posix --disable-checking --disable-multilib --enable-languages=c,c++ --with-gmp=/usr/local/gmp-6.0.0/ --with-mpfr=/usr/local/mpfr-3.1.6/ --with-mpc=/usr/local/mpc-1.0.1/

       configure 配置會報錯:

configure: error: Building GCC requires GMP 4.2+, MPFR 2.4.0+ and MPC 0.8.0+.  
Try the --with-gmp, --with-mpfr and/or --with-mpc options to specify

        說明 gcc 的編譯須要一些依賴項 gmp,mpfr,mpc,m4。下載這些軟件包:

# wget -c http://ftp.gnu.org/gnu/m4/m4-latest.tar.xz
# wget -c http://www.mpfr.org/mpfr-current/mpfr-3.1.6.tar.gz
# wget -c ftp://ftp.gnu.org/gnu/mpc/mpc-1.0.1.tar.gz
# wget -c https://gmplib.org/download/gmp/gmp-6.0.0a.tar.xz

       xz 是一種壓縮格式,將 tar 打包後的軟件包進行進一步壓縮。處理這類文件須要首先使用 xz -d 命令將指定的文件解壓縮爲 .tar 文件,而後就可使用 tar 命令進行處理。

       解壓後分別新建同級文件夾 mkdir gcc-build, m4-bulid, gmp-bulid, mpfr-bulid, mpc-bulid, gmp-bulid,在對應的 build 文件夾裏執行 configure:

       軟件包之間存在依賴關係,因此須要按照順序編譯,依賴關係以下:      

        m4 -> gmp  

        mpfr -> gmp

        mpc -> gmpmpfr

        gcc -> gmp, mpfr, mpc

       分別編譯安裝:

#m4 ../m4-xxx/configure;    make;    make check;   make install
#gmp ../gmp-xxx/configure --prefix=/usr/local/gmp-xxx;    make;    make check;    make install
#mpfr ../mpfr-xxx/configure --prefix=/usr/local/mpfr-xxx --with-gmp=/usr/local/gmp-xxx;    make;    make check;    make install
#mpc  ../mpc-xxx/configure --prefix=/usr/local/mpc-xxx --with-gmp=/usr/local/gmp-xxx --with-mpfr=/usr/local/mpfr-xxx;    make;    make check;    make install

      3. 安裝完上述依賴軟件包以後須要添加其庫路徑,使 gcc 在編譯的過程當中可以訪問到這些庫,有兩種方式:

        1. 動態函數庫加載到內存中(高速緩存 cache),當軟件套件須要採用動態函數庫時,就不須要從新從硬盤中讀出,這樣就能夠提升動態函數庫的讀取速度。經過 ldconfig 命令和 /etc/ld.so.conf 文件來完成上述操做。

          1. 首先將須要加載到內存中的動態函數庫路徑寫入 /etc/ld.so.conf 文件中:

include ld.so.conf.d/*.conf    #這一列是自己存在的,咱們只須要在下面添加函數庫路徑便可
/usr/local/mpc-1.0.1/lib    
/usr/local/mpfr-3.1.6/lib
/usr/local/gmp-6.0.0/lib    #將咱們所須要的函數庫都加入高速緩存中

          2. 使用 ldconfig 命令將上述文件中記錄的動態函數庫讀入高速緩存中,這樣就能夠實現 gcc 編譯過程當中自動讀取上述函數庫。

        2. 將動態函數庫的路徑寫入 $LD_LIBRARY_PATH 環境變量中,而後在 gcc 的編譯命令加上 -LLDPATH 參數即可自動讀取上述環境變量指定的函數庫。

       實測方式一比較有效。

      4. 安裝上述命令從新配置後編譯 gcc

make

        若是報錯 configure: error: cannot compute suffix of object files: cannot compile。是由於以前安裝的依賴項沒有能被正確讀取致使的。

      5. 安裝 gcc

make install

      6. 修改 gcc g++ 的符號連接

# cd /usr/bin/
# ln -si /usr/local/gcc-4.8.5/bin/gcc gcc
# ln -si /usr/local/gcc-4.8.5/bin/g++ g++
# 上述使用的是相對路徑修改 /usr/bin/gcc 和 /usr/bin/g++ 的符號連接爲咱們剛編譯安裝的編譯器的連接,有時須要使用絕對路徑

        到此爲止 gcc-4.8.5 的安裝過程到此結束,編譯器的安裝涉及大量的依賴項,須要安裝順序一步步來,不能急躁,確保每一步的執行正確才能繼續往前,不然會找不到錯誤的源頭,只能進行簡單的重試,浪費大量時間。

    2. 安裝好支持 C++ 11 的編譯器,就能夠開始 XGBoost 的安裝。

      1. 下載並編譯支持各個語言的 XGB 模塊

git clone --recursive https://github.com/dmlc/xgboost
cd xgboost; make -j4

      2. 將對應 Python 的模塊安裝進模塊地址

cd python-package; sudo python setup.py install

        注意若是須要安裝進 anaconda 的軟件包地址,須要指定 anaconda 包自帶的 python 程序地址來執行 setup.py 文件,不然會默認使用以前安裝的其餘路徑的 python 程序。

       或者使用環境變量的方式也能夠正常導入 xgboost 模塊,以下:

export PYTHONPATH=~/xgboost/python-package

    3. 至此,XGBoost 模塊的安裝到此結束,這件事情給個人體會是安裝一個文件時,能夠先多調研調研不一樣的方法,看看哪一種最合適和簡單再去執行,不然容易選擇了複雜的方法。中途發現了簡單的方法,又不肯意放棄複雜方法的情況。總的來講,一步步解決問題。

33. 模塊與包的組織

  1. 任何模塊代碼的第一個字符串都被視爲這個模塊的文檔註釋,用__author__變量能夠將做者的名字寫進去。一個模塊能夠看做是一個文件,多個模塊組織成一個包(至關於一個目錄下有多個文件),此時目錄下必須存在__init__.py文件。當導入一個模塊時,其實是引入了一個變量名,此變量名就指向該模塊文件。模塊的導入之間沒法自動繼承,好比說模塊model文件中倒入了math模塊,那麼在導入模塊的文件中仍不能直接使用math模塊,要麼本身從新導入math模塊,要麼顯式使用model文件下的math模塊。

  2. 私有變量和公開變量

    在導入一個包時,會自動的過濾掉以'_'或者'__'開頭的模塊,那是由於這部分變量或者函數被聲明爲私有變量或者函數。在咱們本身定義的模塊內部,正常的函數和變量名是公開的,除此以外,__xxx__的變量名能夠被直接引用,可是包含特殊用途,好比__name__,__author__,__doc__。相似_xxx和__xxx這樣的函數和變量就是非公開的,不該該被直接引用。

  3. __all__

    在__init__.py文件中能夠顯式的定義__all__變量,來控制from model import *時導入的模塊。不然會默認導入模塊中全部不如下劃線開頭的全局名稱。

相關文章
相關標籤/搜索