2017-10-17 184 views
1

在macOS Sierra(第10.12.6节)中,我有一个包含许多平面文本(.txt)文件的目录。每个文件都有一个无用的名称,例如“无标题文本252.txt”。我想知道是否有可能以每个文件第一行中的代码为基础,以编程方式重命名每个文件。根据内容重命名文件

每个文件都以一个节符号(§)开头,一个空格,一个始终包含句点(.)的代码和一个空格。该代码通常只是数字,但偶尔还会有一个尾随连字符(-),后跟一个字母。例如:'§ 177.30 ''§ 60.10-a '

我想根据代码重命名每个文件,但首先要重新设置代码的格式。简而言之,前缀为P,从代码中删除期间,并添加尾随.txt。使用上面的示例,文件名将是:P17730.txtP6010-a.txt

在命令提示,我已想出如何从每个文件的grep的代码:

grep -o '^§ [A-Za-z0-9]*\.[A-Za-z0-9\-]* ' *.txt 

这返回一切从部分符号尾随空格(例如'§ 130.65-a ')。

那么,剩下的问题是:

  1. 如何格式化grep的结果我想要的文件名(如P13065-a.txt);和,
  2. 如何将文件重命名操作与grep结合?

回答

1

可以使用sed(通过删除所有非数字)提取只能从第一行数字:

$ sed -n '1 {s/[^0-9]//g; p;}' <<<"§ 177.30 " 
17730 

然后find所有*.txt文件,提取数字,并重新命名为P<digits>.txt。而不是就地重命名的,它的安全复制文件,重命名飞,到目标目录:

$ mkdir -p /path/to/targetdir 
$ find . -name '*.txt' -exec bash -c 'digits=$(sed -n "1{s/[^0-9]//g;p;}" "$1"); cp "$1" "/path/to/targetdir/$newname"' _ {} \; 

通过执行短bash脚本:

#!/bin/bash 
digits=$(sed -n "1{s/[^0-9]//g;p;}" "$1") 
cp "$1" "/path/to/targetdir/$newname" 

find找到的每个文件(并且作为第一位置参数给出,$1)。

+0

执行,请让你的文件的副本,只有试试这件复印件,并确保你有与之前相同的文件数量,因为有可能两个文件可能以相同的名称结尾,而您将用第二个文件覆盖第一个文件。这可能是一个想法,在“mv”之前检查目标文件的存在,如果目标文件存在,则拒绝执行“mv”。 –

+0

好点的@MarkSetchell将会解决。 – randomir

+0

sed命令接收错误:'p命令结尾的额外字符'。 – protasm

1
find . -maxdepth 1 -regex '[^P].*\.txt' -exec \ 
    sed -n "1 s|§ \([0-9]*\)\.\([0-9a-z-]*\) |mv '{}' P\1\2.txt|p" '{}' \ 
    \; 

产生像

mv './file.txt' P6010-a.txt 

一个shell脚本,你可以查看并通过附加| sh

相关问题