【linux shell】while read line几种方法以及区别(有大坑)

引言:开始时自己的写的一个下载某个bing网站上面的图片的脚本程序中需要使用while read line读取自己提取出来的图片信息,刚开始没有用临时文件存放信息,而是直接使用管道机制重定向,结果…坑了我一个小时
然后自己查了一些资料,比较一下三种while read line方法的区别
首先自己的test文件如下:(就简单是三行数据)
在这里插入图片描述

1.形如cat test | while read line;do echo $line;done

  • 代码如下
name1="xiaowang"
date1="2020-05-08"
cat test | while read date
do
    read url
    read name
    name1="$name"
    date1="$date"
    echo "$date1 $name1 $url"
    echo "$date $name $url"
done

echo "888888 $date1 777 $name1 666  $url"
  • 结果输出
2020-05-07 https://bing.ioliu.cn/photo/WildflowerWeek_ZH-CN4593499387?force=download 印克斯湖国家公园中的德克萨斯矢车菊,德克萨斯州
2020-05-07 https://bing.ioliu.cn/photo/WildflowerWeek_ZH-CN4593499387?force=download 印克斯湖国家公园中的德克萨斯矢车菊,德克萨斯州
888888 2020-05-08 777 xiaowang 666

我想的是使用while read line读取文件之后赋值给name1和date1,结果并没赋值。刚开始很疑惑,明明在while循环中的name1和date1都赋值了为啥退出之后没了呢,结果发现是管道的机制,这个使用管道之后while read line是在子shell中进行的,所以在退出while之后其中的操作都是无效的

另外,参考一片博客中说的:cat test会一次性将test文件所有数据装入内存,如果test文件足够大,会直接占用巨量内存

2.形如 while read line
  • 代码如下
name1="xiaowang"
date1="2020-05-08"
while read date < test
do
    read url
    read name
    name1="$name"
    date1="$date"
    echo "$date1 $name1 $url"
    echo "$date $name $url"
done

echo "888888 $date1 777 $name1 666  $url"
  • 结果如下
   

2020-05-07  
2020-05-07  


2020-05-07  
2020-05-07  


2020-05-07  
2020-05-07  
...

首先我看不懂这个输出结果(其中的空行全是我自己按的回车,也就是按了两次回车之后才出现结果,然后这个while循环一直不结束…)查说法就是:它会在每次循环的时候都重新打开test文件,使得每次都从头开始读数据,而不是每次从上一次标记的地方继续读数据。

3.【最佳】形如while read line;do echo $line;done
  • 代码如下
name1="xiaowang"
date1="2020-05-08"
while read date
do
    read url
    read name
    name1="$name"
    date1="$date"
    echo "$date1 $name1 $url"
    echo "$date $name $url"
done < test

echo "888888 $date1 777 $name1 666  $url"
  • 结果如下(正常了耶)
2020-05-07 https://bing.ioliu.cn/photo/WildflowerWeek_ZH-CN4593499387?force=download 印克斯湖国家公园中的德克萨斯矢车菊,德克萨斯州
2020-05-07 https://bing.ioliu.cn/photo/WildflowerWeek_ZH-CN4593499387?force=download 印克斯湖国家公园中的德克萨斯矢车菊,德克萨斯州
888888 2020-05-07 777 https://bing.ioliu.cn/photo/WildflowerWeek_ZH-CN4593499387?force=download 666  印克斯湖国家公园中的德克萨斯矢车菊,德克萨斯州

这个不就是我想要的结果吗,使用输入重定向的方式则每次只占用一行数据的内存,而且是在当前shell环境下执行的,while内的变量赋值、数组赋值在退出while后仍然有效。

总结

  1. 以上三种方法中,大家在选取的时候最好选择第三那种方法,别问为什么问。
  2. 其实读取文件内容的方法有很多,比如使用形如:for line in $(
  3. 另外如果想要了解我那个下载图片的脚本程序可以访问我的github

参考

https://www.cnblogs.com/xl-892694298/p/11017168.html
https://blog.csdn.net/u014650722/article/details/51563823

你可能感兴趣的:(linux,shell)