批处理 - 如何在作为参数传递给子例程的字符串中回显感叹号?

Batch - How to echo exclamation mark inside string passed as parameter to subroutine?

我有以下脚本:

@ECHO OFF
SETLOCAL ENABLEEXTENSIONS ENABLEDELAYEDEXPANSION

SET /A countArgs=1

FOR %%p in (%pathListToCheck%) DO (
    IF NOT EXIST %%p (
        CALL :error "!countArgs!. Argument -> bla!"
        EXIT /B 1
    )
    SET /A countArgs+=1
)

:error
    ECHO ERROR  
    set x=%~1
    ECHO !x!
EXIT /B 0

遗憾的是感叹号没有得到 echod。我也试过像 ^!^^! 那样转义它,但它不起作用。

我在这里使用延迟扩展来使大于号 (>) 起作用。如果我尝试直接回显参数 (ECHO %~1),它将失败。有关详细信息,请参阅我的

如何解决这个问题?

感谢您的帮助...

你没有 read/understand Stephans 的摘要
setlocal enabledelayedexpansion 是感叹号消失的原因。
没有理由在您当前的代码中使用它。

如果你想在没有引号的情况下回显 <|>& 你必须逃避那些。这可以通过代码来完成。

:: Q:\Test18\SO_50419709.cmd
@Echo off
SetLocal EnableExtensions DisableDelayedExpansion

SET /A countArgs=1

set "pathlisttocheck=%userprofile%,x:\x\x\"
FOR %%p in (%pathListToCheck%) DO (
    IF NOT EXIST %%p (
        CALL :error "%%countArgs%%. Argument -> bla!  %%~p"
        EXIT /B 1
    )
    SET /A countArgs+=1
)
EXIT /B 1

:error
ECHO ERROR  
set "x=%~1"
set "x=%x:>=^>%"
ECHO %x%
EXIT /B 0

示例输出:

> Q:\Test18\SO_50419709.cmd
ERROR
2. Argument -> bla! x:\x\x\

如果你转义感叹号并且dis能够在函数内延迟扩展,它会起作用(虽然它删除了"delayed" 替代方案——你无论如何都不喜欢)

@echo off
SETLOCAL ENABLEEXTENSIONS ENABLEDELAYEDEXPANSION
SET /A countArgs=2
CALL :error "!countArgs!. Argument -> bla^!"
EXIT /B 1

:error
  setlocal disabledelayedexpansion
    for /f "delims=" %%a in ("%~1") do echo for:      %%a
    echo quoted:  "%~1"
  endlocal
EXIT /B 0