在批处理文件中测试参数是否为空的正确方法是什么?

bla*_*k3r 194 windows shell cmd batch-file

我需要测试是否设置了变量.我已经尝试了几种技术,但他们忽视了,只要%1用双引号包围时,如情况%1"c:\some path with spaces".

IF NOT %1 GOTO MyLabel // This is invalid syntax
IF "%1" == "" GOTO MyLabel // Works unless %1 has double quotes which fatally kills bat execution
IF %1 == GOTO MyLabel // Gives an unexpected GOTO error.
Run Code Online (Sandbox Code Playgroud)

根据此站点,这些是受支持的IF语法类型.所以,我没有办法做到这一点.

IF [NOT] ERRORLEVEL number command
IF [NOT] string1==string2 command
IF [NOT] EXIST filename command
Run Code Online (Sandbox Code Playgroud)

Dan*_*ory 272

使用方括号而不是引号:

IF [%1] == [] GOTO MyLabel
Run Code Online (Sandbox Code Playgroud)

括号是不安全的:只使用方括号.

  • 如果变量文本中包含空格,则此方法无效. (24认同)
  • 使用其他字符,例如`if#%1#== ##`或`if [%1] == []`只要参数中没有空格就好,否则你会得到一个`...意外的这次`错误. (12认同)
  • 括号不安全!像'%1`中的`&`这样的内容会破坏这条线 (11认同)
  • 正如我在回答中提到的那样,使用"%~1"`确实是一种更好的方法. (9认同)
  • 伙计们,@ jamesdlin是对的.如果变量文本有空格或是`==`,这种方法将不起作用.请改用他的答案. (5认同)
  • 有关安全方法,请参阅@ jeb的答案:/sf/answers/591665441/ (4认同)
  • 你没有说清楚它"它不适用于空间".请改用@jamesdlin. (3认同)
  • @NYCBilly嗯?如果运行`test.bat"hello world",那么`%1`将包含空格.(如果我们只是想检查`%1`是否为空,那无关紧要,但kungufjam的观点是`if [%1] == [hello world]`如果`%1`是``你好`世界"`. (2认同)

jam*_*lin 137

您可以使用:

IF "%~1" == "" GOTO MyLabel
Run Code Online (Sandbox Code Playgroud)

剥去外部报价集.通常,这是一种比使用方括号更可靠的方法,因为即使变量中包含空格,它也会起作用.

  • 这确实是一个很好的方法.通过使用`~`,如果它们存在,则剥离外引号,然后手动添加它们(确保只有一组).此外,如果参数包含空格,你*必须使用引号(当我使用`#`或括号而不是引号的先前版本导致带有空格的参数时,我很难学会这种情况......此时出乎意料的是......错误.) (8认同)
  • 这是否也适用于%MYVAR%等常规变量,而不是像%1这样的参数? (3认同)
  • @simpleuser糟糕,你是对的,它不适用于一般的环境变量. (3认同)
  • +1我没试过.但是,知道这一点很有意义. (2认同)
  • 注意使用双 '"' 作为转义序列的字符串 - 尝试比较时脚本将崩溃。例如`""这个字符串将使比较崩溃""`。双 '"' 是正确的转义序列,并且如果字符串为空,则对双 '"' 进行替换将会失败。 (2认同)
  • @Amalgovinus您可能可以将变量作为参数传递给子例程,并让子例程使用“%~1”。 (2认同)
  • 我应该更改已接受的答案吗?这总是比[]更好吗 (2认同)

jeb*_*jeb 36

最好的半解决方案之一是复制%1到变量然后使用延迟扩展,作为delayedExp.对任何内容都是安全的.

set "param1=%~1"
setlocal EnableDelayedExpansion
if "!param1!"=="" ( echo it is empty )
rem ... or use the DEFINED keyword now
if defined param1 echo There is something
Run Code Online (Sandbox Code Playgroud)

这样做的好处是处理param1是绝对安全的.

param1的设置在许多情况下都会起作用,比如

test.bat hello"this is"a"test
test.bat you^&me
Run Code Online (Sandbox Code Playgroud)

但它会失败,如奇怪的内容

test.bat "&"^&
Run Code Online (Sandbox Code Playgroud)

如果你想成为99%防弹,你可以阅读如何接收最奇怪的命令行参数?


And*_*ris 17

来自IF/?:

如果启用了命令扩展,则IF更改如下:

IF [/I] string1 compare-op string2 command
IF CMDEXTVERSION number command
IF DEFINED variable command
Run Code Online (Sandbox Code Playgroud)

......

DEFINED条件就像EXISTS一样,除了它采用环境变量名称,如果定义了环境变量,则返回true.

  • 是的,我实际上尝试过这种方法,据我所知,这只适用于环境变量。因此,无法使用 %1 或批处理文件中定义的变量。 (2认同)
  • 这只对`%1`等类似。批处理文件运行时,“批处理文件中定义的变量”实际上是**环境变量,您可以在它们上使用“ IF DEFINED”。 (2认同)

小智 7

使用"IF DEFINED变量命令"来测试批处理文件中的变量.

但是如果你想测试批处理参数,请尝试下面的代码以避免棘手的输入(例如"1 2"或ab ^> cd)

set tmp="%1"
if "%tmp:"=.%"==".." (
    echo empty
) else (
    echo not empty
)
Run Code Online (Sandbox Code Playgroud)


