国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 編程 > Python > 正文

詳解Python中的文本處理

2019-11-25 17:46:21
字體:
供稿:網(wǎng)友

字符串 -- 不可改變的序列

如同大多數(shù)高級編程語言一樣,變長字符串是 Python 中的基本類型。Python 在“后臺”分配內(nèi)存以保存字符串(或其它值),程序員不必為此操心。Python 還有一些其它高級語言沒有的字符串處理功能。

在 Python 中,字符串是“不可改變的序列”。盡管不能“按位置”修改字符串(如字節(jié)組),但程序可以引用字符串的元素或子序列,就象使用任何序列一樣。Python 使用靈活的“分片”操作來引用子序列,字符片段的格式類似于電子表格中一定范圍的行或列。以下交互式會話說明了字符串和字符片段的的用法:
字符串和分片

>>> s =     "mary had a little lamb">>> s[0]     # index is zero-based    'm'>>> s[3] =     'x'     # changing element in-place failsTraceback (innermost last): File     "<stdin>", line 1,     in     ?TypeError: object doesn't support item assignment>>> s[11:18]     # 'slice' a subsequence    'little '>>> s[:4]     # empty slice-begin assumes zero    'mary'>>> s[4]     # index 4 is not included in slice [:4]    ' '>>> s[5:-5]     # can use "from end" index with negatives    'had a little'>>> s[:5]+s[5:]     # slice-begin & slice-end are complimentary    'mary had a little lamb'

另一個功能強大的字符串操作就是簡單的 in 關(guān)鍵字。它提供了兩個直觀有效的構(gòu)造:
in 關(guān)鍵字

>>> s =     "mary had a little lamb">>>     for     c     in     s[11:18]:     print     c,     # print each char in slice...l i t t l e>>>     if    'x'     in     s:     print    'got x'     # test for char occurrence...>>>     if    'y'     in     s:     print    'got y'     # test for char occurrence...got y

在 Python 中,有幾種方法可以構(gòu)成字符串文字。可以使用單引號或雙引號,只要左引號和右引號匹配,常用的還有其它引號的變化形式。如果字符串包含換行符或嵌入引號,三重引號可以很方便地定義這樣的字符串,如下例所示:
三重引號的使用

>>> s2 =     """Mary had a little lamb... its fleece was white as snow... and everywhere that Mary went... the lamb was sure to go""">>>     print     s2Mary had a little lambits fleece was white as snow    and     everywhere that Mary wentthe lamb was sure to go

使用單引號或三重引號的字符串前面可以加一個字母 "r" 以表示 Python 不應(yīng)該解釋規(guī)則表達式特殊字符。例如:
使用 "r-strings"

>>> s3 =     "this /n and /n that">>>     print     s3this    and    that>>> s4 = r    "this /n and /n that">>>     print     s4this /n     and     /n that

在 "r-strings" 中,可能另外組成換碼符的反斜杠被當作是常規(guī)反斜杠。在以后的規(guī)則表達式討論中會進一步說明這個話題。

文件和字符串變量

我們談到“文本處理”時,我們通常是指處理的內(nèi)容。Python 將文本文件的內(nèi)容讀入可以操作的字符串變量非常容易。文件對象提供了三個“讀”方法: .read()、.readline() 和 .readlines()。每種方法可以接受一個變量以限制每次讀取的數(shù)據(jù)量,但它們通常不使用變量。 .read() 每次讀取整個文件,它通常用于將文件內(nèi)容放到一個字符串變量中。然而 .read() 生成文件內(nèi)容最直接的字符串表示,但對于連續(xù)的面向行的處理,它卻是不必要的,并且如果文件大于可用內(nèi)存,則不可能實現(xiàn)這種處理。

.readline() 和 .readlines() 非常相似。它們都在類似于以下的結(jié)構(gòu)中使用:
Python .readlines() 示例

    fh = open(    'c://autoexec.bat')    for     line     in     fh.readlines():     print     line

.readline() 和 .readlines() 之間的差異是后者一次讀取整個文件,象 .read() 一樣。.readlines() 自動將文件內(nèi)容分析成一個行的列表,該列表可以由 Python 的 for ... in ... 結(jié)構(gòu)進行處理。另一方面,.readline() 每次只讀取一行,通常比 .readlines() 慢得多。僅當沒有足夠內(nèi)存可以一次讀取整個文件時,才應(yīng)該使用 .readline()。

