将定界输出读取到多个Bash变量中

时间:2018-08-25 01:18:21

标签: bash

这应该很简单,我以前在某个地方的脚本中完成过此操作,找不到我的示例(或等效示例),今天这个问题使我陷入精神错乱。 (即使我还没有包括脚本的其余部分,该脚本也只能在脚本内部使用,而不是交互式的。)

cat testfile | grep -e eth0

返回:

eth0         123.45.67.8/23                  u/u  Internet - Cable WAN

最终结果是我需要为每个元素设置变量。即就像我手动完成此操作一样:

INTF = "etho"
IPADDR = "123.45.67.8/23"
STS = "u/u"
DESC = "Internet - Cable WAN"

我认为我可以做类似的事情:

cat testfile | grep -e eth0 | awk '{print $2}' | xargs read IPADDR

cat testfile | grep -e eth0 | cut -d " " -n2 | read IPADDR

但是我尝试过的一切都没有带来欢乐。...我的路障(headblock)是什么?

要添加编辑-该脚本比仅仅获取一个IP还要复杂,正如我的例子所引导的那样。这是一个基于Cron的脚本,每分钟运行一次,它通过8个接口运行一个循环,并在某些警报条件下发送消息。当我使用硬编码的变量运行脚本时,脚本的其余部分都可以正常工作,我只是询问了困扰我的那一部分。

4 个答案:

答案 0 :(得分:4)

由于您要设置4个变量,因此不必像这样cut做4次,可以像这样使用read

#!/bin/bash
#
read INTF IPADDR STS DESC <<< $(cat testfile | grep -e eth0)

echo $INTF
echo $IPADDR
echo $STS
echo $DESC

这将使用默认的$IFS在任何空白处“剪切”。

如果您想从以下项中剪切值:“ aaa,bbb,ccc,ddd”,
您可以在read之前更改IFS值。

例如:

IFS="," read INTF IPADDR STS DESC <<< $(cat testfile | grep -e eth0)

答案 1 :(得分:2)

如果要使用read一次获得所有分配的变量,可以按以下步骤进行操作:

read INTF IPADDR STS DESC <<< `cat testfile | grep -e eth0`

答案 2 :(得分:0)

大量方法,甚至可以扫描测试文件并将结果一对一匹配地放入数组:

#!/bin/bash
file="testfile.txt"

declare -a intf
declare -a ipaddr
declare -a sts
declare -a desc

# - file reader -
while IFS= read -r line; do
    if [[ ${line,,} == *"intf"* ]];then
        intf+=("$(echo $line | cut -d'"' -f2- | cut -d'"' -f1)")
    elif [[ ${line,,} == *"ipaddr"* ]];then
        ipaddr+=("$(echo $line | cut -d'"' -f2- | cut -d'"' -f1)")
    elif [[ ${line,,} == *"sts"* ]];then
        sts+=("$(echo $line | cut -d'"' -f2- | cut -d'"' -f1)")
    elif [[ ${line,,} == *"desc"* ]];then
        desc+=("$(echo $line | cut -d'"' -f2- | cut -d'"' -f1)")
    fi
done < "$file"

if [[ ${#intf[@]} -eq  ${#ipaddr[@]} &&  ${#intf[@]} -eq ${#ipaddr[@]} &&  ${#intf[@]} -eq  ${#sts[@]} ]] ;then
    echo "file read successful! continuing .."
else
    echo "icky, this didn't work"
fi

for ((i=0; i< ${#intf[@]}; i++)) ;do
       echo -e "INTF=${intf[$i]} \nIPADDR=${ipaddr[$i]} \n"

done

输出(类似):

$ ./script.sh
file read successful! continuing ..
INTF=etho 
IPADDR=123.45.67.8/23 

INTF=etho 
IPADDR=13.45.67.8/23 

INTF=etho 
IPADDR=23.45.67.8/23 

答案 3 :(得分:0)

在您的命令中

cat testfile | grep -e eth0 | cut -d " " -n2 | read IPADDR
cat testfile | grep -e eth0 | awk '{print $2}' | xargs read IPADDR

read命令在子Shell中运行,它对主Shell不可见。

您需要process substitution才能将这些值一目了然地放入父外壳:

read -r intf ipaddr sts desc < <(grep eth0 testfile)

前三个变量将获取grep输出中前三个字段的值(基于IFS进行字符串拆分),而第四个变量desc将在输出中获取其余标记。


顺便说一句,cat outfile | grep -e eth0UUOC的情况。只要grep eth0 outfile就能做好工作。


相关: