一、问题

问题很简单,看下面一段tmp.sh代码:

#!/bin/sh
x="this is the initial value of x"
cat /tmp/tmp | while read line;do
x="$line"
echo $x
done
echo x = $x

/tmp/tmp的内容

1,a

执行 ./tmp.sh,正常x变量是蓝色的“1,a”,但是实际的结果却是红色部分:

[qiu.li@l-tdata1.tkt.cn6 ~]$ ./tmp.sh
1,a
x = this is the initial value of x

问题很明显,变量x在while内修改之后,并没有带到外面来,为什么哪?

二、答案

经过几经查找,终于发现问题的原因:是因为启动了子进程,而变量x在子进程修改之后,并没有带入到父进程。原文如下:

This is because in the Bourne shell redirected control structures run in a subshell, so the value of x only gets changed in the  subshell, and is lost when the loop ends.

In other shells the same result may be seen because of the way pipelines are handled. In shells other than ksh (not pdksh) and zsh elements of a pipeline are run in subshells. In ksh and zsh, the last element of the pipeline is run in the current shell.

An alternative for non-Bourne shells is to use redirection
instead of the pipeline

如何解决哪?

1、一般方法:

#!/bin/sh
x="this is the initial value of x"
while read line;do
x="$line"
echo $x
done < /tmp/tmp
echo x = $x

运行:

[qiu.li@l-tdata1.tkt.cn6 ~]$ ./tmp.sh
1,a
x = 1,a

2、优雅一些的解决方法:

#!/bin/sh
x="this is the initial value of x"
exec <& # save stdin 将标准输入重定向到文件描述符3
exec < /tmp/tmp # 输入文件
while read line; do
x=$line
echo $x
done
exec <& # restore stdin
echo x = $x

上面使用的方法是:使用重定向代替子shell,从而可以在外面获取while里面的变量值。

参考:http://www.cnblogs.com/liqiu/p/4107948.html

shell while内获取外部变量内容的更多相关文章

  1. PHP 闭包获取外部变量和global关键字声明变量的区别

    最近在学习workerman的时候比较频繁的接触到回调函数,使用中经常会因为worker的使用方式不同,会用这两种不同的方式去调用外部的worker变量,这里就整理一下PHP闭包获取外部变量和glob ...

  2. awk获取外部变量

    语法 awk [ -F re] [parameter...] ['pattern {action}' ] [-f progfile][in_file...] 获得普通外部变量 [xingxing.dx ...

  3. 【shell】awk引用外部变量

    在使用awk的过程中,经常会需要引用外部变量,但是awk需要使用单引号将print包起来,导致print后的$引用无效,可以采用下面的方式 例如: #!/bin/bash a="line1 ...

  4. awk内置函数、外部变量

    外部变量 ①获取外部变量 格式: awk '{action}' 变量名=变量值 ,这样传入变量可以在action中获得值. 示例: test='awk test'--day-5 外部变量 ①获取外部变 ...

  5. FileReader对象异步获取外部文件的内容

    1.在网页表单中,定义input的type为file,就可以打开存储在计算机上的文件. <!DOCTYPE html> <head> <meta charset=&quo ...

  6. python 获取系统环境变量 os.environ and os.putenv

    从一段code说起 “if "BATCH_CONFIG_INI" in os.environ:” 判断环境变量的值有没有定义 如果定义的话就去环境变量的值,否则就取当前目录下的co ...

  7. shell的内建命令和外部命令

    shell的内建命令和外部命令 Shell执行的命令可以分为内建命令(built-in)和外部命令(external),前者是构建在shell内部:后者是一个独立的文件(可以是二进制文件,也可以是一个 ...

  8. Bean Shell常用内置变量总结

    JMeter在它的BeanShell中内置了变量,用户可以通过这些变量与JMeter进行交互,其中主要的变量及其使用方法如下: log:写入信息到jmeber.log文件,使用方法:log.info( ...

  9. (未完成)在block内如何修改block外部变量

    变量必须用__block修饰,否则编译不通过 block内部会把变量拷贝到堆区 变量从栈区copy->堆区 通过对对象取地址,打印出对象在内存中的地址 &a block不允许修改外部变量 ...

随机推荐

  1. 《剑指offer》-青蛙跳台阶II

    一只青蛙一次可以跳上1级台阶,也可以跳上2级--它也可以跳上n级.求该青蛙跳上一个n级的台阶总共有多少种跳法. 其实题目很水...就是一个等比数列通项公式嘛 f(0)=1 f(1)=1 f(n)=f( ...

  2. JS高级 - 面向对象1(this,Object ,工厂方式,new )

    面向对象三要素: 封装 继承 多态 1.this 详解,事件处理中this的本质 window this -- 函数属于谁 <script type="text/javascript& ...

  3. sql分组获取第一条或者最小一条值

    很多人都在问这个问题,现在记录一下 select id from test as a where id = (select min(b.id ) from test as b where a.pid ...

  4. 快速定位 Android APP 当前页面的三种方法(Activity / Fragment)

    方法一.通过adb命令打印当前页面: Android 如何快速定位当前页面是哪个Activity or Fragment (1)查看当前Activity :adb shell "dumpsy ...

  5. 大数据统计分析平台之二、ElasticSearch 6.2.1的安装与使用

    # 下载文件cd /usr/local/software wget https://artifacts.elastic.co/downloads/elasticsearch/elasticsearch ...

  6. day5模块学习--re正则模块

    1. 正则表达式基础 1.1. 简单介绍 正则表达式并不是Python的一部分.正则表达式是用于处理字符串的强大工具,拥有自己独特的语法以及一个独立的处理引擎,效率上可能不如str自带的方法,但功能十 ...

  7. 被忽视的META标签之特效(页面过渡效果)

    在web设计中使用js可以实现很多的页面特效,然而很多人却忽视了HTML标签中META标签的强大功效,其实meta标签也可以实现很多漂亮的页面过渡效果. META标签是HTML语言HEAD区的一个辅助 ...

  8. BZOJ2333 [SCOI2011]棘手的操作 堆 左偏树 可并堆

    欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - BZOJ2333 题意概括 有N个节点,标号从1到N,这N个节点一开始相互不连通.第i个节点的初始权值为a[i ...

  9. 8.Django-form组件

    1.form组件的校验功能 文件formsdemo models from django.db import models # Create your models here. class UserI ...

  10. java中与和或的注意点

    1.&&和&的区别 &:无论左边是true是false.右边都运算. &&:当左边为false时,右边不运算. 2.|与||的区别 |:两边都参与运算. ...