如果正在使用處理文件的標準模塊,可以使用 cStringIO 模塊將字符串轉(zhuǎn)換成“虛擬文件”(如果需要生成模塊的子類,可以使用 StringIO 模塊,初學(xué)者未必要這樣做)。例如:
cStringIO 模塊

>>>     import     cStringIO>>> fh = cStringIO.StringIO()>>> fh.write(    "mary had a little lamb")>>> fh.getvalue()    'mary had a little lamb'>>> fh.seek(5)>>> fh.write(    'ATE')>>> fh.getvalue()    'mary ATE a little lamb'

但是,請記住,cStringIO“虛擬文件”不是永久的,這一點與真正的文件不同。如果不保存它(如將它寫入一個真正的文件,或者使用 shelve 模塊或數(shù)據(jù)庫),則程序結(jié)束時,它將消失。

標準模塊:string

string 模塊也許是 Python 1.5.* 標準發(fā)行版中最常用的模塊。實際上,在 Python 1.6 或更高版本中,string 模塊中的功能將作為內(nèi)置字符串方法(在撰寫本文時,詳細信息尚未發(fā)布)。當然,任何執(zhí)行文本處理任務(wù)的程序也許應(yīng)該用以下這行開頭:
開始使用 string 的方法

      import string

一般經(jīng)驗法則告訴我們,如果 可以 使用 string 模塊完成任務(wù),那么那就是 正確 的方法。與 re(規(guī)則表達式)相比,string 函數(shù)通常更快速,大多數(shù)情況下他們更易于理解和維護。第三方 Python 模塊,包括某些用 C 編寫的快速模塊,適用于專門的任務(wù),但可移植性和熟悉性都建議只要可能就使用 string。如果您習(xí)慣于使用其它語言,也會有例外,但不如您想像的那樣多。

string 模塊包含了幾種類型的事物,如函數(shù)、方法和類;它還包含了公共常量的字符串。例如:
string 用法例 1

>>>     import     string>>> string.whitespace    '/011/012/013/014/015 '>>> string.uppercase    'ABCDEFGHIJKLMNOPQRSTUVWXYZ'

雖然可以用手寫出這些常量,string 版本或多或少確保了常量對于運行 Python 腳本的國家語言和平臺將是正確的。

string 還包括了以常見方式(可以結(jié)合這些方式來構(gòu)成幾種罕見的轉(zhuǎn)換)轉(zhuǎn)換字符串的函數(shù)。例如:
string 用法例 2

>>>     import     string>>> s =     "mary had a little lamb">>> string.capwords(s)    'Mary Had A Little Lamb'>>> string.replace(s,     'little',     'ferocious')    'mary had a ferocious lamb'

還有許多沒有在這里具體說明的其它轉(zhuǎn)換;可以在 Python 手冊中查找詳細信息。

還可以使用 string 函數(shù)來報告字符串屬性,如子串的長度或位置,例如:
string 用法例 3

>>>     import     string>>> s =     "mary had a little lamb">>> string.find(s,     'had')5>>> string.count(s,     'a')4

最后,string 提供了非常 Python 化的奇特事物。.split() 和 .join() 對提供了在字符串和字節(jié)組之間轉(zhuǎn)換的迅捷方法,您會發(fā)現(xiàn)它們非常有用。用法很簡單:
string 用法例 4

>>>     import     string>>> s =     "mary had a little lamb">>> L = string.split(s)>>> L[    'mary',     'had',     'a',     'little',     'lamb']>>> string.join(L,     "-")    'mary-had-a-little-lamb'

當然,除了 .join() 之外,也許會利用列表來做其它事(如某些涉及我們熟悉的 for ... in ... 結(jié)構(gòu)的事情)。

標準模塊:re

re 模塊廢棄了在老的 Python 代碼中使用的 regex 和 regsub 模塊。雖然相對于 regex 仍然有幾個有限的優(yōu)點,不過這些優(yōu)點微不足道,不值得在新代碼中使用。過時的模塊可能會從未來的 Python 發(fā)行版中刪除,并且 1.6 版可能有一個改進的接口兼容的 re 模塊。所以,規(guī)則表達式仍將使用 re 模塊。

規(guī)則表達式很復(fù)雜。也許有人會撰寫關(guān)于這個主題的書,但實際上,已經(jīng)有許多人這樣做了!本文嘗試捕捉規(guī)則表達式的“完全形態(tài)”,讓讀者可以掌握它。

