Shell 为什么在'中使用括号而不是方括号';如果!(ssh…)然后'';?

Shell 为什么在'中使用括号而不是方括号';如果!(ssh…)然后'';?,shell,unix,Shell,Unix,我试图理解这一行中括号的用法: if !(ssh -q $user@$server "[ -d /some/directory ]")then 通常情况下,条件介于[]之间,这里()的用法是什么?您需要在之间留出一个空格和(…)。使用bashshell编写此命令的一种正确方法: if ! (ssh -q $user@$server "[ -d \"/some/directory\" ]"); then echo "do something"; else echo "do so

我试图理解这一行中括号的用法:

if !(ssh -q $user@$server "[ -d /some/directory ]")then

通常情况下,条件介于[]之间,这里()的用法是什么?

您需要在
之间留出一个空格
(…)
。使用
bash
shell编写此命令的一种正确方法:

if ! (ssh -q $user@$server "[ -d \"/some/directory\" ]"); then 
   echo "do something"; 
else 
   echo "do something else"; 
fi
这将使用
ssh
检查远程
服务器上是否存在目录
/some/directory

人工测试
了解选项,如
-d

表示对
()
输出的逻辑(布尔)非或否定

ssh
中的
-q
选项用于安静模式

有关bash中单括号
()
的信息,请参见

注意,单括号用于分组子shell中的命令行。正如OP所建议的,
()
在这里并不是严格需要/推荐的,如果没有它也可以编写相同的
,则使用相同的

if ! ssh -q $user@$server "[ -d \"/some/directory\" ]"; then
.....

您需要在
之间留出一个空格
(…)
。使用
bash
shell编写此命令的一种正确方法:

if ! (ssh -q $user@$server "[ -d \"/some/directory\" ]"); then 
   echo "do something"; 
else 
   echo "do something else"; 
fi
这将使用
ssh
检查远程
服务器上是否存在目录
/some/directory

人工测试
了解选项,如
-d

表示对
()
输出的逻辑(布尔)非或否定

ssh
中的
-q
选项用于安静模式

有关bash中单括号
()
的信息,请参见

注意,单括号用于分组子shell中的命令行。正如OP所建议的,
()
在这里并不是严格需要/推荐的,如果没有它也可以编写相同的
,则使用相同的

if ! ssh -q $user@$server "[ -d \"/some/directory\" ]"; then
.....
你的台词中有一个小的“有争议的”(见评论)打字错误。第一个括号前面的空格。在shell脚本中,不需要空间。但是,根据shell中的某些选项,在命令行上直接键入此行时可能需要添加空格。用空格重写将是:

if ! (ssh -q $user@$server "[ -d /some/directory ]"); then ... ; fi
这一行有几个部分

  • [-d/some/directory]
    :这是对所谓的
    test
    命令的调用,该命令也可以写成
    […]
    test-d/some/directory
    [-d/some/directory]
    是相同的命令。它将检查目录
    /some/directory
    是否存在或可访问。(有关更多信息,请参见
    人工测试
  • ssh-q$user@$server cmd
    :这将在
    $server
    上以
    $user
    的身份执行命令
    cmd
    。但是,它将通过不抛出任何错误输出来安静地执行此操作(
    -q
    )。因此,本质上,用上面的测试替换
    cmd
    ,我们检查
    $server
    上的
    $user
    是否存在该目录或是否可以访问该目录。
    manssh::
    -q
    :安静模式。导致大多数警告和诊断消息被抑制

  • 完整命令现在被括在括号中。括号是一个分组,允许统一执行多个命令。即,
    (cmd1;cmd2)
    将作为一个单元执行。尽管如此,这些括号将在单独的实例中执行此操作。它将派生一个子shell来执行。在这种情况下,子shell中只执行一个命令。这是不必要的开销。如您所见,尽管语法看起来更干净,但它还是有效果的

    manbash::
    (列表)
    list
    在子shell环境中执行。影响shell环境的变量指定和内置命令在命令完成后不会保持有效。返回状态是
    列表的退出状态

  • !cmd
    :这将否定
    cmd
    的退出状态。如果命令成功执行(退出状态=0),它将假定为false。反之亦然

  • if
    语句写为
    if列表;然后是列表;fi
    。如果
    list
    的退出状态为零,则执行
    if
    语句。在这种情况下,
    列表
    !(ssh-q$user@$server“[-d/some/directory]”
    ,而
    列表
    的更常见示例是
    [-e foo]
    ,这是
    测试
    命令

编写if条件的类似方法现在有:

if ! ssh -q $user@$server "[ -d /some/directory ]"; then ...; fi
或者你可以移动
测试中的code>,导致:

if ssh -q $user@$server "[ ! -d /some/directory ]"; then ...; fi
最后,如果希望在没有子shell的情况下保留外观分组,可以使用
{…}
,即

if ! { ssh -q $user@$server "[ -d /some/directory ]"; }; then ...; fi
manbash::
{list;}
list
仅在当前shell环境中执行。列表必须以换行符或分号终止。 这称为组命令。返回状态为退出
列表的状态

你的台词中有一个小的“有争议的”(见评论)打字错误。第一个括号前面的空格。在shell脚本中,不需要空间。但是,根据shell中的某些选项,在命令行上直接键入此行时可能需要添加空格。用空格重写将是:

if ! (ssh -q $user@$server "[ -d /some/directory ]"); then ... ; fi
这一行有几个部分

  • [-d/some/directory]
    :这是对所谓的
    test
    命令的调用,该命令也可以写成
    […]
    test-d/some/directory
    [-d/some/directory]
    是相同的命令。它将检查目录
    /some/directory
    是否存在或可访问。(有关更多信息,请参见
    人工测试
  • ssh-q$user@$server cmd
    :这将执行命令