如何在windows命令提示符下对变量执行字符串替换?

如何在windows命令提示符下对变量执行字符串替换?,windows,batch-file,cmd,registry,batch-processing,Windows,Batch File,Cmd,Registry,Batch Processing,是否有一种方法可以在命令提示符下代替批处理文件中的字符串替换 一点背景:不久前,我需要注册一个自定义URI协议,通过注册表黑客将调用的url转发给Chrome,结果: Windows Registry Editor Version 5.00 [HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CNX] @="Chrome HTML Document" "URL Protocol"="" [HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CNX\D

是否有一种方法可以在命令提示符下代替批处理文件中的字符串替换

一点背景:不久前,我需要注册一个自定义URI协议,通过注册表黑客将调用的url转发给Chrome,结果:

Windows Registry Editor Version 5.00 [HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CNX] @="Chrome HTML Document" "URL Protocol"="" [HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CNX\DefaultIcon] @="C:\\Program Files (x86)\\Google\\Chrome\\Application\\chrome.exe,0" [HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CNX\shell] [HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CNX\shell\open] [HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CNX\shell\open\command] @="cmd /c cd \"C:\\Program Files (x86)\\Google\\Chrome\\Application\\\" & FOR /f \"tokens=1-3delims=?#\" %%a IN (\"%1\") DO (if \"%%a#%%b%%c\"==\"%1\" (chrome.exe %1) else (chrome.exe %%a#%%c%%b) )" [HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\Internet Explorer\ProtocolExecute\CNX] "WarnOnOpen"=dword:00000000 在IE中,现在变成了

cnx://%20www.someurl.com cnx://%20www.someurl.com 当命令执行时

因此,我想知道是否有一种方法可以在某个地方进行字符串替换,并从我的
%%a
变量中完全删除
cnx://%20


但我所有的尝试都没有成功。听到或读到这根本不可能,我会很高兴,这样我就可以停止旋转轮子了。

解决方案在Windows注册表文件中使用:

@="cmd.exe /V:ON /C cd /D \"C:\\Program Files (x86)\\Google\\Chrome\\Application\\\" & set \"url=%1\" & set \"url=!url:cnx://%%20=!\" & set \"url=!url:cnx://=!\" & for /F \"tokens=1-3 delims=?#\" %%a in (\"!url!\") do if \"%%a#%%b%%c\"==\"!url!\" (chrome.exe \"!url!\") else (chrome.exe \"%%a#%%c%%b\")"
这将导致Windows注册表中出现以下命令行:

cmd.exe /V:ON /C cd /D "C:\Program Files (x86)\Google\Chrome\Application\" & set "url=%1" & set "url=!url:cnx://%%20=!" & set "url=!url:cnx://=!" & for /F "tokens=1-3 delims=?#" %%a in ("!url!") do if "%%a#%%b%%c"=="!url!" (chrome.exe "!url!") else (chrome.exe "%%a#%%c%%b")
重要的是Windows命令处理器选项
/V:ON
,该选项在命令提示符窗口
cmd/?
中运行时启用环境变量的帮助输出。选项
/V:ON
必须分别在选项
/C
(执行命令行后关闭)左侧指定
/K
(在执行命令行后保持命令进程运行),因为
/C
/K
之后的所有内容都被解释为要执行的命令行的一部分

使用
/K
而不是
/C
可以查看执行此命令行时发生的情况,并且用户可以在命令行执行完成后执行
设置url
,以查看环境变量
url
的最终值

在cmd窗口中运行时的帮助输出
set/?
解释了何时以及如何使用延迟环境变量扩展。如果在命令行上定义或修改了环境变量,并且在同一命令行上引用了环境变量,则必须使用它。如果在命令块中定义或修改了环境变量(以
开头)(
并以匹配
结尾),则也有必要这样做
因为
cmd.exe
解析整个命令块,并在执行此命令块的任何命令之前,用引用环境变量的当前值替换所有
%variable%
引用,或在同一命令行上左移到命令块的开头

另见

必须使用
引用环境变量!变数在启用延迟扩展后延迟扩展此引用

注意:即使在双引号参数字符串中启用,命令行中的每个感叹号也会被解释为延迟扩展环境变量引用的开始/结束

具有(几乎)相同代码的已注释批处理文件应为:

@echo off
rem Explicitly enable command extensions although enabled by default
rem and delayed environment variable expansion disabled by default.
setlocal EnableExtensions EnableDelayedExpansion

rem Change current directory to directory containing Google Chrome browser.
cd /D "%ProgramFiles(x86)%\Google\Chrome\Application\"

rem Define environment variable url with value of first
rem argument with surrounding double quotes removed.
set "url=%~1"

rem Exit batch file if called without any argument or with just "".
if not defined url goto EndBatch

rem Remove case-insensitive all occurrences of string "cnx://"
rem with an additional percent encoded space from the url argument.
set "url=!url:cnx://%%20=!"

rem Remove case-insensitive all occurrences of string "cnx://".
set "url=!url:cnx://=!"

rem Split up the url strings on question mark and hash and assign just
rem first three ?# delimited substrings to loop variables a, b and c.
rem FOR would not run any command in command block on url starting with
rem a semicolon. Run Google Chrome with the url if first substring with #
rem and the two other substrings appended is case-sensitive equal the url.
rem Otherwise run Google Chrome with redefined url with second and third
rem substring exchanged after first substring and hash character.
for /F "tokens=1-3 delims=?#" %%a in ("!url!") do (
    if "%%a#%%b%%c" == "!url!" (
        start "" chrome.exe "!url!"
    ) else (
        start "" chrome.exe "%%a#%%c%%b"
    )
)

rem Restore initial environment on calling the batch file which means
rem discarding all environment variables defined or modified in block
rem above like environment variable url, restore initial current directory
rem as it was before using command CD and restore also initial states of
rem command extensions (most likely enabled) and delayed expansion (most
rem likely disabled).
:EndBatch
endlocal
@echo off
rem Explicitly enable command extensions although enabled by default
rem and delayed environment variable expansion disabled by default.
setlocal EnableExtensions EnableDelayedExpansion

rem Change current directory to directory containing Google Chrome browser.
cd /D "%ProgramFiles(x86)%\Google\Chrome\Application\"

rem Define environment variable url with value of first
rem argument with surrounding double quotes removed.
set "url=%~1"

rem Exit batch file if called without any argument or with just "".
if not defined url goto EndBatch

rem Remove case-insensitive all occurrences of string "cnx://"
rem with an additional percent encoded space from the url argument.
set "url=!url:cnx://%%20=!"

rem Remove case-insensitive all occurrences of string "cnx://".
set "url=!url:cnx://=!"

rem Split up the url strings on question mark and hash and assign just
rem first three ?# delimited substrings to loop variables a, b and c.
rem FOR would not run any command in command block on url starting with
rem a semicolon. Run Google Chrome with the url if first substring with #
rem and the two other substrings appended is case-sensitive equal the url.
rem Otherwise run Google Chrome with redefined url with second and third
rem substring exchanged after first substring and hash character.
for /F "tokens=1-3 delims=?#" %%a in ("!url!") do (
    if "%%a#%%b%%c" == "!url!" (
        start "" chrome.exe "!url!"
    ) else (
        start "" chrome.exe "%%a#%%c%%b"
    )
)

rem Restore initial environment on calling the batch file which means
rem discarding all environment variables defined or modified in block
rem above like environment variable url, restore initial current directory
rem as it was before using command CD and restore also initial states of
rem command extensions (most likely enabled) and delayed expansion (most
rem likely disabled).
:EndBatch
endlocal