如何正确执行批处理脚本中的字符串进行数字比较

时间:2019-04-30 11:48:44

标签: batch-file

我不知道脚本出了什么问题,但是如果输入值大于1,它总是返回false,如果输入值小于1,则根本没有输出。

示例

@echo off

echo [1] Option 1
echo [2] Option 2
echo [3] Option 3
echo [4] Option 4
echo [5] Option 5
echo [6] Option 6
echo [7] Option 7
echo [8] Option 8
echo [9] Option 9
echo [10] Option 10

set /p option="Enter option (1-10): "

if "%option%" geq "1" if "%option%" leq "10" (
  echo %option% is greater than or qual to 1, and is less than or equal to 10
) else (
  echo Invalid option %option%
)

pause >nul

输入

2

输出

Invalid option 2

预期结果

2 is greater than or qual to 1, and is less than or equal to 10

3 个答案:

答案 0 :(得分:1)

删除引号进行数字比较:

set /p option="Enter option (1-10): "

if %option% geq 1 if %option% leq 10 (
    echo %option% is greater than or qual to 1, and is less than or equal to 10
) else (
    echo Invalid option %option%
)

用引号引起来的是字符串比较,因为实际上它们也是比较值的一部分。如果它们中的任何一个都是非数字的(如果其中一个或两个都包含引号,就是这种情况),则使用字符串或字母比较,其中2大于10,因为字符{{ 1}}的代码比2高。


如果输入值1为空,则此方法失败;您可以使用%option%进行抵消:

if defined

或者您可以通过尝试使用:LOOP rem // Reset variable, so it is empty if user just presses {Enter}: set "option=" set /P option="Enter option (1-10): " rem // Jump back to prompt if user did not enter anything: if not defined option goto :LOOP if %option% geq 1 if %option% leq 10 ( echo %option% is greater than or qual to 1, and is less than or equal to 10 ) else ( echo Invalid option %option% ) 进行转换来强制将值转换为数字;这比以前的版本更安全,因为它甚至可以在用户输入包含set /A和其他特殊字符的情况下起作用:

"

当然可以使用delayed variable expansion来避免出现空值或特殊字符的麻烦:

set "option="
set /P option="Enter option (1-10): "
rem // Convert user entry to numeric value:
set /A "comp=option"
if %comp% geq 1 if %comp% leq 10 (
    echo %option% is greater than or qual to 1, and is less than or equal to 10
) else (
    echo Invalid option %option%
)

现在让我们集中讨论set "option=" set /P option="Enter option (1-10): " rem // Delayed expansion even allows to compare empty values and even to safely echo all possible strings: setlocal EnableDelayedExpansion if !option! geq 1 if !option! leq 10 ( echo !option! is greater than or qual to 1, and is less than or equal to 10 ) else ( echo Invalid option !option! ) endlocal 条件本身(此处扩展延迟)并重新编写一下:

if

现在您可以清楚地看到if !option! geq 1 ( if !option! leq 10 ( echo !option! is greater than or qual to 1, and is less than or equal to 10 ) else ( echo Invalid option !option! ) ) 小于!option!的情况没有得到处理;为此,您将需要另一个1子句:

else

或者您只需使用goto即可完成相同操作:

if !option! geq 1 (
    if !option! leq 10 (
        echo !option! is greater than or qual to 1, and is less than or equal to 10
    ) else (
        echo Invalid option !option!
    )
) else (
    echo Invalid option !option!
)

答案 1 :(得分:1)

您还可以更加动态地执行此操作,例如:

@Echo Off
SetLocal EnableDelayedExpansion
For /F "Delims==" %%A In ('Set Option[ 2^>Nul')Do Set "%%A="
For /F "Tokens=1*Delims=:" %%A In ('FindStr "^::" "%~f0"^|FindStr /N "^"')Do Set "Option[%%A]=%%B"&Echo(%%A %%B
Set Option[>Nul 2>&1||Exit /B
Echo( Select an option from the list&Echo(
:Opt
::Option 1
::Option 2
::Option 3
::Option 4
::Option 5
::Option 6
::Option 7
::Option 8
::Option 9
::Option 10
Set /P "Opt="
Set Option[|Findstr /BL "Option[%Opt%]=">Nul||GoTo :Opt
Rem Your commands go below here.
Echo( You Selected "!Option[%Opt%]!"&Pause

您的选项仅在批处理文件中列出,并且带有格式错误的标签::,这表示该批处理文件不会运行它们,但可以读取它们。将Set /P输入与已经动态定义为变量的输入进行检查,并且仅在输入有效输入后才继续。可以使用延迟扩展作为!Option[%Opt%]!来检索分配给所选变量的字符串,我添加了一个示例命令行以向您展示其用法。最后,选项可以移动到脚本中的任何位置。

答案 2 :(得分:1)

使用choice.exe而不是set /p可以避免对输入内容进行明确检查。
当使用9个以上的选项时,也可以使用字母保留单个键输入。

:: Q:\Test\2019\04\30\SO_55920303.cmd
@echo off
:Loop
echo [1] Option 1
echo [2] Option 2
echo [3] Option 3
echo [4] Option 4
echo [5] Option 5
echo [6] Option 6
echo [7] Option 7
echo [8] Option 8
echo [9] Option 9
echo [A] Option 10
echo [Q] quit
choice /C 123456789AQ /M "Enter option"
if errorlevel 11 exit /B 0
echo You chose Option %ErrorLevel%
Timeout /t 3 >Nul
goto :loop