簡體   English   中英

負向前瞻斷言不在python中工作

[英]negative lookahead assertion not working in python

任務:
- 給定:圖像文件名列表
- todo:創建一個文件名不包含單詞“thumb”的新列表 - 即僅定位非縮略圖圖像(使用PIL - Python Imaging Library)。

我試過r".*(?!thumb).*"但它失敗了。

我已經找到了解決方案(這里是stackoverflow)將^到正則表達式並將.*放入負向前瞻: r"^(?!.*thumb).*"這現在有效。

問題是,我想了解為什么我的第一個解決方案不起作用,但我不這樣做。 由於正則表達式足夠復雜,我真的很想理解它們。

我所理解的是^告訴解析器以下條件是在字符串的開頭匹配。 但是,(不工作)第一個例子中的.*也不是從字符串的開頭開始的嗎? 我認為它會從字符串的開頭開始,並在到達“拇指”之前搜索盡可能多的字符。 如果是這樣,它將返回不匹配。

有人可以解釋為什么r".*(?!thumb).*"不起作用但是r"^(?!.*thumb).*"是嗎?

謝謝!

有人可以解釋為什么r".*(?!thumb).*"不起作用但是r"^(?!.*thumb).*"是嗎?

第一個將始終匹配,因為.*將消耗所有字符串(因此它不能被任何內容跟隨負向前瞻失敗)。 第二個是有點復雜的,並且將從行的開頭匹配,最多的字符直到它遇到“拇指”並且如果存在,那么整個匹配失敗,因為該行開始后面跟着'拇指' 。

第二個更容易寫為:

  • 'thumb' not in string
  • not re.search('thumb', string) (而不是匹配)

正如我在評論中提到的,你的問題是:

文件名不包含單詞 “拇指”

因此,您可能希望考慮是否應該排除thumbs up

(Darn,Jon打敗了我。好吧,你可以看看這些例子)

就像其他人說的那樣,正則表達式不是這項工作的最佳工具。 如果您正在使用文件路徑,請查看os.path

至於過濾你不想要的文件,你可以這樣做, if 'thumb' not in filename: ...一旦你解剖了路徑(其中filenamestr )。

對后人來說,這是我對那些正則表達式的看法。 r".*(?!thumb).*"不起作用,因為.*是貪婪的,前瞻的優先級非常低。 看看這個:

>>> re.search('(.*)((?!thumb))(.*)', '/tmp/somewhere/thumb').groups()
('/tmp/somewhere/thumb', '', '')
>>> re.search('(.*?)((?!thumb))(.*)', '/tmp/somewhere/thumb').groups()
('', '', '/tmp/somewhere/thumb')
>>> re.search('(.*?)((?!thumb))(.*?)', '/tmp/somewhere/thumb').groups()
('', '', '')

最后一個很奇怪......

另一個正則表達式( r"^(?!.*thumb).*" )的作用是因為.*位於前瞻之內,所以你沒有任何字符被盜的問題。 實際上你根本不需要^ ,這取決於你是使用re.match還是re.search

>>> re.search('((?!.*thumb))(.*)', '/tmp/somewhere/thumb').groups()
('', 'humb')
>>> re.search('^((?!.*thumb))(.*)', '/tmp/somewhere/thumb').groups()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'NoneType' object has no attribute 'groups'
>>> re.match('((?!.*thumb))(.*)', '/tmp/somewhere/thumb').groups()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'NoneType' object has no attribute 'groups'

忽略關於正則表達式的所有內容,您的任務似乎相對簡單:

  • 給定:圖像文件名列表
  • todo:創建一個文件名不包含單詞“thumb”的新列表 - 即僅定位非縮略圖圖像(使用PIL - Python Imaging Library)。

假設您有一個類似於下面的文件名列表:

filenames = [ 'file1.jpg', 'file1-thumb.jpg', 'file2.jpg', 'file2-thumb.jpg' ]

然后你可以獲得一個包含單詞thumb的文件列表,如下所示:

not_thumb_filenames = [ filename for filename in filenames if not 'thumb' in filename ]

這就是我們所說的列表理解 ,基本上是簡寫:

not_thumb_filenames = []
for filename in filenames:
  if not 'thumb' in filename:
    not_thumb_filenames.append(filename)

對於這個簡單的任務,正則表達式並不是必需的。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM