2013-09-30 47 views
5

我试图从某个目录中的所有文件中删除特定单词列表,并将其替换为空白。从文件名中删除单词列表

所以:

这真棒内容的720p BLAH FOO BANG OOO - 30.9.2013.mp4

变为:

这真棒内容 - 30.9.2013.mp4

现在下面的工程对单翅d并替换一个词。

find path/to/folder/ -maxdepth 3 -name '*.*' -execdir bash -c 'mv -i "$1" "${1//foo/}"' bash {} \; 

我也尝试了多次发现,但这似乎是一个很长的做法,我似乎遇到这样的问题。

几个问题,我有:

  • 希望它是不区分大小写
  • 极品“$ {1个//富/}”来指代一个列表,如果大于
  • 删除空格1

试图在cronjob上将其作为bash脚本运行。

除非有更好的方法来删除“This Awesome Content” - “30.9.2013.mp4”之间的所有内容。

非常感谢。

回答

4

您可以使用'echo'命令将文件的名称作为变量来访问。完成之后,进行所需更改的最有效方法是使用'sed'。您可以使用'-e'标志将sed命令串起来。作为bash for循环的一部分,这一行为您提供了一个开始。你也可以使用这样的一行来作为你的'find'语句的一部分。

echo $fyle | sed -e 's/FOO//gI' -e 's/BANG//gI' 

一旦你有你想要的文件名,你可以将它们移回原来的名称。让我知道你是否需要更具体的指示。

更新:这是一个更完整的解决方案。你必须调整脚本到您自己的文件名等

for fyle in $(find . -name "*.*") 
do 
    mv -i $fyle `echo $fyle | sed -e 's/FOO//gI' -e 's/BANG//gI' ` 
done 

最后,用一个空格字符替换多个空格字符,你可以添加其他sed命令。这是一个工作指令:

echo "file input.txt" | sed 's/ */ /g' 
+0

似乎我是一个完整的newb。我将如何实现这个到我的find命令中,替换mv命令?另外如果我把我加到-e's/FOO // g',例如-e'/ FOO // Ig'会忽略大小写敏感性。 – Keelan

+1

要使sed不区分大小写,请在末尾添加gI。我更新了我的帖子。 – philshem

+1

我已经添加了更完整的解决方案。请让我知道它是如何为你工作的。 – philshem

3

一种方式做,这将增加在那里你生成mv命令的文件来实现这一目标的一个中间步骤,然后执行该文件。我假设你有一个文件包含你不想要的单词。

cd文件夹开始

# Create list of valid <file>s in file_list, and list of "mv <file> " commmands 
# in cmd_file 
ls | grep -f words_file | tee file_list | sed 's/\(.*\)/mv "\1" /g' > cmd_file 

# Create the sed statements using the words_file, store it to sed_commands 
# Then, apply the sed commands to file_list 
sed 's/\(.*\)/s\/\1\/\/g/g' words_file > sed_commands 
sed -f sed_commands file_list > new_file_names 

# Combine cmd_file and new_file_names to produce the full mv statements 
paste cmd_file new_file_names > final_cmds 

# To verify the commands 
cat final_cmds 

# Finally, execute it 
sh final_cmds 

之前,这是我能想出的,它避免了手工编写sed -e每个字。不知道是否有更简单的方法使用常用的bash实用程序。当然,您可以使用perl或python并更简洁地编写它。

编辑:简化它,取消了eval和xargs。

+0

看起来不错,我如何指定一个文件夹? – Keelan

+0

当我运行这个“$ sed's /\(.*\)/ s \/\ 1 \/\/g'words_file> sed_commands”时出现错误----错误是: sed:-e expression #1,char 19:未终止's'命令 –

+0

@Keelan在开始之前cd到目录。 –

1

A 该任务的脚本。它接受至少有两个参数,第一个是单词从文件名称中删除列表,剩下的都是要处理的文件:

perl -MFile::Spec -MFile::Copy -e ' 
    $words = join(q{|}, split(q| |, shift)); 
    $words_re = qr{$words}i; 
    for $path (@ARGV) { 
     ($dummy, $dir, $f) = File::Spec->splitpath($path); 
     $f =~ s/$words_re//g; 
     $f =~ s/\s{2,}/ /g; 
     $newpath = File::Spec->catfile($dir, $f); 
     move($path, $newpath); 
     printf qq|[[%s]] renamed to [[%s]]\n|, $path, $newpath; 
    } 
' "720p BLAH FOO BANG OOO" tmp/user/*.mp4 

在我的测试我下面的输出:

[[tmp/user/This Awesome Content 720p BLAH FOO BANG OOO - 30.9.2013.mp4]] renamed to [[tmp/user/This Awesome Content - 30.9.2013.mp4]] 
+0

我根本不知道perl,所以我认为这可能超出了我的境界。我可以指定一个目录来搜索文件吗? – Keelan

+1

@Keelan:是的。但是然后使用替代命令是很危险的,因为可以修改部分路径。它需要修复才能使用模块。 – Birei

+0

噢好吧,我想我会保持清醒。 Perl吓坏了我。 – Keelan

0

prename可用于文件重命名部分。 stg类似的:

find ... -exec prename 's/(deleteme1|deleteme2|…)//g' {} \;