在 Windows 批处理脚本中设置变量

在 Windows 批处理脚本中设置变量

我需要根据 Windows 批处理脚本的参数设置一些变量。

@echo off       
if [%1]==[] (
    echo "Usage: xxx <AAA|ZZZ>"
) else (
    if [%1]==[AAA] (
        SET SOURCE_DIR=c:\dirA
    ) else if [%1]==[ZZZ] (
        SET SOURCE_DIR=c:\dirZ
    ) 
    echo Source dir is: %SOURCE_DIR%
)

当我使用参数调用上述脚本时AAA,我得到输出

Source dir is: c:\dirA

第二次通话后。从那时起,当我交替使用AAA雙方,我得到了这个模式:

C:\stageing-area>test.bat AAA
Source dir is: c:\dirZ
C:\stageing-area>test.bat ZZZ
Source dir is: c:\dirA
C:\stageing-area>test.bat AAA
Source dir is: c:\dirZ
C:\stageing-area>test.bat ZZZ
Source dir is: c:\dirA

因此,看起来我正在操作一个全局变量,该变量即使在脚本完成后也可用。这一点并不困扰我,但新设置仅在脚本终止是一个问题,因为我的脚本的其余部分依赖于它(显然)。

在这种情况下,局部变量的正确用法是什么?如何解释上述“延迟状态设置”的奇怪行为?

谢谢!

答案1

批处理文件中的变量默认在脚本执行开始时扩展;您需要使用延迟扩展,可以使用“!”分隔符:

echo Source dir is: !SOURCE_DIR!

这仅在命令解释器启用了延迟扩展时才有效,默认情况下不是;因此您需要在启动解释器时启用它,使用CMD.EXE /V

您也可以在批处理文件中使用此语句启用它:

setlocal ENABLEDELAYEDEXPANSION

更多信息这里

答案2

我本可以处理得更简单一些……

@ECHO OFF       
SET SOURCE_DIR=
IF /I [%1]==[AAA] SET SOURCE_DIR=c:\dirA
IF /I [%1]==[ZZZ] SET SOURCE_DIR=c:\dirZ
IF [%SOURCE_DIR]==[] (
    ECHO "Usage: xxx <AAA|ZZZ>"
    EXIT 1
) 
ECHO Source dir is: %SOURCE_DIR%

我必须承认,我有点困惑,为什么这个方法有效,而问题中的例子却不行。我最好的猜测是,这是一个范围问题。因为在示例中,变量 SOURCE_DIR 是在括号内设置的,所以它在根范围内的值保持不变。我的脚本在根范围内更改了 SOURCE_DIR。

至于为什么延迟扩展技巧会导致它拾取更深一层范围的更改,似乎扩展发生在每次范围更改的开始。因此,通过延迟,您基本上是在强制它在返回根范围后重新扩展。

相关内容