用python實現glob style pattern,pythonglob

來源:互聯網
上載者:User

用python實現glob style pattern,pythonglob
一說起萬用字元,大家很快就會想起*和?號,有了萬用字元,使得表達能力大大增強,很多linux命令都支援這個東西,其實就是glob style pattern.
就連redis的keys命令都支援glob.

我要實現的glob,支援以下特性:

  • 星號*匹配0個或多個任一字元
  • ?匹配確切的一個任一字元
  • [characters]匹配任意一個方括弧內的字元,比如[abc],要麼匹配a,要麼匹配b,要麼匹配c.
  • [!character]排除方括弧內的字元
  • [character-character],表示2個字元範圍內的都可以匹配,如[a-z],[0-9]

實現這個東西其實挺簡單的,從左往右掃描s串和p串,如果最後都走到了結尾,那麼就是可以匹配的.
主要痛點在於*號的匹配.因為*號可以匹配0個或者多個,所以需要試探回溯.這裡通過儲存*號位置,如果後面的走不通了,就拉回*號位置,貪婪匹配.

至於方括弧的展開,弄個include和exclude變數就很清晰了.


下面上代碼.

#coding=utf-8def build_expand(p):#方括弧展開    ptr2include = {}    ptr2exclude = {}    ptr2next = {}    len_p = len(p)    pPtr = 0    while pPtr<len_p:        if p[pPtr] == '[':            start = pPtr            pPtr += 1            include = set([])            exclude = set([])            while p[pPtr]!=']':                if p[pPtr]=='!':                    exclude.add(p[pPtr+1])                    pPtr += 2                elif p[pPtr+1] == '-':                    include.update({chr(x) for x in range(ord(p[pPtr]),ord(p[pPtr+2])+1)})                    pPtr += 3                else:                    include.add(p[pPtr])                    pPtr += 1            if include:                ptr2include[start] = include            if exclude:                ptr2exclude[start] = exclude            ptr2next[start] = pPtr + 1        else:            pPtr += 1    return ptr2include, ptr2exclude, ptr2nextdef isMatch(s, p):    len_s = len(s); len_p = len(p)    sPtr = pPtr = ss = 0    star = None    ptr2include, ptr2exclude, ptr2next = build_expand(p)    while sPtr<len_s:        if pPtr<len_p and (p[pPtr] in ['?',s[sPtr]]):            sPtr += 1; pPtr += 1            continue        if pPtr<len_p and p[pPtr] == '[':            if pPtr in ptr2include and s[sPtr] in ptr2include[pPtr]:                sPtr += 1                pPtr = ptr2next[pPtr]                continue            if pPtr in ptr2exclude and s[sPtr] not in ptr2exclude[pPtr]:                sPtr += 1                pPtr = ptr2next[pPtr]                continue        if pPtr<len_p and p[pPtr]=='*':            star = pPtr; pPtr += 1; ss = sPtr            continue        if star is not None:            pPtr = star + 1; ss += 1; sPtr = ss            continue        return False    while pPtr<len(p) and p[pPtr]=='*':        pPtr += 1    return pPtr == len_pif __name__ == '__main__':    params = [            ("aa","a"),            ("aa","aa"),            ("aaa","aa"),            ("aa", "*"),            ("aa", "a*"),            ("ab", "?*"),            ("aab", "c*a*b"),            ("cab", "c*a*b"),            ("cxyzbazba", "c*ba"),            ('abc','ab[a-c]'),            ('abd','ab[a-c]'),            ('abe','ab[cde]'),            ('abe','ab[!e]'),            ('abe','ab[!c]'),        ]    for p in params:        print p,isMatch(*p)

運行結果是

('aa', 'a') False
('aa', 'aa') True
('aaa', 'aa') False
('aa', '*') True
('aa', 'a*') True
('ab', '?*') True
('aab', 'c*a*b') False
('cab', 'c*a*b') True
('cxyzbazba', 'c*ba') True
('abc', 'ab[a-c]') True
('abd', 'ab[a-c]') False
('abe', 'ab[cde]') True
('abe', 'ab[!e]') False
('abe', 'ab[!c]') True




python 裡面的glob模組是怎使用的

glob是python自己帶的一個檔案操作相關模組,用它可以尋找符合自己目的的檔案,就類似於Windows下的檔案搜尋,支援萬用字元操作,*,?,[]這三個萬用字元,*代表0個或多個字元,?代表一個字元,[]匹配指定範圍內的字元,如[0-9]匹配數字。
它的主要方法就是glob,該方法返回所有匹配的檔案路徑列表,該方法需要一個參數用來指定匹配的路徑字串(本字串可以為絕對路徑也可以為相對路徑),其返回的檔案名稱只包括目前的目錄裡的檔案名稱,不包括子檔案夾裡的檔案。
比如:
glob.glob(r'c:\*.txt')
我這裡就是獲得C盤下的所有txt檔案
glob.glob(r'E:\pic\*\*.jpg')
獲得指定目錄下的所有jpg檔案
使用相對路徑:
glob.glob(r'../*.py')
 
用python glob問題

你輸入 
print "\210"
結果是什嗎?\210被轉義成八位元210代表的字元了
在字串前加上r,讓字串不轉義
fileList = glob.glob(r"C:\Users\Administrator\210\*.htm")
或者用正斜杠分隔目錄
fileList = glob.glob("C:/Users/Administrator/210/*.htm")
 

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.