字符串比较以在批处理文件中跳出循环

string comparison to break out of loop in batch file

对于使用批处理脚本在 Windows 注册表中进行搜索,我必须循环几个键,进行比较以确定哪个是正确的,然后更新键。

for 循环中的迭代似乎无法跳出。我看到 others 也面临类似的问题,但似乎没有简单的解决方案。这是演示该问题的片段。

@echo off
echo.
echo Diet Favorites

set favorite="bananas"
for %%a in (apples, bananas, chocolates) do call :reviewList %%a
echo.
echo Processing completed.
goto end

:reviewList item
    set foundFavorite="false"
    call :chooseFavorite "%~1"
    if /I "%foundFavorite%"=="true" (
        echo found the favorite - %~1
        exit /b 0
    ) else (
        echo skip %~1
    )
    endlocal & goto :eof

:chooseFavorite item
    if "%~1"==%favorite% set "foundFavorite=true"
    endlocal & goto :eof

:end

chooseFavorite returns 环境变量中的收藏夹。输出显示 reviewList 在确定收藏夹后继续循环。

Diet Favorites
skip apples
found the favorite - bananas
skip chocolates

Processing completed.

比较有效,但如果退出按预期工作,则根本不应列出巧克力饮食选项。如何巧妙地跳出循环迭代?

检查循环中 :reviewList 的 return 代码,并相应地中断。您需要在 non-breaker 调用中正确调用 exit /b 0,并在断路器调用中调用 exit /b 1(或任何 non-zero 值)。

试试看:

@echo off
echo.
echo Diet Favorites

set favorite="bananas"
for %%a in (apples, bananas, chocolates) do (
    call :reviewList %%a || goto :break_loop
)
:break_loop
echo.
echo Processing completed.
goto end

:reviewList item
set foundFavorite="false"
call :chooseFavorite "%~1"
if /I "%foundFavorite%"=="true" (
    echo found the favorite - %~1
    exit /b 1
) else (
    echo skip %~1
)
endlocal
exit /b 0

:chooseFavorite item
if "%~1"==%favorite% set "foundFavorite=true"
endlocal & goto :eof

:end

输出为:

S:\Temp>test

Diet Favorites
skip apples
found the favorite - bananas

Processing completed.
@ECHO Off
SETLOCAL
echo.
echo Diet Favorites

set "favorite=bananas"
for %%a in (apples, bananas, chocolates) do call :reviewList %%a&IF DEFINED foundFavorite GOTO foundit
:foundit
echo.
echo Processing completed.
goto end

:reviewList param
set "foundFavorite="
call :chooseFavorite "%~1"
if DEFINED foundFavorite (
 echo found the favorite - %~1
) else (
 echo skip %~1
)
goto :eof

:chooseFavorite param
if "%~1"=="%favorite%" set "foundFavorite=%~1"
goto :eof

:end
GOTO :EOF

由于您在发布的代码中没有使用任何 setlocal 命令,因此 endlocal 是多余的。

此版本将 foundFavorite 设置为 empty,并将其设置为 something(可以是您喜欢的任何内容 - 我只是选择找到的东西,这通常很方便)找到匹配项时。 if defined variable 解释变量的 run-time 状态,因此它可以在 for 循环中使用。

顺便说一句- 尝试 运行 您的原始代码 echo ON。您会看到您的 if 语句实际上正在执行 if /i ""false""=="true" ...

这就是为什么在 SO 上约定使用 string-assignments 的 set "var=value" 语法。然后,您可以根据需要应用引号,而不必担心在何处或是否应用或删除可能在变量中的引号。