If statement 我可以在DOS批处理文件中使用IF块吗?

If statement 我可以在DOS批处理文件中使用IF块吗?,if-statement,batch-file,If Statement,Batch File,在DOS批处理文件中,我们只能有一行if语句体?我想我找到了一个地方,我可以使用()作为if块,就像在类似C的编程语言中使用的{}一样,但是当我尝试这样做时,它不会执行语句。也没有错误消息。这是我的代码: if %GPMANAGER_FOUND%==true(echo GP Manager is up goto Continue7 ) echo GP Manager is down :Continue7 奇怪的是,当我运行批处理文件时,“GP Manager已启动”和“GP Manager已关

在DOS批处理文件中,我们只能有一行if语句体?我想我找到了一个地方,我可以使用
()
作为if块,就像在类似C的编程语言中使用的
{}
一样,但是当我尝试这样做时,它不会执行语句。也没有错误消息。这是我的代码:

if %GPMANAGER_FOUND%==true(echo GP Manager is up
goto Continue7
)
echo GP Manager is down
:Continue7

奇怪的是,当我运行批处理文件时,“GP Manager已启动”和“GP Manager已关闭”都不会打印出来。

您确实可以将create语句块放在条件语句之后执行。但是你的语法错了。括号的使用必须与下图所示完全一致:

