Linux Unix shell 脚本:将文件中的值赋给变量到 while 循环中,并在循环外使用此值
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/4304390/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Unix shell scripting: assign value from file to variable into while loop, and use this value outside the loop
提问by sangi
I'm writing a shell script, where I have to extract the contents of a file which is of type:
我正在编写一个 shell 脚本,我必须在其中提取以下类型的文件的内容:
type1|valueA
type2|valueB
type1|valueC
type2|valueD
type3|valueE
....
typen|valueZ.
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:
对于 中的每种类型column_1
,我都有一个目标变量,它连接相同类型的值,以获得如下结果:
var1=valueA,valueC
var2=valueB,valueD
var3=valueE
.....
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
:
但是当我尝试使用我链接的任何变量的值时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.
在互联网上搜索,我读到问题与管道创建了一个子shell 来复制实际值有关。
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.
最重要的是,有一种方法可以适用于所有类型的 shell,事实上,这个脚本必须可能在不同的 shell 上运行!?我不想使用文件支持来写入部分结果。
回答by Ignacio Vazquez-Abrams
回答by Didier Trosset
Oneliner:
单线:
for a in `awk "-F|" '{print ;}' test | sort -u` ; do echo -n "$a =" ; grep -e "^$a" test | awk "-F|" '{ printf(" %s,", );}' ; echo "" ; done
回答by Paused until further notice.
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
:
您不需要使用cat
. 将某些东西放入管道中while
会创建一个子外壳。当子shell退出时,循环中设置的变量值将丢失(cd
作为另一个示例的目录更改也会丢失。相反,您应该将文件重定向到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
回答by BMW
Using awk
使用 awk
awk '{a[]=a[]==""?:a[] OFS }
END{for (i in a) print i"="a[i]}' FS=\| OFS=, file
type1=valueA,valueC
type2=valueB,valueD
type3=valueE