我试图删除string中的部分path。 我有path:
/path/to/file/drive/file/path/
我想删除第一部分/path/to/file/drive
并产生输出:
file/path/
注意:我在while循环中有几条path,在它们中都有相同的/path/to/file/drive
,但我只是想find如何去除所需的string。
我find了一些例子,但我无法让他们工作:
echo /path/to/file/drive/file/path/ | sed 's:/path/to/file/drive:\2:' echo /path/to/file/drive/file/path/ | sed 's:/path/to/file/drive:2'
\2
作为string的第二部分,我显然做错了什么…也许有一个更简单的方法?
你也可以使用POSIX shell变量扩展来做到这一点。
path=/path/to/file/drive/file/path/ echo ${path#/path/to/file/drive/}
当变量被展开时, #..
部分剥离了一个主要的匹配字符串; 如果你的字符串已经在shell变量中,比如你正在使用for
循环,这个特别有用。 你可以使用%...
从变量的末尾去掉匹配的字符串(例如一个扩展名)。 见bash
手册页的血淋淋的细节。
如果你想删除一定数量的路径组件,你应该使用-d'/'
cut
。 例如,如果path=/home/dude/some/deepish/dir
:
要删除前两个组件:
# (Add 2 to the number of components to remove to get the value to pass to -f) $ echo $path | cut -d'/' -f4- some/deepish/dir
保留前两个组件:
$ echo $path | cut -d'/' -f-3 /home/dude
删除最后两个组件( rev
反转字符串):
$ echo $path | rev | cut -d'/' -f4- | rev /home/dude/some
要保留最后三个组件:
$ echo $path | rev | cut -d'/' -f-3 | rev some/deepish/dir
或者,如果你想删除特定组件之前的所有内容, sed
将会工作:
$ echo $path | sed 's/.*\(some\)/\1/g' some/deepish/dir
或者在特定组件之后:
$ echo $path | sed 's/\(dude\).*/\1/g' /home/dude
如果你不想保留你指定的组件,这更容易:
$ echo $path | sed 's/some.*//g' /home/dude/
如果你想保持一致,你可以匹配最后的斜线:
$ echo $path | sed 's/\/some.*//g' /home/dude
当然,如果你匹配几个斜线,你应该切换sed
分隔符:
$ echo $path | sed 's!/some.*!!g' /home/dude
请注意,这些示例都使用绝对路径,您将不得不四处使用它们来处理相对路径。
如果你不想硬编码你要删除的部分:
$ s='/path/to/file/drive/file/path/' $ echo ${s#$(dirname "$(dirname "$s")")/} file/path/
一个方法与sed做到这一点是
echo /path/to/file/drive/file/path/ | sed 's:^/path/to/file/drive/::'
使用邪恶奥托建议的${path#/path/to/file/drive/}
肯定是这样做的典型/最好的方式,但是因为有很多sed的建议,值得指出的是,如果你是sed使用固定的字符串。 你也可以这样做:
echo $PATH | cut -b 21-
丢弃前20个字符。 同样,您可以在bash中使用${PATH:20}
或在zsh中使用$PATH[20,-1]
。
如果要删除路径的前N个部分 ,那么当然可以使用N个调用basename
,如在glenn的答案中 ,但使用globbing可能更容易:
path=/path/to/file/drive/file/path/ echo "${path#*/*/*/*/*/}" # file/path/
具体而言, ${path#*/*/*/*/*/}
表示“return $path
减去包含5个斜杠的最短前缀” 。