且构网

分享程序员开发的那些事...
且构网 - 分享程序员编程开发的那些事

如何在环境变量PATH中搜索和替换字符串?

更新时间:2022-10-31 08:05:57

h2>本地PATH替换

wmz 提供的解决方案完美:

  setPATH =%PATH:Python24 = Python27%
/ pre>

有关在命令提示符窗口中运行的环境变量值的替换的详细信息 set /?在关于




  • 设置 - Microsoft TechNet页面

  • 设置 - Windows XP产品文档页面



在创建新进程(如运行批处理文件时的命令行解释器进程)时,Windows会创建父进程的环境变量表(Windows资源管理器作为桌面)的副本。对环境变量表进行的每个修改都仅应用于此副本,从而避免对其他已在运行的应用程序造成影响。只是从这个过程调用的应用程序获得修改的环境变量表(作为新进程启动时的副本)。






系统PATH替换



设置或更改系统范围可变的解决方案是使用命令 setx (set extended)。



问题如何在Windows批处理文件中使用setx命令大约有相同的要求:

如何在环境变量 PATH 系统范围内替换Python版本?



Microsoft在关于命令的引用页面上写了 setx


Setx 将变量写入注册表中的主环境。使用setx变量设置的变量仅在未来的命令窗口中可用,而不是在当前命令窗口中。


这意味着如果在使用 setx 之后从同一控制台窗口执行Python脚本,则还必须使用命令修改局部 PATH 设置。已在使用 setx 更改目录列表运行的其他控制台或GUI进程的其他环境变量 PATH 实例不会被 setx



但是,如果 PATH 变量的更改应该被修改,那么必须终止并重新启动这些进程。完全系统和永久只在本地计算机上,只有一次,通常通过控制面板 - 系统比使用命令 setx


$ b b b b b b b b b p>这是一个关于如何在本地和系统环境变量 PATH 中替换Python版本的示例。作为一个额外的功能,如果 PATH 中缺少Python目录的路径,则会附加该路径。
  @echo off 

rem在本地环境变量PATH中用Python27替换Python24。
setNEWPATH =%PATH:Python24 = Python27%

rem如果不包含C:\Python27,则将C:\Python27附加到PATH。
如果%NEWPATH:Python27 =%==%PATH%setNEWPATH =%PATH%; C:\Python27

rem更新系统环境表中的PATH。
setx PATH%NEWPATH%/ M

rem在此控制台窗口中更新本地PATH。 (重要:没有双引号!)
路径%NEWPATH%

rem删除不再需要的本地环境变量NEWPATH。
set NEWPATH =

rem本地环境变量PATH的输出值。
path

延迟扩展的替代代码:

  @echo off 
setlocal EnableDelayedExpansion

rem在本地环境变量PATH中用Python27替换Python24。
setNEWPATH =!PATH:Python24 = Python27!

rem如果不包含C:\Python27,则将C:\Python27附加到PATH。
if!NEWPATH:Python27 =!==!PATH!设置NEWPATH =!PATH!; C:\ Python27

rem更新系统环境表中的PATH。
setx PATH!NEWPATH! / M

rem在此控制台窗口中更新本地PATH。 (重要:没有双引号!)
路径%NEWPATH%

rem删除不再需要的本地环境变量NEWPATH。
set NEWPATH =

rem本地环境变量PATH的输出值。
path

endlocal

请注意, PATH 不仅是一个环境变量,也是一个内部命令。在命令提示符窗口中输入帮助路径 path /? / p>

命令 path 此处用于更新环境变量 PATH code> path%NEWPATH%并显示局部环境变量 PATH 中的目录与示例批处理文件的最后一行。



在命令 setx 上,%NEWPATH%下的双引号非常重要,因为 PATH 最有可能还包含一个或多个目录路径,其中有一个空格。因此,应该分配给系统环境变量 PATH 的整个字符串必须用双引号括起。



