我有VBoxManage list vms
看起来像这样的输出:
"arch" {de1a1db2-86c5-43e7-a8de-a0031835f7a7}
"arch2" {92d8513c-f13e-41b5-97e2-2a6b17d47b67}
我需要获取名称arch
并将arch2
其保存到变量中。
我有VBoxManage list vms
看起来像这样的输出:
"arch" {de1a1db2-86c5-43e7-a8de-a0031835f7a7}
"arch2" {92d8513c-f13e-41b5-97e2-2a6b17d47b67}
我需要获取名称arch
并将arch2
其保存到变量中。
Answers:
这将解析这两个字符串的内容:
$ grep -o '".*"' somefile | sed 's/"//g'
arch
arch2
上面寻找与模式匹配的字符串".*"
。这将匹配双引号中出现的所有内容。因此grep
将返回以下类型的值:
"arch"
"arch2"
管道sed
将去除这些字符串中的所有双引号,从而为您提供所需的字符串。该符号sed 's/"//g'
指示sed
进行搜索并替换所有出现的双引号,并用\代替s/"//g
。该命令s/find/replace/g
在那里执行,g
搜索的结尾告诉它在给定的整个字符串上全局进行搜索。
您还可以sed
用来截断开始的双引号,保留它们之间的内容,并截去剩余的引号和之后的所有内容:
$ sed 's/^"\(.*\)".*/\1/' a
arch
arch2
$ grep -o '".*"' somefile | tr -d '"'
arch
arch2
该命令tr
可用于删除字符。在这种情况下,它将删除双引号。
$ grep -oP '(?<=").*(?=")' somefile
arch
arch2
使用grep
的PCRE功能,您可以查找任何以双引号开头或以双引号结尾的子字符串,并仅报告该子字符串。
/address/
到sed
像sed '/^"\(arch[^"]*\)/s//\1/
你只对包含该串线运营。
sed
确实应该这样做s/^"\([^"]*\)".*/\1/
,以防万一在线上只有两个双引号。
那是另一项工作cut
:
VBoxManage list vms | cut -d \" -f2
cut
使用引号作为分隔符将每一行拆分为多个字段,然后输出字段2:字段1是第一个引号之前的空字符串,字段2是引号之间的所需字符串,而字段3是其余的线。
有了sed
您就可以做到:
var=$(VBoxManage list vms | sed 's/^"\([^"]*\).*/\1/')
说明:
s/.../.../
-匹配并替换^
-在行首匹配\(...\)
-这是一个反向参考,我们可以稍后在这里参考匹配的内容 \1
[^"]*
-匹配任何不包含的序列"
(即直到下一个"
).*
-匹配其余部分\1
-替换为后面的参考或搭配awk
:
var=$(VBoxManage list vms | awk -F\" '{ print $2 }')
请注意,在现代Shell中,您也可以使用数组代替普通变量。在bash
你可以这样做:
IFS=$'\n'; set -f
array=( $(VBoxManage list vms | awk -F\" '{ print $2 }') )
echo "array[0] = ${array[0]}"
echo "array[1] = ${array[1]}"
当您开始使用该变量时,这可能会更容易。
还有一个通过grep oneliner --perl-regexp
选项提供的选项,
VBoxManage list vms | grep -oP '(?<=^\")[^"]*'
说明:
(?<=^\")[^"]*
->在这里使用后向。它匹配任何字符,但不匹配"
零次或多次(一旦找到双引号,它将停止匹配),该字符仅在双引号之后(仅以双引号开头的行)。
通过另一个丑陋的骇客sed
,
$ sed '/.*\"\(.*\)\".*/ s//\1/g' file
arch
arch2
tr -d \"
是删除引号的另一种方法。(tr
通常将一组字符转换为另一组;-d
告诉它只是删除它们。)