規(guī)則表達式是一種很簡練方法,用于描述可能在文本中出現(xiàn)的模式。是否會出現(xiàn)某些字符?是否按特定順序出現(xiàn)?子模式是否會重復(fù)一定次數(shù)?其它子模式是否會排除在匹配之外?從概念上說,似乎不能用自然語言了直觀地描述模式。訣竅是使用規(guī)則表達式的簡潔語法來編碼這種描述。

當處理規(guī)則表達式時,將它作為它自己的編程問題來處理,即使只涉及一或兩行代碼;這些行有效地構(gòu)成了一個小程序。

從最小處著手。從最基本上看,任何規(guī)則表達式都涉及匹配特定的“字符類”。最簡單的字符類就是單個字符,它在模式中只是一個字。通常,您希望匹配一類字符。可以通過將類括在方括號內(nèi)來表明這是一個類;在括號中,可以有一組字符或者用破折號指定的字符范圍。還可以使用許多命名字符類來確定您的平臺和國家語言。以下是一些示例:
字符類

>>>     import     re>>> s =     "mary had a little lamb">>>     if     re.search(    "m", s):     print    "Match!"     # char literalMatch!>>>     if     re.search(    "[@A-Z]", s):     print    "Match!"     # char class...     # match either at-sign or capital letter...>>>     if     re.search(    "/d", s):     print    "Match!"     # digits class...

可以將字符類看作是規(guī)則表達式的“原子”,通常會將那些原子組合成“分子”。可以結(jié)合使用 分組和 循環(huán) 來完成此操作。由括號表示分組:括號中包含的任何子表達式都被看作是用于以后分組或循環(huán)的原子。循環(huán)則由以下幾個運算符中的某一個來表示:"*" 表示“零或多”;"+" 表示“一或多”;"?" 表示“零或一”。例如,請看以下示例:
樣本規(guī)則表達式

ABC([d-w]*/d/d?)+XYZ

對于要匹配這個表達式的字符串,它必須以 "ABC" 開頭、以 "XYZ" 結(jié)尾 -- 但它的中間必須要有什么呢?中間子表達式是 ([d-w]*/d/d?),而且后面跟了“一或多”運算符。所以,字符串的中間必須包括一個(或者兩個,或者一千個)與括號中的子表達式匹配的字符或字符串。字符串 "ABCXYZ" 不匹配,因為它的中間沒有必要的字符。

不過這個內(nèi)部子表達式是什么呢?它以 d-w 范圍內(nèi)的 零或多個 字母開頭。一定要注意:零字母是有效匹配,雖然使用英語單詞 "some"(一些)來描述它,可能會感到很別扭。接著,字符串必須 恰好有一個數(shù)字;然后有 零或一個 附加數(shù)字。(第一個數(shù)字字符類沒有循環(huán)運算符,所以它只出現(xiàn)一次。第二個數(shù)字字符類有 "?" 運算符。)總而言之,這將翻譯成“一個或兩個數(shù)字”。以下是一些與規(guī)則表達式匹配的字符串:
匹配樣本表達式的字符串

ABC1234567890XYZABCd12e1f37g3XYZABC1XYZ

還有一些表達式與規(guī)則表達式 不匹配(想一想,它們?yōu)槭裁床黄ヅ洌?br />不匹配樣本表達式的字符串

ABC123456789dXYZABCdefghijklmnopqrstuvwXYZABcd12e1f37g3XYZABC12345%67890XYZABCD12E1F37G3XYZ

需要一些練習(xí)才能習(xí)慣創(chuàng)建和理解規(guī)則表達式。但是,一旦掌握了規(guī)則表達式,您就具有了強大的表達能力。也就是說,轉(zhuǎn)而使用規(guī)則表達式解決問題通常會很容易,而這類問題實際上可以使用更簡單(而且更快速)的工具,如 string,來解決。

發(fā)表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發(fā)表
主站蜘蛛池模板: 阳城县| 汤原县| 舞钢市| 公安县| 临沂市| 汝阳县| 灯塔市| 哈密市| 虹口区| 呼伦贝尔市| 荣成市| 周宁县| 通城县| 武隆县| 江门市| 托克逊县| 鄂伦春自治旗| 买车| 榆林市| 邳州市| 呼伦贝尔市| 平泉县| 宁都县| 禹城市| 宝丰县| 麻城市| 米泉市| 双鸭山市| 达州市| 龙里县| 卢氏县| 乌鲁木齐市| 临朐县| 永春县| 迁西县| 祁门县| 荔浦县| 乡城县| 达州市| 曲阜市| 盐池县|