1

ファイル拡張子を除いた特定のファイルタイプのフルパスファイル名を短いファイル名に変換する正規表現を作成しようとしています。

たとえば、次の文字列から.barファイルの名前だけを取得しようとしています。

re.search('/(.*?)\.bar$', '/def_params/param_1M56/param/foo.bar')

Python re docsによると、*?は貪欲でないバージョンな*ので、

'foo'

のために戻ったmatch.group(1)が、代わりに私は得た

'def_params/param_1M56/param/foo'

私はここで貪欲について何が欠けていますか?

4

7 に答える 7

8

不足しているのは、正規表現エンジンほどの貪欲さではありません。左から右に動作するため、/できるだけ早く一致し.*?、そこから動作するように強制されます。この場合、最良の正規表現には貪欲はまったく含まれません(これを機能させるにはバックトラックが必要です。ただし、スラッシュが多い場合は実行に非常に長い時間がかかる可能性があります)が、より明確なパターンです。

'/([^/]*)\.bar$'
于 2011-04-20T20:41:32.333 に答える
3

貪欲に依存しないように正規表現を変更することをお勧めします。

拡張子の前のファイル名.barと最後の。の後のすべてが必要です/。これは行う必要があります:

re.search(`/[^/]*\.bar$`, '/def_params/param_1M56/param/foo.bar')

これが行うことは、一致し、次に一致しない/0個以上の文字(可能な限り)、そして。 /.bar

于 2011-04-20T20:39:40.963 に答える
0

欲張りでない演算子をそれほどよく理解しているとは言いませんが、その特定の問題の解決策は([^ /] *?)を使用することです。

于 2011-04-20T20:40:05.163 に答える
0

正規表現は右から始まります。最初に。*を付けると、機能するはずです。

于 2011-04-20T20:40:11.440 に答える
0

私は正規表現が好きですが、ここでは必要ありません。

path = '/def_params/param_1M56/param/foo.bar'
print  path.rsplit('/',1)[1].rsplit('.')[0]

path = '/def_params/param_1M56/param/fululu'
print  path.rsplit('/',1)[1].rsplit('.')[0]

path = '/def_params/param_1M56/param/one.before.two.dat'
print  path.rsplit('/',1)[1].rsplit('.',1)[0]

結果

foo
fululu
one.before.two
于 2011-04-20T21:24:13.780 に答える
0

他の人が正規表現の質問に答えましたが、この場合、正規表現よりも効率的な方法があります。

file_name = path[path.rindex('/')+1 : path.rindex('.')]
于 2011-04-20T21:49:33.930 に答える
-1

サイズについてはこれを試してみてください:

match = re.search('。*/(。*?)。bar $'、'/def_params/param_1M56/param/foo.bar')

于 2011-04-20T20:42:17.983 に答える