但是命令 path 需要带有目录路径的字符串,而且不会包含双引号,即使在字符串中有空格字符,因为此命令不期望或支持除目录路径列表之外的其他选项(以及开发人员命令 path 的代码很可能没有考虑在字符串的开头和结尾删除双引号,如果用户包围该字符串,像往常一样几乎所有其他命令双。



上述批处理文件的缺点是:


  1. p> PATH 包含所有已经展开的环境变量的目录,因此系统 PATH 不再包含%SystemRoot%$

  2. 在当前命令过程或任何父进程中添加到本地 PATH 的其他目录也添加到系统 PATH


更新系统的更好解决方案 PATH



为什么也是其他文件夹路径添加到使用SetX的系统PATH中,而不仅仅是指定的文件夹路径?



所以更好的批处理代码替换 Python24 在本地和系统 PATH 中的Python27 是:

  @echo off 
setlocal EnableDelayedExpansion

rem定义一个变量Separator以分号作为值如果
rem本地PATH字符串尚未结束分号。
setSeparator =
如果没有%PATH:〜-1%==;设置Separator =;

rem在本地环境变量PATH中用Python27替换Python24。
setLocalPath =!PATH:Python24 = Python27!

rem如果不包含C:\Python27,则将C:\Python27附加到本地PATH。
if!LocalPath:Python27 =!==!PATH!设置LocalPath =!PATH!%Separator%C:\Python27

rem在此控制台窗口中更新此命令过程的本地PATH。
setPATH =%LocalPath%

rem本地环境变量PATH的输出值。
path

rem直接从Windows注册表获取系统PATH以获取
rem不包含扩展环境变量的目录列表。
for / Fskip = 2 tokens = 3%% P in('%SystemRoot%\System32\reg.exe queryHKLM \System\CurrentControlSet\Control\Session Manager\环境/ vPath2 ^> nul')do(
setSystemPath = %% P
goto CheckPath

echo错误:系统环境变量PATH未找到。
echo。
endlocal
暂停
goto:EOF

:CheckPath
rem定义一个变量Separator,以分号作为值,如果
rem系统PATH字符串不以分号结束。
setSeparator =
如果没有%SystemPath:〜-1%==;设置Separator =;

rem在系统环境变量PATH中用Python27替换Python24。
setNewPath =!SystemPath:Python24 = Python27!

rem如果不包含C:\Python27,则将C:\Python27附加到系统PATH。
if!NewPath:Python27 =!==!SystemPath! setNewPath =!SystemPath!%Separator%C:\Python27

rem如果需要进行任何更改,请更新系统路径。
如果不是!SystemPath! ==!NewPath! (
%SystemRoot%\System32\setx.exe PATH%NewPath%/ M


rem系统环境变量PATH的输出值。
echo PATH =%NewPath%

endlocal

使用的命令及其如何工作,打开命令提示符窗口,执行以下命令,并仔细阅读所有为每个命令显示的帮助页面。




  • echo /?

  • endlocal /? li>
  • for /?

  • goto /?

  • if /?

  • / code>

  • 暂停/?

  • rem /?

  • reg query /?

  • code> set /?

  • setlocal /?

  • setx /?


Is there any command in batch to search and replace a string in environment variable PATH?

For example the contents of environment variable PATH is:

C:\windows\system32;C:\windows;C:\windows\System32\Wbem;C:\windows\System32\WindowsPowerShell\v1.0\;C:\Program Files\AccuRev\bin;C:\Python24

I have to search for C:\Python24 in this variable and need to replace it by C:\Python27.

Local PATH replacement

The solution provided by wmz is perfect:

set "PATH=%PATH:Python24=Python27%"

For details about replacements in values of environment variables run in a command prompt window set /? or look on the Microsoft pages about

  • Set - Microsoft TechNet page
  • Set - Windows XP product documentation page

On creation of a new process, like the command line interpreter process on running a batch file, Windows creates a copy of the environment variables table of the parent process (Windows Explorer as desktop). Every modification made on the environment variables table are applied only on this copy which avoids impacts on other already running applications. Just applications called from this process get the modified environment variables table (as copy when started as new process).


System PATH replacement

The solution to set or change a variable system wide is the usage of command setx (set extended).

The question How to use setx command in a windows batch file is about same requirement:
How to replace the version of Python in environment variable PATH system wide?

Microsoft wrote on referenced page about command setx:

Setx writes variables to the master environment in the registry. Variables set with setx variables are available in future command windows only, not in the current command window.

This means if Python scripts are executed from same console window after using setx, the local PATH must be also modified using command set. Other instances of environment variable PATH of other console or GUI processes already running on using setx to change the list of directories are not modified by setx. Those processes must be terminated and restarted to take note of changes made on master environment table.

But if the change of the PATH variable should be done system wide and permanently on local computer only and only once, it is often easier to do this via Control Panel - System than doing it with command setx from command line.


Local and system PATH replacement example

Here is an example on how to replace version of Python in local and system environment variable PATH. As an extra feature the path of Python directory is appended if missing in PATH.

@echo off

rem Replace Python24 by Python27 in local environment variable PATH.
set "NEWPATH=%PATH:Python24=Python27%"

rem Append C:\Python27 to PATH if not containing C:\Python27 at all.
if "%NEWPATH:Python27=%"=="%PATH%" set "NEWPATH=%PATH%;C:\Python27"

rem Update PATH in system environment table.
setx PATH "%NEWPATH%" /M

rem Update local PATH in this console window. (Important: No double quotes!)
path %NEWPATH%

rem Remove local environment variable NEWPATH as not needed anymore.
set NEWPATH=

rem Output value of local environment variable PATH.
path

Alternate code with delayed expansion:

@echo off
setlocal EnableDelayedExpansion

rem Replace Python24 by Python27 in local environment variable PATH.
set "NEWPATH=!PATH:Python24=Python27!"

rem Append C:\Python27 to PATH if not containing C:\Python27 at all.
if "!NEWPATH:Python27=!"=="!PATH!" set "NEWPATH=!PATH!;C:\Python27"

rem Update PATH in system environment table.
setx PATH "!NEWPATH!" /M

rem Update local PATH in this console window. (Important: No double quotes!)
path %NEWPATH%

rem Remove local environment variable NEWPATH as not needed anymore.
set NEWPATH=

rem Output value of local environment variable PATH.
path

endlocal

Please note that PATH is not only an environment variable, but also an internal command. Type in a command prompt window either help path or path /? to get short help for this little command displayed.

The command path is used here to update local instance of environment variable PATH with path %NEWPATH% and to display the directories in local environment variable PATH with last line of the example batch file.

On line with command setx the double quotes around %NEWPATH% are very important as PATH most likely contains also 1 or more directory paths with a space inside. Therefore the entire string which should be assigned to system environment variable PATH must be in double quotes.

But the command path requires the string with the directory paths always without surrounding double quotes even with space characters inside the string simply because this command does not expect or support other options than the list of directory paths (and the developer who wrote the code for command path did most likely not think about removing the double quotes at beginning and end of the string if a user surrounded the string as usual for nearly all other commands with double quotes).

The disadvantages of the batch files above are:

  1. Local PATH contains the directories always with all environment variables already expanded and therefore system PATH does not have anymore for example %SystemRoot% in list of directories.

  2. Additional directories added to local PATH in current command process or any parent process would be also added to system PATH.

A better solution to update system PATH is explained in answer on

Why are other folder paths also added to system PATH with SetX and not only the specified folder path?

So a better batch code to replace Python24 by Python27 in local and system PATH is:

@echo off
setlocal EnableDelayedExpansion

rem Define a variable Separator with a semicolon as value if
rem the local PATH string does not end already with a semicolon.
set "Separator="
if not "%PATH:~-1%" == ";" set "Separator=;"

rem Replace Python24 by Python27 in local environment variable PATH.
set "LocalPath=!PATH:Python24=Python27!"

rem Append C:\Python27 to local PATH if not containing C:\Python27 at all.
if "!LocalPath:Python27=!"=="!PATH!" set "LocalPath=!PATH!%Separator%C:\Python27"

rem Update local PATH for this command process in this console window.
set "PATH=%LocalPath%"

rem Output value of local environment variable PATH.
path

rem Get system PATH directly from Windows registry to get
rem the directory list with not expanded environment variables.
for /F "skip=2 tokens=3" %%P in ('%SystemRoot%\System32\reg.exe query "HKLM\System\CurrentControlSet\Control\Session Manager\Environment" /v "Path" 2^>nul') do (
    set "SystemPath=%%P"
    goto CheckPath
)
echo Error: System environment variable PATH not found.
echo.
endlocal
Pause
goto :EOF

:CheckPath
rem Define a variable Separator with a semicolon as value if
rem the system PATH string does not end already with a semicolon.
set "Separator="
if not "%SystemPath:~-1%" == ";" set "Separator=;"

rem Replace Python24 by Python27 in system environment variable PATH.
set "NewPath=!SystemPath:Python24=Python27!"

rem Append C:\Python27 to system PATH if not containing C:\Python27 at all.
if "!NewPath:Python27=!"=="!SystemPath!" set "NewPath=!SystemPath!%Separator%C:\Python27"

rem Update system PATH if any change is necessary at all.
if not "!SystemPath!" == "!NewPath!" (
    %SystemRoot%\System32\setx.exe PATH "%NewPath%" /M
)

rem Output value of system environment variable PATH.
echo PATH=%NewPath%

endlocal

For understanding the used commands and how they work, open a command prompt window, execute there the following commands, and read entirely all help pages displayed for each command very carefully.

  • echo /?
  • endlocal /?
  • for /?
  • goto /?
  • if /?
  • path /?
  • pause /?
  • rem /?
  • reg query /?
  • set /?
  • setlocal /?
  • setx /?