Aut*_*ick 7

不幸的是,我没有足够的声誉来评论或投票给我自己写的答案。

最初,OP的问题说的是“变量”而不是“参数”,这引起了极大的混乱,尤其是因为这是google中搜索如何测试空白变量的第一链接。自从我获得原始答案以来,Stephan已经编辑了原始问题,以使用正确的术语,但是我决定删除该答案,以消除任何混淆,而不是删除我的答案,尤其是在Google仍然派人来这里询问变量的情况下:

%1不是变量!这是一个命令行参数。

非常重要的区别。后面带有数字的单个百分号表示命令行参数而不是变量。

使用set命令设置变量,并使用2个百分号调用-前一个和后一个。例如%myvar%

要测试空变量,请使用“如果未定义”语法(显式用于变量的命令不需要任何百分号),例如:

set myvar1=foo  
if not defined myvar1 echo You won't see this because %myvar1% is defined.  
if not defined myvar2 echo You will see this because %myvar2% isn't defined.
Run Code Online (Sandbox Code Playgroud)

(如果要测试命令行参数,那么我建议参考jamesdlin的答案。)


kay*_*eck 5

我根据这里的答案创建了这个小批量脚本,因为有很多有效的。只要您遵循相同的格式,就可以随意添加:

REM Parameter-testing

Setlocal EnableDelayedExpansion EnableExtensions

IF NOT "%~1"=="" (echo Percent Tilde 1 failed with quotes) ELSE (echo SUCCESS)
IF NOT [%~1]==[] (echo Percent Tilde 1 failed with brackets) ELSE (echo SUCCESS)
IF NOT  "%1"=="" (echo Quotes one failed) ELSE (echo SUCCESS)
IF NOT [%1]==[] (echo Brackets one failed) ELSE (echo SUCCESS)
IF NOT "%1."=="." (echo Appended dot quotes one failed) ELSE (echo SUCCESS)
IF NOT [%1.]==[.] (echo Appended dot brackets one failed) ELSE (echo SUCCESS)

pause
Run Code Online (Sandbox Code Playgroud)


小智 5

您可以使用

if defined (variable) echo That's defined!
if not defined (variable) echo Nope. Undefined.
Run Code Online (Sandbox Code Playgroud)


小智 5

我用下面的代码测试,这很好。

@echo off

set varEmpty=
if not "%varEmpty%"=="" (
    echo varEmpty is not empty
) else (
    echo varEmpty is empty
)
set varNotEmpty=hasValue
if not "%varNotEmpty%"=="" (
    echo varNotEmpty is not empty
) else (
    echo varNotEmpty is empty
)
Run Code Online (Sandbox Code Playgroud)