这与我之前的问题类似,但我认为它与相似之处相比有更多不同。
我在Bash中有一个文件夹。在该文件夹中,是编号文件,所有文件类型均相同。这些文件的文件名不能包含空格。我需要按编号对这些文件进行排序。说,如果文件夹包含:
1.jpg 1.2.jpg ch.002.jpg Chapter3.jpg Chapter_004:_Blah.jpg Chapter_4.1.jpg Chapter_5.jpg Chapter_5.005.jpg
结果字符串为
"1.jpg 1.2.jpg 002.jpg Chapter3.jpg Chapter 004:_Blah.jpg Chapter_4.1.jpg Chapter_5.jpg Chapter_5.005.jpg"
如您所见,我需要浮点数,带前导零的数字和常规数字的支持。
答案 0 :(得分:3)
带有粘贴,GNU排序和bash的Schwartzian transform:
paste <(tr -cd '[0-9.\n]' < file | sort -V) file | awk '{print $2}' | tr '\n' ' '
输出:
1.jpg 1.2.jpg 002.jpg Chapter3.jpg Chapter_004:_Blah.jpg Chapter_4.1.jpg Chapter_5.jpg Chapter_5.005.jpg
答案 1 :(得分:1)
由于您已声明这些文件的文件名不能包含空格。您可以使用一个相当简单的Bash管道,使用*
和DSU(Decorate Sort Undecorate或Schwartzian转换)来生成DSU( gawk
和数字排序。 (如果文件中可以包含空格,则方法相同,但是我们需要使用Bash循环而不是tr ' ' '\n'
来分隔每个文件名。)
给出以下文件:
$ echo *
1.2.jpg 1.jpg Chapter3.jpg Chapter_004:_Blah.jpg Chapter_4.1.jpg Chapter_5.005.jpg Chapter_5.jpg ch.002.jpg
您可以这样做:
$ echo * | tr ' ' '\n' | gawk '{match($0, /([0-9]+\.{0,1}[0-9]*)/, arr); print arr[1] "/" $0}' | sort -n | awk -F"/" '{print $NF}' | tr '\n' ' '
1.jpg 1.2.jpg ch.002.jpg Chapter3.jpg Chapter_004:_Blah.jpg Chapter_4.1.jpg Chapter_5.jpg Chapter_5.005.jpg
无论要添加到装饰部分的任何条件,都可以通过更改match($0, /([0-9]+\.{0,1}[0-9]*)/, arr)
中的正则表达式来添加,以从文件名捕获该部分。
在Unix中,字符/
是非法的文件名字符,因此在修饰和文件名之间是有效的分隔符。然后,我们根据装饰的float解释对数字进行排序,并使用第二个awk
删除装饰。
如果您想向sort
添加多个条件,则可以添加第一个awk
并以无效的文件名字符作为分隔符的修饰。然后适当地使用sort
的多字段参数,并用最后的awk
命令取消修饰以打印文件名。