我最近在 Mac OS 10.7 (Lion) 上使用 XLD 将我所有的 FLAC 文件转换为 44.1 kHz 的较低采样率和 24 位的位深度(因为 iPhone/iPod 不支持以上任何内容)。
虽然我告诉 XLD 覆盖所有以前的文件,但 XLD(1)在非常文件的末尾附加了一个像 from
some_song.m4a
Run Code Online (Sandbox Code Playgroud)
到
some_song(1).m4a
Run Code Online (Sandbox Code Playgroud)
所以现在我想(1)从我转换的所有 FLAC 文件中删除它。
我知道我可以使用一些程序甚至 AppleScript 来重命名文件,但我想学习使用老派的命令行方式。
我知道这find . -name *\(1\).m4a会抓取所有转换后的 FLAC 文件。
接下来,我知道我必须做的东西-exec和mv重命名所有找到的文件。但我想不通的是如何保留原始文件名并只删除(1).
也许我需要做一些组正则表达式捕获来存储我不想修改的文件名部分?或者也许不可能在一行中完成所有事情,我应该创建一个 shell 脚本(我不太喜欢这样做,但我愿意尝试一下)。
欢迎任何提示或建议!谢谢!
是否有任何在线 grep 教程可以提供一些用于执行练习的在线工具?例如,有一些预定义的文本样本并被告知要查找什么模式等等?对于在可预测的环境中实际学习 grep 来说,这将是一个非常有用的工具。
您可能已经知道,Bash RegEx 引擎不支持现代 RegEx 引擎支持的许多功能(反向引用、环视断言等)。以下是我刚刚创建的一个简单的 Bash 脚本,试图解释我的最终目标是什么:
#!/bin/bash
# Make sure exactly two arguments are passed.
if [ $# -lt 2 ]
then
echo "Usage: match [string] [pattern]"
return
fi
variable=${1}
pattern=${2}
if [[ ${variable} =~ ${pattern} ]]
then
echo "true"
else
echo "false"
fi
Run Code Online (Sandbox Code Playgroud)
因此,例如,类似以下命令的内容将返回 false:
. match.sh "catfish" "(?=catfish)fish"
Run Code Online (Sandbox Code Playgroud)
而完全相同的表达式在 Perl 或 JavaScript 正则表达式测试器中使用时会找到匹配项。
反向引用(例如 (expr1)(expr2)[ ]\1\2)也不会匹配。
我得出的结论是,只有强制 bash 使用与 Perl 兼容的 RegEx 引擎才能解决我的问题。这是可行的吗?如果是这样,我将如何执行该程序?
我在当前路径有 3 个目录。
$ls
a_0db_data a_clean_0db_data a_clean_data
$ls a_*_data
a_0db_data:
a_clean_0db_data:
a_clean_data:
$ls a_[a-z]*_data
a_clean_0db_data:
a_clean_data:
Run Code Online (Sandbox Code Playgroud)
我希望最后一个 ls 命令只匹配a_clean_data. 为什么它也匹配包含0?
bash --version
GNU bash, version 4.2.24(1)-release (i686-pc-linux-gnu)
Run Code Online (Sandbox Code Playgroud) 我有一个像这样的字符串rev00000010,我只想要最后一个数字,在这种情况下是 10。
我试过这个:
TEST='rev00000010'
echo "$TEST" | sed '/^[[:alpha:]][0]*/d'
echo "$TEST" | sed '/^rev[0]*/d'
Run Code Online (Sandbox Code Playgroud)
我有
输入:
NISHA =\455
Run Code Online (Sandbox Code Playgroud)
输出:
NISHA = 455
Run Code Online (Sandbox Code Playgroud)
我想\从输出中删除。我尝试使用命令sed "s/[\]//g" P但它不起作用并且它标记了一个错误:
character found after backslash is not meaningful
Run Code Online (Sandbox Code Playgroud) 我的电脑运行的是 macOS 10.12.3,我使用的是系统安装的grep2.5.1-FreeBSD 版实用程序。
这些是我在测试各种正则表达式时得到的输出:
但是如果我使用 GNU grep(2.25 版)运行这些,我会得到以下信息:
GNU 的 grep 在我看来是正确的,而 BSD 的不正确,不是吗?他们为什么不同?我不明白为什么 BSD 的 grep 当正则表达式指定它必须跟在行的开头时匹配“a”。
在使用 时sed,我经常创建相当复杂和错综复杂的正则表达式,我需要在一个文件中匹配两次。有没有办法让我保存这个正则表达式并只引用它两次?
也许看起来像这样的东西?
sed ' complicated_regex=/^(([a-f0-9]{32})+([a-zA-Z0-9=]{{$i}})?)+$/
s/complicated_regex:complicated_regex/simple-output/
' my_file
Run Code Online (Sandbox Code Playgroud)
更新:一个答案提出了使用 bash 变量的解决方案。这不起作用。给定一个test.txt.
#test.txt
foo bar
bar foo
Run Code Online (Sandbox Code Playgroud)
还有剧本
#!/bin/bash
VALUE='foo \([a-z]\+\)'
sed 's/"${VALUE}"/foo happy \1/' test.txt
Run Code Online (Sandbox Code Playgroud)
这应该产生输出
foo happy bar
bar foo
Run Code Online (Sandbox Code Playgroud)
但相反,我得到了错误
sed: -e expression #1, char 24: invalid reference \1 on `s' command's RHS
Run Code Online (Sandbox Code Playgroud) 我想使用sed或perl替换前面没有某个词的所有出现的词。
例如,我有一个包含电影情节的文本文件,我想用他们的名字替换所有出现的角色姓氏,但前提是他们的名字不紧跟在他们的姓氏之前。
示例文本可能如下所示:
John Smith and Jane Johnson talk about Smith's car.
Run Code Online (Sandbox Code Playgroud)
我希望它看起来像这样:
John Smith and Jane Johnson talk about John's car.
Run Code Online (Sandbox Code Playgroud)
如果我只是这样做sed 's/Smith/John/' file,那么我会:
John John and Jane Johnson talk about John's car.
Run Code Online (Sandbox Code Playgroud)
姓氏之前的名字将始终相同。我不必处理John Smith和Frank Smith。我只需要一种方法来匹配Smith它John前面没有的。
“有效的 awk 编程”一书中有一个关于字段拆分的示例。这是示例:
如果您希望字段由文字句点后跟任何单个字符分隔,请使用
‘FS = "\\.."’.
为什么是双反斜杠?不应该\..吗?