it-swarm.com.ru

Как проверить параметр командной строки в файле ".bat"?

Моя ОС - Windows Vista. Мне нужно иметь файл .bat, в котором мне нужно проверить, вводит ли пользователь какой-либо параметр командной строки или нет. Если да, то если параметр равен -b, тогда я сделаю что-то другое, в противном случае я отмечу "Неверный ввод". Если пользователь не введет какой-либо параметр командной строки, я сделаю что-нибудь. Я создал следующий .bat файл. Он работает для -b и не равен -b, но завершается ошибкой, когда пользователь не передает какой-либо параметр командной строки.

Я всегда получаю ошибку:

GOTO was unexpected at this time.

Может кто-нибудь сказать мне, что я здесь делаю не так?


ECHO OFF
CLS
ECHO.

IF [%1]==[/?] GOTO BLANK

IF %1=="-b" GOTO SPECIFIC

IF NOT %1=="-b" GOTO UNKNOWN

:SPECIFIC

ECHO SPECIFIC

GOTO DONE

:BLANK

ECHO No Parameter

GOTO DONE

:UNKNOWN

ECHO Unknown Option

GOTO DONE

:DONE

ECHO Done!
90
javauser71

Вам нужно проверить, не задан ли параметр: if "%~1"=="" goto blank

После того, как вы это сделаете, включите переключатель if/else на -b: if "%~1"=="-b" (goto specific) else goto unknown

Окружение параметров кавычками упрощает проверку таких параметров, как пустые/пустые/отсутствующие параметры. "~" гарантирует удаление двойных кавычек, если они были в аргументе командной строки.

125
afrazier

Посмотрите http://ss64.com/nt/if.html для ответа; команда IF [%1]==[] GOTO NO_ARGUMENT или похожая.

25
Jeremiah Willcock

Краткий ответ - используйте квадратные скобки:

if [%1]==[] goto :blank

или (когда вам нужно обработать заключенные в кавычки аргументы, см. Редактирование ниже):

if [%~1]==[] goto :blank

Зачем? Вы можете спросить. Ну, так же, как упоминал Иеремия Уиллкок: http://ss64.com/nt/if.html - они используют это! Хорошо, но что не так с цитатами?

Опять же, короткий ответ: они "магические" - иногда двойные (двойные) кавычки преобразуются в одинарные (двойные) кавычки. И они должны соответствовать, для начала.

Рассмотрим этот маленький скрипт:

@rem argq.bat
@echo off

:loop 
if "%1"=="" goto :done
echo %1
shift
goto :loop

:done
echo Done.

Давайте проверим это:

C:\> argq bla bla
bla
bla
Done.

Кажется, работает. Но теперь давайте переключимся на вторую передачу:

C:\> argq "bla bla"
bla""=="" was unexpected at this time.

Boom Это не оценивалось как true, равно как и false. Сценарий Умер. Если вы должны были выключить реактор где-то вниз по линии, ну, вам не повезло. Теперь ты умрешь, как Гарри Даглиан.

Вы можете подумать - хорошо, аргументы не могут содержать кавычки. Если они это сделают, это произойдет. Неправильно Вот несколько утешений:

C:\> argq ""bla bla""
""bla
bla""
Done.

О да. Не волнуйтесь - иногда это будет работать.

Давайте попробуем другой скрипт:

@rem args.bat
@echo off

:loop 
if [%1]==[] goto :done
echo %1
shift
goto :loop

:done
echo Done.

Вы можете проверить себя, что это работает нормально для вышеуказанных случаев. Это логично - кавычки не имеют ничего общего с скобками, поэтому здесь нет никакой магии. Но как насчет того, чтобы приправить аргументы скобками?

