it-swarm.com.ru

Работа с кавычками в пакетных скриптах Windows

В пакетном файле Windows, когда вы делаете следующее:

set myvar="c:\my music & videos"

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

Благодарю.

55
GetFree
set "myvar=c:\my music & videos"

Обратите внимание, что кавычки начинаются до myvar. Это на самом деле так просто. Примечание: myvar не может быть отображен впоследствии, если он не заключен в кавычки, потому что & будет читаться как разделитель команд, но он все равно будет работать как путь.

http://ss64.com/nt/set.html в разделе "Имена переменных могут включать пробелы"

50
RuskoGuyachev

Это правильный способ сделать это:

set "myvar=c:\my music & videos"

Кавычки не будут включены в значение переменной.

59
Craig Rorrer

Это зависит от того, как вы хотите использовать переменную. Если вы просто хотите использовать значение переменной без кавычек, вы можете использовать либо отложенное раскрытие и подстановку строк, либо команду for:

@echo OFF
SETLOCAL enabledelayedexpansion

set myvar="C:\my music & videos"

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

Если вы используете отложенное раскрытие с подстановкой строк, вы получите значение переменной без кавычек:

@echo !myvar:"=!
>>> C:\my music & videos

Вы также можете использовать команду for:

for /f "tokens=* delims=" %%P in (%myvar%) do (
    @echo %%P
)
>>> C:\my music & videos

Однако, если вы хотите использовать переменную в команде, вы должны использовать значение в кавычках или заключить значение переменной в кавычки:

  1. Используя подстановку строк и отложенное расширение, используйте значение переменной без кавычек, но используйте переменную в команде:

    @echo OFF
    SETLOCAL enabledelayedexpansion
    
    set myvar="C:\my music & videos"
    md %myvar%
    @echo !myvar:"=! created.
    
  2. Использование команды for для использования значения переменной без кавычек, но вам придется заключать переменную в кавычки при использовании ее в командах:

    @echo OFF
    set myvar="C:\my music & videos"
    
    for /f "tokens=* delims=" %%P in (%myvar%) do (
        md "%%P"
        @echo %%P created.
    )
    

Короче говоря, на самом деле нет чистого способа использовать путь или имя файла, которые содержат встроенные пробелы и/или &s в командном файле.

35
Patrick Cuff

Используйте jscript.

Много лун назад (то есть около 8 лет) я работал над большим проектом C++/VB6, и у меня были различные фрагменты Batch Script для выполнения частей сборки.

Затем кто-то указал мне на Joel Test , я был особенно очарован пунктом 2 и приступил к объединению всех моих маленьких сценариев сборки в один отдельный сценарий сборки. , ,.

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

В конце концов - я могу быть упрямым мной - Я забросил всю партию и примерно за день переписал ее все в JavaScript , запустив его из командной строки с CScript.

Я не оглядывался назад. Хотя в наши дни это MSBuild и Cruise Control, если мне нужно что-то даже немного связанное с пакетным скриптом, я использую jscript.

6
Binary Worrier

Интерпретатор команд Windows позволяет использовать кавычки вокруг всей команды set (действует в каждой версии Windows NT от NT 4.0 до Windows 2012 R2)

Ваш сценарий должен быть написан следующим образом:

@echo OFF

set "myvar=C:\my music & videos"

Затем вы можете поместить кавычки вокруг переменных по мере необходимости.

Работа с CMD Prompt иногда может показаться эзотерической, но интерпретатор команд на самом деле ведет себя довольно твердо, подчиняясь своей внутренней логике, вам просто нужно переосмыслить вещи.

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

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

set myvar=some text   
set myvar="some text" 

например Оба приведенных ниже хороших метода для установки переменных в интерпретаторе команд Windows, однако метод двойных кавычек лучше:

set "myvar=Some text"
(set myvar=Some value)

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

сильный текст Однако, для ваших целей, только указанный метод будет работать корректно, потому что вы используете зарезервированный символ

Таким образом, вы будете использовать:

set myvar="c:\my music & videos"

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

Поэтому, если вы хотите вывести строку из переменной, интерпретатору CMD все равно нужно сообщить, что это текстовая строка, или если вы не хотите, чтобы в кавычках показывалось, вы должны выполнить одно из следующих действий:

выводим переменную WITH Quotes:

Echo."%myvar%"

выводим переменную БЕЗ Кавычек:

Echo.%myvar:&=^&%
<nul SET /P="%myvar%"

В приведенных выше двух сценариях вы можете просто повторить строку без кавычек. Пример вывода ниже:

C:\Admin>    Echo.%myvar:&=^&%
C:\my music & videos

C:\Admin>    <nul SET /P="%myvar%"
C:\my music & videos
C:\Admin>
2
Ben Personick

Вы должны иметь кавычки, если текст, который вы устанавливаете, содержит определенные символы, включая &. Если ваш текст не содержит &, тогда вам не нужны кавычки.

Например, если бы текст был просто "c:\my music", то вы могли бы сделать:

set myvar = c:\my music

Но поскольку в вашем тексте есть &, вам нужны кавычки.

Edit:

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

1
andynormancx

Попробуйте использовать escape-символ "^", например.

set myvar=c:\my music ^& videos

Вы будете осторожны, когда расширяете myvar, потому что Shell может не рассматривать & как литерал. Если вышеприведенное не работает, попробуйте вставить каретку в строку:

set myvar=c:\my music ^^^& videos
1
Dave