在Windows批处理脚本中设置variables

我需要根据windows批处理脚本的参数设置一些variables。

@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 

在第二次电话之后。 从此之后,当我在AAAZZZ交替时,我得到这样的模式:

 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 

所以看起来我正在操作一个全局variables,即使在脚本完成之后,这个全局variables也是可用的。 这本身并没有打扰我,但新的设置只有脚本终止后才可用,因为我的脚本的其余部分依赖于它(显然)。

在这种情况下,局部variables的正确用法是什么? 如何解释上述“国家背景”的怪异行为?

谢谢!

batch file中的variables默认在脚本执行开始时展开; 你需要使用延迟扩展,这是可用的“!” 分隔符:

echo Source dir is: !SOURCE_DIR!

这只有在命令解释器启用延迟扩展时才起作用,默认情况下不是这样 。 所以你需要在启动解释器时启用它,使用CMD.EXE /V

您也可以在batch file中使用以下语句启用它:

setlocal ENABLEDELAYEDEXPANSION

更多信息在这里 。

我可能已经处理了一些简单的…

 @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% 

我不得不承认,当这个问题的例子不是这样的时候,为什么这是有效的,我有点困惑。 我最好的猜测是这是一个范围问题。 因为在这个例子中,variablesSOURCE_DIR被设置在parens中,它的值在根目录中保持不变。 我的脚本在根作用域中改变了SOURCE_DIR。

至于为什么Delayed Expansion技巧会使得它的范围级别变得更深,看起来扩展发生在每个范围变化的开始。 所以通过拖延,你基本上迫使它在返回到根作用域之后重新扩展。