D:\>args ]bla bla[
]bla
bla[
Done.

D:\>args [bla bla]
[bla
bla]
Done.

Не повезло там. Скобки просто не могут заглушить парсер cmd.exe.

Давайте вернемся к злым цитатам на мгновение. Проблема была там, когда аргумент заканчивался цитатой:

D:\>argq "bla1 bla2"
bla2""=="" was unexpected at this time.

Что если я пройду просто:

D:\>argq bla2"
The syntax of the command is incorrect.

Скрипт вообще не запускается. То же самое для args.bat:

D:\>args bla2"
The syntax of the command is incorrect.

Но что я получу, когда количество "- символов "совпадает" (т.е. является четным), в таком случае:

D:\>args bla2" "bla3
bla2" "bla3
Done.

Хорошо - надеюсь, вы узнали кое-что о том, как файлы .bat разделяют свои аргументы командной строки (СОВЕТ: * Это не совсем так, как в bash). Приведенный выше аргумент содержит пробел. Но цитаты не удаляются автоматически.

А argq? Как это реагирует на это? Как и следовало ожидать:

D:\>argq bla2" "bla3
"bla3"=="" was unexpected at this time.

Так что - подумайте, прежде чем сказать: "Знаете что? Просто используйте кавычки. [Потому что, для меня это выглядит лучше]".

Редактировать

Недавно были комментарии об этом ответе - ну, квадратные скобки "не могут справиться" с передачей цитируемых аргументов и обработкой их так же, как если бы они не были заключены в кавычки.

Синтаксис:

if "%~1"=="" (...)

Это не какое-то недавно обнаруженное достоинство двойных кавычек, а отображение аккуратной возможности извлечения кавычек из переменной аргумента, если первый и последний символ является двойной кавычкой.

Эта "технология" работает так же хорошо с квадратными скобками:

if [%~1]==[] (...)

Было полезно указать на это, поэтому я также приветствую новый ответ.

Наконец, поклонники двойных кавычек, существует ли в вашей книге аргумент вида "" или он пустой? Просто спрашиваешь;)

13
Tomasz Gandor

В дополнение к другим ответам, на которые я подписан, вы можете рассмотреть возможность использования переключателя /I команды IF.

... ключ/I, если он указан, говорит о необходимости сравнения строк без учета регистра.

это может быть полезно, если вы хотите предоставить своим пользователям гибкую возможность указывать параметры без учета регистра.

IF /I "%1"=="-b" GOTO SPECIFIC
8
PA.

На самом деле, все остальные ответы имеют недостатки. Самый надежный способ это:

IF "%~1"=="-b" (GOTO SPECIFIC) ELSE (GOTO UNKNOWN)

Подробное объяснение:

Использование "%1"=="-b" сгладит сбой при передаче аргумента с пробелами и кавычками. Это наименее надежный метод.

IF "%1"=="-b" (GOTO SPECIFIC) ELSE (GOTO UNKNOWN)

C:\> run.bat "a b"

b""=="-b" was unexpected at this time.

Использование [%1]==[-b] лучше, потому что оно не завершится с пробелами и кавычками, но не совпадет, если аргумент будет окружен кавычками.

IF [%1]==[-b] (GOTO SPECIFIC) ELSE (GOTO UNKNOWN)

C:\> run.bat "-b"

(does not match, and jumps to UNKNOWN instead of SPECIFIC)

Использование "%~1"=="-b" является наиболее надежным. %~1 удалит окружающие кавычки, если они существуют. Так что это работает с и без кавычек, а также без аргументов.

IF "%~1"=="-b" (GOTO SPECIFIC) ELSE (GOTO UNKNOWN)

C:\> run.bat
C:\> run.bat -b
C:\> run.bat "-b"
C:\> run.bat "a b"

(all of the above tests work correctly)
5
wisbucky

Вы сравниваете строки. Если аргументы опущены, %1 расширяется до пустого значения, поэтому команды становятся, например, IF =="-b" GOTO SPECIFIC (что является синтаксической ошибкой). Оберните свои строки в кавычки (или квадратные скобки).

REM this is ok
IF [%1]==[/?] GOTO BLANK

REM I'd recommend using quotes exclusively
IF "%1"=="-b" GOTO SPECIFIC

IF NOT "%1"=="-b" GOTO UNKNOWN
5
Jeff Mercado