我的脚本将接收各种长度的输入,我想删除由“/”分隔的最后一个字段。我将要处理的输入的一个示例是。
this/that/and/more
但是我遇到的问题是输入的长度会像这样变化:
this/that/maybe/more/and/more
or/even/this/could/be/it/and/maybe/more
short/more
无论如何,预期的输出应该是整个字符串减去最后一个“/more”。
注意:“更多”一词不会是一个常数,这些都是任意的例子。
输入示例:
this/that/and/more
this/that/maybe/more/and/more
预期输出:
this/that/and
this/that/maybe/more/and
我所知道的适用于你知道其长度的字符串
cut -d'/' -f[x]
我需要的是一个以“/”分隔的 AWK 命令,我假设如下:
awk '{$NF=""; print $0}'
根据要求使用 awk:
$ awk '{sub("/[^/]*$","")} 1' file
this/that/maybe/more/and
or/even/this/could/be/it/and/maybe
short
但这是 sed 最适合的工作类型:
$ sed 's:/[^/]*$::' file
this/that/maybe/more/and
or/even/this/could/be/it/and/maybe
short
以上是针对此输入文件运行的:
$ cat file
this/that/maybe/more/and/more
or/even/this/could/be/it/and/maybe/more
short/more
根据您在脚本中的输入方式,bash 的 Shell 参数扩展可能会很方便:
$ s1=this/that/maybe/more/and/more
$ s2=or/even/this/could/be/it/and/maybe/more
$ s3=short/more
$ echo ${s1%/*}
this/that/maybe/more/and
$ echo ${s2%/*}
or/even/this/could/be/it/and/maybe
$ echo ${s3%/*}
short
(有关参数扩展的更多信息,请访问 https://www.gnu.org/software/bash/manual/html_node/Shell-Parameter-Expansion.html)
在脚本中,您可以创建一个循环,如果输入字符串中的最后一个字符不是每次迭代中的斜杠,则删除该循环。然后,当循环找到斜杠字符时,退出循环,然后删除最后一个字符(应该是斜杠)。
伪代码:
while (lastCharacter != '/') {
removeLastCharacter();
}
removeLastCharacter(); # removes the slash
(抱歉,我已经有一段时间没有写 bash 脚本了。)
另一种
awk
使用字段代替正则表达式的替代方案
awk -F/ '{printf "%s", $1; for (i=2; i<NF; i++) printf "/%s", $i; printf "\n"}'
这是另一种 shell 解决方案:
while read -r path; do dirname "$path"; done < file
知道
NF
存储当前记录的字段数
$ awk -F/ '{print NF, $NF}' <<< "a/b/c/d/e"
5 e
但是
NF
实际上可以写成:
$ awk -F/ -vOFS=/ '{NF=NF-1; print NF; print $NF; print $0}' <<< "a/b/c/d/e"
4
d
a/b/c/d
我认为它是一个优雅的解决方案(使用
mawk
和 gawk
进行测试)。