【问题标题】:Rename with pattern用图案重命名
【发布时间】:2013-08-27 02:40:43
【问题描述】:

我有很多这样的文件:

"THIS IS my file.txt"
"THIS IS My file.txt"
"THIS IS m file.txt"
"THIS IS M file.txt"

所以基本上,如果我尝试描述它,文件名由两部分组成,一个大写,另一个小写(尽管第二部分的第一个字母也可以大写)。单词可以由一个字符组成。当有选择时,大写的单个字符的单词被认为是第一部分。

我想提取文件名的第一部分,由大写单词组成,将它们转换为小写(只有第一个字母为大写),然后用连字符将其与其余部分隔开。

所以我期待的结果是:

"This Is - my file.txt"
"This Is - My file.txt"
"This Is - m file.txt"
"This Is M - file.txt"

到目前为止我所拥有的是:

rename 's/^(([A-Z]{2,}| )+)(.*)/\u\L$1\E - $3/g' *

但它有不少问题(一个字母大写单词不匹配,只有第一个单词大写)。

【问题讨论】:

  • Perl rename 函数不是这样工作的。根据doc,重命名需要两个参数,oldname,newname。你有两个问题需要解决:1)找出分裂应该发生在哪里; 2)更改大小写并插入连字符。我建议你一开始就分开处理。
  • @JimGarrison 我怀疑他在谈论 linux 中的rename 命令行工具。
  • 对不起,我没有使用 perl 的 rename 功能,而是 linux 中可用的 rename 实用程序。然而,根据其手册页,它使用 perl 正则表达式。是的,我的第一个问题是如何使用正则表达式模式匹配将它们分开,正如我上面所说的,我没有为一个字母单词这样做。
  • 你想要什么THIS is my file.txt;大概是This - is my file.txt?所以不需要两个大写的词——或者这是一个要求。
  • 你是对的。结果应该是This - is my file.txt。只有大写的单词要小写(第一个字符除外)。字数无关紧要。

标签: regex perl rename


【解决方案1】:

我认为您正在寻找的正则表达式是:

s/^((?:[A-Z]+ )+)/(join " ", map ucfirst, split " ", lc $1) . " - "/e

我是这样测试的:

$ perl -pe 's/^((?:[A-Z]+ )+)/(join " ", map ucfirst, split " ", lc $1) . " - "/e' <<eoq
THIS IS my file.txt
THIS IS My file.txt
THIS IS m file.txt
THIS IS M file.txt
eoq

这是输出:

This Is - my file.txt
This Is - My file.txt
This Is - m file.txt
This Is M - file.txt

【讨论】:

  • 是的,它似乎工作!愿意解释一下吗?我不知道我可以在正则表达式中执行函数等......
  • 正则表达式末尾的 /e 标志表示替换值是一个应该被评估的 perl 表达式,而不仅仅是插值。
  • (谢谢,但我的意思是解释正则表达式的内容)。不知道“?:, join, map, ucfirst, split, lc, e”是什么意思。
  • ?: 只是告诉正则表达式引擎不要捕获该组的值,这不是绝对必要的。
  • join、map、ucfirst、split 和 lc 是 Perl 函数,参见:perldoc.perl.org/perlfunc.html#Perl-Functions-by-Category
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2017-11-26
  • 1970-01-01
  • 2015-03-17
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多