在python中使用模式匹配获取文件扩展名
我试图找到一个文件的扩展名,以字符串的形式给出它的名称。我知道我可以使用函数在python中使用模式匹配获取文件扩展名,python,regex,Python,Regex,我试图找到一个文件的扩展名,以字符串的形式给出它的名称。我知道我可以使用函数os.path.splitext,但如果我的文件扩展名是.tar.gz或.tar.bz2,它将扩展名分别指定为gz和bz2,而不是tar.gz和tar.bz2。 所以我决定自己使用模式匹配来查找文件的扩展名 print re.compile(r'^.*[.](?P<ext>tar\.gz|tar\.bz2|\w+)$').match('a.tar.gz')group('ext') >>> g
os.path.splitext
,但如果我的文件扩展名是.tar.gz
或.tar.bz2
,它将扩展名分别指定为gz
和bz2
,而不是tar.gz
和tar.bz2
。所以我决定自己使用模式匹配来查找文件的扩展名
print re.compile(r'^.*[.](?P<ext>tar\.gz|tar\.bz2|\w+)$').match('a.tar.gz')group('ext')
>>> gz # I want this to come as 'tar.gz'
print re.compile(r'^.*[.](?P<ext>tar\.gz|tar\.bz2|\w+)$').match('a.tar.bz2')group('ext')
>>> bz2 # I want this to come 'tar.bz2'
print re.compile(r'^.[.](?Ptar\.gz|tar\.bz2|\w+$)).match('a.tar.gz')组('ext'))
>>>gz#我想把它命名为“tar.gz”
打印重新编译(r'^.[.](?Ptar\.gz|tar\.bz2|w+$)。匹配('a.tar.bz2')组('ext'))
>>>bz2#我希望这是‘焦油,bz2’
我在模式匹配中使用了(?p…)
,因为我也想获得扩展名
请帮忙
root,ext = os.path.splitext('a.tar.gz')
if ext in ['.gz', '.bz2']:
ext = os.path.splitext(root)[1] + ext
有些人在遇到问题时会想“我知道,我会使用正则表达式。”现在他们有两个问题。
>>打印重新编译(r'^.[.](?Ptar\.gz|tar\.bz2|w+$)。匹配('a.tar.gz')。组('ext'))
广州
>>>打印重新编译(r'^.*.[.](?Ptar\.gz|tar\.bz2|w+$).match('a.tar.gz').group('ext'))
tar.gz
>>>
那个?运算符尝试查找最小匹配项,因此,不是。*同时吃“.tar”,而是。*?找到允许匹配.tar.gz的最小匹配项。我知道这比用正则表达式打断你的头容易得多,有时听起来可能也很愚蠢。
name=“filename.tar.gz”
扩展=('.tar.gz','.py')
[x表示扩展名中的x,如果name.endswith(x)]
从phihags开始回答:
DOUBLE_EXTENSIONS = ['tar.gz','tar.bz2'] # Add extra extensions where desired.
def guess_extension(filename):
"""
Guess the extension of given filename.
"""
root,ext = os.path.splitext(filename)
if any([filename.endswith(x) for x in DOUBLE_EXTENSIONS]):
root, first_ext = os.path.splitext(root)
ext = first_ext + ext
return root, ext
继续从phihags答案到generic删除所有双扩展名或三扩展名,例如CropQDS275.jpg.aux.xml,同时在以下位置使用“.”:
tempfilename, file_extension = os.path.splitext(filename)
while '.' in tempfilename:
tempfilename, tempfile_extension = os.path.splitext(tempfilename)
file_extension = tempfile_extension + file_extension
这很简单,可以用于单个扩展和多个扩展
In [1]: '/folder/folder/folder/filename.tar.gz'.split('/')[-1].split('.')[0]
Out[1]: 'filename'
In [2]: '/folder/folder/folder/filename.tar'.split('/')[-1].split('.')[0]
Out[2]: 'filename'
In [3]: 'filename.tar.gz'.split('/')[-1].split('.')[0]
Out[3]: 'filename'
如果name=“hi.c.java”如果你想单独使用.java呢?目前是的。但是,如果愿意的话,我应该可以在以后的正则表达式模式中添加更多内容。好的,在这种情况下可以这样做,但我想用python正则表达式来解决它。@Guanidene:如果是家庭作业,请标记问题家庭作业。如果这不是家庭作业,那么在函数已经编写、调试并运行时不要使用正则表达式。@s.Lott-这不是家庭作业,我想使用正则表达式解决问题,仅此而已。如果仅仅解决问题是目的,我早就可以像phihag说的那样做了。@phihag——我希望使用正则表达式的另一个原因——它很紧凑。如果我按照你的方式去做,我将不必要地需要3行代码(这也使得我的代码很笨拙),而使用regex我可以在一行中获得所有东西@Guanidene更紧凑并不意味着可读性和可维护性更强。还有,为什么一个复杂的正则表达式没有非程序员能理解的三行那么笨拙?不管怎样,每个人都有自己的。我真的很感谢你!这件事花了我很多时间!假设存在一个文件扩展名
.gz
(假设),我可能也想匹配它。因此,在本例中,元组将是extensions=('.gz','.tar.gz','.py')
(name=filenmae.tar.gz
),如果我执行此命令-[x for x in extensions if name.endswith(x)]
当我想将其与tar gz
匹配时,它将错误地匹配gz
。伙计,我想要的是一个通用的解决方案,而不是一个特定于数据的解决方案!这有一个选项,因此如果tar.gz与return匹配,则将其放在列表的第一位,但一旦将gz放在tar.gz.gz.gz.gz.gz.extensions=('tar.gz','gz','py')>>>>name'set.tar.gz'>>>>def test()之前,此方法将不起作用:。。。对于扩展中的x:。。。如果name.endswith(x):。。。返回x。。。return'>>>>test()'tar.gz'>>>>
@Guanidene:是的,我不记得同意了,但你可以留下评论,也许regex是一个正确的解决方案,确实如此,但在回答这个问题时,我一开始就说它可能很愚蠢,而且有一个选项,我并不是在争论这是正确的。在[4]:'/folder/folder/folder/filename.tar.gz'/')split('/')[-1].split('..')[1:[4]:['tar','gz']对我来说很好用!
In [1]: '/folder/folder/folder/filename.tar.gz'.split('/')[-1].split('.')[0]
Out[1]: 'filename'
In [2]: '/folder/folder/folder/filename.tar'.split('/')[-1].split('.')[0]
Out[2]: 'filename'
In [3]: 'filename.tar.gz'.split('/')[-1].split('.')[0]
Out[3]: 'filename'