变量值在bash脚本中没有变化

时间:2017-10-27 15:43:37

标签: bash shell

运行以下代码:

a=one; echo $a
a=two echo $a
a=three echo $a >$a

结果

一个

一个

和一个名为&#34的创建文件;一个"内容"一个"

为什么变量在第2行没有变为two而在第3行变为three

2 个答案:

答案 0 :(得分:6)

当一个赋值用作命令本身而不是作为其他命令的前缀(例如echo)时,它会做一些不同的事情。当它本身用作命令时,它将shell变量设置为该值。当用作其他命令的前缀时,它在命令的环境中设置该变量,但不在shell 中设置。

因此,请看第一个示例a=one; echo $a,其中分号在同一行上生成这两个命令。第一个命令将shell变量a设置为值"一个",然后对于第二个命令,shell将a扩展为"一个",然后将其作为参数传递给echo

在第二个示例a=two echo $a中,分配是echo命令的前缀,因此echo将执行,a设置为"两个& #34;在它的环境中。但$a由shell扩展,而不是由echo命令扩展,a仍然设置为"一个"作为shell变量,以便使用该值。

第三个例子a=three echo $a >$a与第二个例子非常相似。 shell将$a扩展为"一个" (因为它是shell变量的值),然后执行echo onea设置为"三"在其环境和输出中定向到名为" one"。

的文件 顺便说一下,我还没有提到另一个复杂问题:export shell变量。默认情况下,shell变量不会在shell执行的命令环境中设置。也就是说,它们是shell变量,而不是环境变量。但是如果你export一个shell变量,它就会变成一个环境变量,并且会被该shell运行的后续命令继承。所以......

  • 这设置了一个shell变量,该变量不会传递给命令'环境:

    a=one
    
  • 这为此命令设置的环境变量,而不是shell或更高版本的命令:

    b=two somecommand
    
  • 这在shell中设置了一个环境变量,因此shell 可以从该shell运行所有后续命令:

    export c=three
    
  • 这也是一样的事情:

    d=four
    export d
    

    您可以在分配给它们之前,之后或分配时将shell变量导出到环境中。

答案 1 :(得分:2)

在您的脚本上运行Shellcheck

In x.sh line 2:
a=two echo $a
^-- SC2097: This assignment is only seen by the forked process.
       ^-- SC2098: This expansion will not see the mentioned assignment.
In x.sh line 3:
a=three echo $a >$a
^-- SC2097: This assignment is only seen by the forked process.
         ^-- SC2098: This expansion will not see the mentioned assignment.
         ^-- SC2094: Make sure not to read and write the same file in the same pipeline.
             ^-- SC2094: Make sure not to read and write the same file in the same pipeline.

然后根据需要查找SC ....代码,例如SC2097

在这种情况下,您的命令是var=... someCommand with params,因此该变量仅针对该命令设置,即在该过程中。

这也是分号(a=one; echo $a)的第一行不同的原因。 man bash声明:

  

由a分隔的命令;按顺序执行

因此,您设置变量,然后将echo作为两个单独的操作运行。