Unix shell 脚本:将文件中的值分配给 while 循环中的变量,并在循环外使用该值

发布于 2024-10-05 04:11:42 字数 957 浏览 0 评论 0原文

我正在编写一个 shell 脚本,我必须在其中提取以下类型的文件的内容:

类型1|值A
类型2|值B
类型1|值C
类型2|值D
类型3|值E
....
类型n|值Z。

对于 column_1 中的每种类型,我都有一个目标变量,它将相同类型的值连接起来,以获得如下结果:

var1=值A,值C
var2=值B,值D
var3=值E
......

脚本实现了这样的东西:

var1="HELLO"  
var2="WORLD"  
...  
cat $file | while read record; do  
   #estract column_1 and column_2 from $record    
if [ $column_1 = "tipo1" ]; then  
   var1="$var1, column_2"  ## column_2 = valueB
elif ....  
....  
fi  
done

但是当我尝试使用链接column_2的任何变量的值时:

    echo "$var1 - $var2"   

我得到原始值:

    HELLO - WORLD.    

搜索互联网,我读到问题与管道创建一个复制实际值的子 shell 相关。

有办法解决这个问题吗!

最重要的是,有一种方法适合所有类型的 shell,事实上,这个脚本必须在不同的 shell 上运行!? 我不想使用文件支持来写入部分结果。

I'm writing a shell script, where I have to extract the contents of a file which is of type:

type1|valueA
type2|valueB
type1|valueC
type2|valueD
type3|valueE
....
typen|valueZ.

For each type in column_1, I have a target variable, which concatenates the values of the same type, to get a result like this:

var1=valueA,valueC
var2=valueB,valueD
var3=valueE
.....

Script implements something like this:

var1="HELLO"  
var2="WORLD"  
...  
cat $file | while read record; do  
   #estract column_1 and column_2 from $record    
if [ $column_1 = "tipo1" ]; then  
   var1="$var1, column_2"  ## column_2 = valueB
elif ....  
....  
fi  
done

But when I try to use the value of any of the variables where I chained column_2:

    echo "$var1 - $var2"   

I get the original values:

    HELLO - WORLD.    

Searching the internet, I read that the problem is related to the fact that the pipeline creates a subshell where the actual values are copied.

Is there a way to solve this problem!?

Above all, there is a way that would fit for all types of shells, in fact, this script must run potentially on different shells!?
I do not want to use file support on which to write the partial results.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

鸠书 2024-10-12 04:11:42

您不需要使用cat。将某些内容通过管道传送到 while 中会创建一个子 shell。当子 shell 退出时,循环中设置的变量值将丢失(另一个示例是使用 cd 进行目录更改。相反,您应该将文件重定向到 done:

while condition
do
    # do some stuff
done < inputfile

顺便说一下,

while read record

你可以这样做:

while IFS='|' read -r column1 column2

You don't need to use cat. Piping something into while creates a subshell. When the subshell exits, the values of variables set in the loop are lost (as would be directory changes using cd as another example. Instead, you should redirect your file into the done:

while condition
do
    # do some stuff
done < inputfile

By the way, instead of:

while read record

you can do:

while IFS='|' read -r column1 column2
黎夕旧梦 2024-10-12 04:11:42

内线:

for a in `awk "-F|" '{print $1;}' test | sort -u` ; do echo -n "$a =" ; grep -e "^$a" test | awk "-F|" '{ printf(" %s,", $2);}' ; echo "" ; done

Oneliner:

for a in `awk "-F|" '{print $1;}' test | sort -u` ; do echo -n "$a =" ; grep -e "^$a" test | awk "-F|" '{ printf(" %s,", $2);}' ; echo "" ; done
爱*していゐ 2024-10-12 04:11:42

使用 awk

awk '{a[$1]=a[$1]==""?$2:a[$1] OFS $2}
END{for (i in a) print i"="a[i]}' FS=\| OFS=, file  

type1=valueA,valueC
type2=valueB,valueD
type3=valueE

Using awk

awk '{a[$1]=a[$1]==""?$2:a[$1] OFS $2}
END{for (i in a) print i"="a[i]}' FS=\| OFS=, file  

type1=valueA,valueC
type2=valueB,valueD
type3=valueE
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文