if <statement> (
    do something
) else (
    do something else
)
请注意有关我的示例代码的一些具体细节:

  • 在条件语句结尾和左括号之间添加的空格
  • 我正在设置
    @echo off
    以避免在执行时看到打印到控制台的所有语句,而只看到那些以
    echo
    开头的语句的输出
  • 我使用内置的
    ERRORLEVEL
    变量作为测试。阅读更多
    • 从逻辑上讲,科迪的答案应该是可行的。但是,我认为命令提示符在逻辑上不能处理代码块。在我的生活中,我不能让它在块中使用任何一个命令都能正常工作。在我的例子中,广泛的测试显示块中的所有命令都被缓存,并在块的末尾同时执行。这当然不会产生预期的结果。下面是一个过于简单的例子:

      if %ERRORLEVEL%==0 (
      set var1=blue
      set var2=cheese
      set var3=%var1%_%var2%
      )
      
      这应为var3提供以下值:

      blue_cheese
      
      但结果是:

      _
      
      因为在退出代码块时,所有3个命令都被缓存并同时执行

      我能够通过重新编写if块以仅执行一个命令goto并添加一些标签来克服这个问题。它笨重,我不太喜欢,但至少它能用

      if %ERRORLEVEL%==0 goto :error0
      goto :endif
      
      :error0
      set var1=blue
      set var2=cheese
      set var3=%var1%_%var2%
      
      :endif
      

      也许有点晚了,但希望如此:

      @echo off 
      
      if %ERRORLEVEL% == 0 (
      msg * 1st line WORKS FINE rem You can relpace msg * with any othe operation...
      goto Continue1
      )
      :Continue1
      If exist "C:\Python31" (
      msg * 2nd line WORKS FINE rem You can relpace msg * with any othe operation...
          goto Continue2
      )
      :Continue2
      If exist "C:\Python31\Lib\site-packages\PyQt4" (  
      msg * 3th line WORKS FINE rem You can relpace msg * with any othe operation...
          goto Continue3
      )
      :Continue3
      msg * 4th line WORKS FINE rem You can relpace msg * with any othe operation...
          goto Continue4
      )
      :Continue4
      msg * "Tutto a posto" rem You can relpace msg * with any othe operation...
      pause
      

      请尝试使用符号AND&或双符号AND&&(条件为errorlevel 0)作为命令分隔符,而不是这种goto混乱

      我用这个技巧修复了一个脚本片段,总结一下,我有三个批处理文件,一个在找到外部备份驱动器分配的字母后调用另外两个。我将第一个文件保留在主外部驱动器上,因此对其备份例程的调用工作正常,但对第二个文件的调用需要更改活动驱动器。下面的代码显示了我是如何修复它的:

      for %%b in (d e f g h i j k l m n o p q r s t u v w x y z) DO (
      if exist "%%b:\Backup.cmd" %%b: & CALL "%%b:\Backup.cmd"
      )
      

      我在与批处理文件中的IF命令相关的搜索返回的结果中读到了这篇文章,我忍不住要纠正IF块仅限于单个命令的错误观念。下面是生产Windows NT命令脚本的一部分,该脚本每天在我撰写此回复的机器上运行

          if "%COPYTOOL%" equ "R" (
          WWLOGGER.exe "%APPDATA%\WizardWrx\%~n0.LOG" "Using RoboCopy to make a backup of %USERPROFILE%\My Documents\Outlook Files\*"
          %TOOLPATH% %SRCEPATH% %DESTPATH% /copyall %RCLOGSTR% /m /np /r:0 /tee
          C:\BIN\ExitCodeMapper.exe C:\BIN\ExitCodeMapper.INI[Robocopy] %TEMP%\%~n0.TMP %ERRORLEVEL%
      ) else (
          WWLOGGER.exe "%APPDATA%\WizardWrx\%~n0.LOG" "Using XCopy to make a backup of %USERPROFILE%\My Documents\Outlook Files\*"
          call %TOOLPATH%  "%USERPROFILE%\My Documents\Outlook Files\*" "%USERPROFILE%\My Documents\Outlook Files\_backups" /f /m /v /y
          C:\BIN\ExitCodeMapper.exe C:\BIN\ExitCodeMapper.INI[Xcopy] %TEMP%\%~n0.TMP %ERRORLEVEL%
      )
      
      可能两行或多行的块只适用于Windows NT命令脚本(.CMD文件),因为搜索仅限于旧的批处理(.BAT)文件的应用程序的生产脚本目录时,只显示一个命令块。由于应用程序已经进入了扩展维护阶段(意味着我没有积极参与支持它),我不能说这是因为我不需要多行代码,还是因为我无法让它们工作


      不管怎样,如果后者是真的,有一个简单的解决办法;将多行移到单独的批处理文件或批处理文件子例程中。我知道后者在两种脚本中都有效。

      也许这可能会有帮助:是的,这很有帮助。DOS很烂。如果我想在If或else中使用多个语句,我必须在语句之间使用&&吗?或者有更优雅的方法吗?如果%ERRORLEVEL%==0,则最好使用,因为另一个变量始终为真,因为如果ERRORLEVEL为真,如果ERRORLEVEL等于或大于,则在此变量中忽略“==”case@jeb当前位置我想你可能没有抓住重点。使用
      ERRORLEVEL
      并不能解决他的问题。我只是发布了一个正确语法的示例。在这种情况下,任何一种形式都是可以接受的,就像0==0时的
      或任何其他普通表达式一样。但实际上,请确保您了解环境变量
      %ERRORLEVEL%
      与命令处理器的内部
      ERRORLEVEL
      之间的区别。Raymond Chen很好地解释了这一点。可能值得注意的是,如果您需要在
      if
      块中使用包含括号的路径(
      C:\Program Files(x86)
      ),则必须使用延迟扩展,否则if块将在遇到路径中的括号时立即退出,在@mythofechelon的评论中,即使REM语句中看似无害的右括号也会结束该块。e、 g.将
      REM这是一条注释(或者我认为是这样)
      放入
      IF
      块会把你搞砸。@mythofechelon和@rkageler都指出了一般规则中需要引用字符串的具体问题。如果%somevar%==example\u string2
      它应该始终是代码,所以操作数解析为
      如果“value\u of\u somevar”==“example\u string2
      ”以避免字符串操作数中的特殊字符导致
      IF
      语句中的语法错误。您设置的值应始终作为
      set“somevar=value\u of_somevar”
      语法允许您转义变量值中的特殊字符,请注意,我不是说
      set somevar=“value\u of_somevar”
      使用延迟扩展应该有效:使用:
      set var3=!var1!!!var2这到底是为什么被否决?这正是我所需要的。@GCB667-为了澄清@Louis”写了一个“答案”,它与为什么IF声明不适用于原始海报的问题无关。它与“vinniejohnson”的答案有关(这也遗漏了原始海报的问题)。
      
          if "%COPYTOOL%" equ "R" (
          WWLOGGER.exe "%APPDATA%\WizardWrx\%~n0.LOG" "Using RoboCopy to make a backup of %USERPROFILE%\My Documents\Outlook Files\*"
          %TOOLPATH% %SRCEPATH% %DESTPATH% /copyall %RCLOGSTR% /m /np /r:0 /tee
          C:\BIN\ExitCodeMapper.exe C:\BIN\ExitCodeMapper.INI[Robocopy] %TEMP%\%~n0.TMP %ERRORLEVEL%
      ) else (
          WWLOGGER.exe "%APPDATA%\WizardWrx\%~n0.LOG" "Using XCopy to make a backup of %USERPROFILE%\My Documents\Outlook Files\*"
          call %TOOLPATH%  "%USERPROFILE%\My Documents\Outlook Files\*" "%USERPROFILE%\My Documents\Outlook Files\_backups" /f /m /v /y
          C:\BIN\ExitCodeMapper.exe C:\BIN\ExitCodeMapper.INI[Xcopy] %TEMP%\%~n0.TMP %ERRORLEVEL%
      )