本问题已经有最佳答案,请猛点这里访问。
我有一个包含jpgs和其他文件的目录,所有jpgs的文件名中都带有数字。 有些文件名中可能包含其他字符串。
例如。
01.jpg
或者可能是
Picture 03.jpg
在Python中,我需要按升序排列所有jpg的列表。
这是此代码段
import os
import numpy as np
myimages = [] #list of image filenames
dirFiles = os.listdir('.') #list of directory files
dirFiles.sort() #good initial sort but doesnt sort numerically very well
sorted(dirFiles) #sort numerically in ascending order
for files in dirFiles: #filter out all non jpgs
if '.jpg' in files:
myimages.append(files)
print len(myimages)
print myimages
我得到的是这个
['0.jpg', '1.jpg', '10.jpg', '11.jpg', '12.jpg', '13.jpg', '14.jpg',
'15.jpg', '16.jpg', '17.jpg', '18.jpg', '19.jpg', '2.jpg', '20.jpg',
'21.jpg', '22.jpg', '23.jpg', '24.jpg', '25.jpg', '26.jpg', '27.jpg',
'28.jpg', '29.jpg', '3.jpg', '30.jpg', '31.jpg', '32.jpg', '33.jpg',
'34.jpg', '35.jpg', '36.jpg', '37.jpg', '4.jpg', '5.jpg', '6.jpg',
'7.jpg', '8.jpg', '9.jpg']
显然,它首先盲目地排序最高有效数字。 我尝试使用sorted(),因为您可以看到它可以解决此问题,但没有区别。
fnames = sorted([fname for fname in os.listdir(.) if fname.endswith(.jpg)], key=lambda f: int(f.rsplit(os.path.extsep, 1)[0].rsplit(None,1)[-1]))
这是因为list元素是strings。
对包含字母数字字符串的列表进行排序
@ inspectorG4dget,您还可以使用生成器理解。
@cris:不。 sorted还是会列出它
@ inspectorG4dget,的确如此,但这仅是实现细节。 其他实现可能不会列出输入。
@ inspectorG4dget我也得到了ValueError:int()的无效字面量以10为底
假设每个文件名中只有一个数字:
>>> dirFiles = ['Picture 03.jpg', '02.jpg', '1.jpg']
>>> dirFiles.sort(key=lambda f: int(filter(str.isdigit, f)))
>>> dirFiles
['1.jpg', '02.jpg', 'Picture 03.jpg']
也可以!非常干净,我最喜欢您的解决方案。但是,如果由于某种原因,列表中包含没有数字的元素,它将失败。但是我只是确保在myimages []中进行排序,因此肯定会在名称中包含一个数字。
@ user3474042是的,如果所有jpeg都有数字,则可以使用。否则,可以使用int(filter(str.isdigit, f) or -1))(这将无数字的文件名放在最前面)。顺便说一句,请检查glob模块,该模块可让您直接请求*.jpg文件。
用于python 3的Lambda变得更难看:lambda f: int(.join(filter(str.isdigit, f))))(否则它会抱怨int()参数必须是字符串,类似字节的对象或数字,而不是过滤器……我想念rubys duck-typing ...)
是的,正如@melboiko所说,您的答案仅适用于Python 2
有一个模块natsort。 只需执行pip install natsort。
>>> import natsort
>>> ll = ['Picture 13.jpg', 'Picture 14.jpg', 'Picture 15.jpg','Picture 0.jpg', 'Picture 1.jpg', 'Picture 10.jpg', 'Picture 11.jpg', 'Picture 12.jpg', 'Picture 16.jpg', 'Picture 17.jpg', 'Picture 18.jpg', 'Picture 19.jpg', 'Picture 2.jpg', 'Picture 20.jpg', 'Picture 21.jpg', 'Picture 22.jpg', 'Picture 23.jpg', 'Picture 24.jpg', 'Picture 25.jpg', 'Picture 26.jpg', 'Picture 27.jpg', 'Picture 28.jpg', 'Picture 29.jpg', 'Picture 3.jpg', 'Picture 30.jpg', 'Picture 31.jpg', 'Picture 32.jpg', 'Picture 33.jpg', 'Picture 34.jpg', 'Picture 35.jpg', 'Picture 36.jpg', 'Picture 37.jpg']
>>> print(natsort.natsorted(ll,reverse=True))
['Picture 37.jpg', 'Picture 36.jpg', 'Picture 35.jpg', 'Picture 34.jpg', 'Picture 33.jpg', 'Picture 32.jpg', 'Picture 31.jpg', 'Picture 30.jpg', 'Picture 29.jpg', 'Picture 28.jpg', 'Picture 27.jpg', 'Picture 26.jpg', 'Picture 25.jpg', 'Picture 24.jpg', 'Picture 23.jpg', 'Picture 22.jpg', 'Picture 21.jpg', 'Picture 20.jpg', 'Picture 19.jpg', 'Picture 18.jpg', 'Picture 17.jpg', 'Picture 16.jpg', 'Picture 15.jpg', 'Picture 14.jpg', 'Picture 13.jpg', 'Picture 12.jpg', 'Picture 11.jpg', 'Picture 10.jpg', 'Picture 3.jpg', 'Picture 2.jpg', 'Picture 1.jpg', 'Picture 0.jpg']
我正在获取ValueError:以10为底的int()的无效文字:
我找到了更好的解决方案。现在将更新。但我没有得到数据错误。如果您只用数字作为名称,则应该适合您。但是由于有通用的方法,您可能会更喜欢它。
仅供参考,看起来安装命令是pip install natsort。这些年来,情况可能发生了变化,我不
I have a directory with jpgs and other files in it.
[...]
['0.jpg', '1.jpg', '10.jpg', '11.jpg', '12.jpg', '13.jpg', '14.jpg',
'15.jpg', '16.jpg', '17.jpg', '18.jpg', '19.jpg', '2.jpg', '20.jpg',
'21.jpg', '22.jpg', '23.jpg', '24.jpg', '25.jpg', '26.jpg', '27.jpg',
'28.jpg', '29.jpg', '3.jpg', '30.jpg', '31.jpg', '32.jpg', '33.jpg',
'34.jpg', '35.jpg', '36.jpg', '37.jpg', '4.jpg', '5.jpg', '6.jpg',
'7.jpg', '8.jpg', '9.jpg'] Clearly it sorts blindly the most
significant number first. I tried using sorted() as you can see hoping
that it would fix it but it makes no difference
您可以使用splitext获取不带扩展名的零件,并将其转换为int进行排序。 如果列表名为" l",而排序后的列表名为" lsorted",则可以使用:
lsorted = sorted(l,key=lambda x: int(os.path.splitext(x)[0]))
os.path.splitext在'10 .jpg'上返回['10','。jpg'],因此只要元素0不带扩展名的文件名仅包含可以 使用int()转换为整数。 否则,您将遇到错误。
哈!作品!感谢您的解释!
没问题。玩得开心。