2016-11-13 41 views
0

引述長filenamed命令在for循環中鏈接的批處理文件

Best free resource for learning advanced batch-file usage?

Dealing with quotes in Windows batch scripts

這似乎是那些發瘋報價問題之一。在這個示例程序中:

@echo off 
set wmicpath=%windir%\System32\wbem\wmic.exe 

for /f "usebackq" %%a in (`%wmicpath% COMPUTERSYSTEM GET SystemType ^| findstr /I "x64"`) do (
    echo %%a 
) 

該程序運行得很好。除非你試圖引用wmicpath。想象一下,如果你會認爲它包含一個長路徑名稱。那麼你應該引用它。但我無法完成它的工作。這種失敗:

for /f "usebackq" %%a in (`"%wmicpath%" COMPUTERSYSTEM GET SystemType ^| findstr /I "x64"`) do (

但這個工程!:

for /f "usebackq" %%a in (`"%wmicpath%" COMPUTERSYSTEM GET SystemType ^| findstr /I x64`) do (

爲做到這一點:

for /f "usebackq" %%a in (`"%wmicpath%" COMPUTERSYSTEM GET SystemType`) do (

有一些非常奇怪的有關在爲命令匹配報價。只要你不在別處開始引用,你可以引用命令...

這可能嗎?我試圖在不同的點逃脫,但我不知道什麼時候行情所涉及的轉義規則...

編輯:我覺得這個環節可能是問題(即:這是一個錯誤):Pipe in for loop breaks double quoted variables

回答

2
@echo off 
    setlocal enableextensions disabledelayedexpansion 
    set "wmicpath=%windir%\System32\wbem\wmic.exe" 

    for /f "usebackq delims=" %%a in (` 
     ^""%wmicpath%" COMPUTERSYSTEM GET SystemType ^| findstr /I "x64"^" 
    `) do (
     echo %%a 
    ) 

如果你看一下開始和內部命令的結束,你會看到兩個額外的^"(一逃脫雙引號)。您的問題是for命令生成一個單獨的實例cmd來處理內部命令,並且這個單獨的實例將刪除最初和最後一個雙引號。

爲什麼要逃脫報價?爲了避免這些額外的引號與命令中的雙引號配對,這可能導致其他一些解析問題。

您可以運行cmd /?獲取幫助頁面(對不起,我有一個西班牙語語言環境,所以我不會在這裏包括輸出)。您會看到一段關於/C/K的用法,解釋了引用移除行爲。

+0

非常好!謝謝。我在昨天凌晨1點左右就想出了我自己,但不知道究竟爲什麼或在哪裏記錄了它(如果有的話)。我認爲這是一個錯誤,但正如你所說,它與最初和最後的雙引號相匹配。 – carveone

0
>x64.txt ECHO x64 

for /f "usebackq" %%a in (`"%wmicpath%" COMPUTERSYSTEM GET SystemType ^| findstr /I /g:x64.txt`) do (

可能是一種解決方法,具體取決於您的實際應用和偏好。

+0

findstr在這方面非常靈活,但通常我會避免創建外部文件。 – carveone

1

首先,我會改變命令,WMIC允許你使用查詢語言LIKE運算符,在這種情況下可以刪除管道任何東西的需要。

@Echo Off 
Set "WMIC=%SystemRoot%\System32\Wbem\wmic.exe" 
For /F "UseBackQ Skip=1" %%a In (
    `""%WMIC%" ComputerSystem Where "SystemType Like 'x64%%'" Get SystemType"` 
) Do For %%b In (%%a) Do Echo=%%b 
Timeout -1 

然後我可能甚至改變命令,使得我不使用反引號的格式。

@Echo Off 
Set "WMIC=%SystemRoot%\System32\Wbem\wmic.exe" 
For /F "Skip=1" %%a In (
    '""%WMIC%" ComputerSystem Where (SystemType Like "x64%%") Get SystemType"' 
) Do For %%b In (%%a) Do Echo=%%b 
Timeout -1 

雖然這並不直接回答主旨題的問題,它允許您的特定命令才能正常工作。

但既不是必要的,您的特定命令的例子,因爲你並不需要在for循環呼應的是輸出:

@Echo Off 
Set "WMIC=%SystemRoot%\System32\Wbem\wmic.exe" 
"%WMIC%" ComputerSystem Get SystemType|Find /I "x64" 
Timeout -1 

更改查找FINDSTR如果你覺得有必要。

+0

你是對的WMIC。做得很好。我猜如果我以某種方式做某件事情,即使效率不高,我仍然會這樣做。我認爲他們稱之爲懶惰:-)你對我的例子是正確的,但在我的實際代碼中,我存儲輸出並進一步使用它。 – carveone

+1

我接受你可能是這樣做的,但是,據我所知,只有根據你的問題選擇的命令才能輸出以下內容,並找到標準'x64-based'。出於這個原因,你可以使用'&&'後面的例子來設置成功。 '「%WMIC%」ComputerSystem Get SystemType | Find/I「x64」> Nul &&(Set var = x64-based)'。 – Compo