WindowsでPATH環境変数が過剰に設定されないようにするにはどうすればよいですか?


115

システムで実行可能ファイルを管理するために使用するアプローチを教えてください。たとえば、コマンドラインからほとんどすべてにアクセスできますが、パス文字列の制限に達したため、dirを追加できません。

それで、あなたは何を勧めますか?ずっと前に、パスに属するDirで実行可能ファイルのソフトリンクを使用しようとしましたが、そのアプローチは機能しませんでした。既知のディレクトリに「実行可能ファイルのみ」を投げると、ほとんどすべてのアプリケーションが一連のファイルを必要とするという問題があり、これも悪いことです。実行可能ファイルとそのすべてのファイルを既知のDirにスローします。これは機能しますが、ファイル名の競合が発生する可能性は非常に高くなります。HardLinkを作成しますか?知りません。どう思いますか?


なぜそんなに多くのパスを使うのですか?パスは通常、アプリが他のユーザーと拡張オブジェクト/アプリ/ライブラリを共有する必要がある場合に、共通ディレクトリに使用されます。あまりにも多く使用すると、アプリの起動が遅くなります。パス環境変数を作成して使用する方法について詳しく教えてください。
pinichi

1
こんにちはpinichiさん、多くのアプリケーションは標準の「C:\ Program File \ AppNAme \ ...」を使用しています。私の場合、このアプリケーションの多くはコマンドライン形式で実行できるか、他のアプリからアクセスできる必要があります(たとえば、Texエディターが存在することを期待しているMiktexの実行可能ファイル)、したがって、それらはPATHに含まれている必要があります。私は私が持続不可能であるため、より良いアプローチを知ってwan't
mjsr

1
このツールはパスを圧縮します。結果は印象的です:uweraabe.de/Blog/2014/09/09/the-garbled-path-variable/#more-337
InTheNameOfScience

回答:


84

私が考えることができる1つの方法は、他の環境変数を使用して部分パスを格納することです。たとえば、

C:\this_is_a\long_path\that_appears\in_multiple_places\subdir1;
C:\this_is_a\long_path\that_appears\in_multiple_places\subdir2;

次に、次のような新しい環境変数を作成できます

SET P1=C:\this_is_a\long_path\that_appears\in_multiple_places

その後、元のパスは

%P1%\subdir1;
%P1%\subdir2;

編集:別のオプションは、適切なファイルを指すファイルをbin保持するディレクトリを作成する.batこと.exeです。

編集2:別の回答へのBen Voigtのコメントは、提案されたように他の環境変数を使用%PATH%しても、格納される前に拡張されるため、長さが短縮されない可能性があると述べています これは本当かもしれません、そして私はそれについてテストしていません。ただし、より長いディレクトリ名に8dot3形式を使用することもできます。たとえばC:\Program Files、通常はと同等C:\PROGRA~1です。を使用dir /xして、短い名前を表示できます。

編集3:この簡単なテストにより、ベンフォイトが正しいと信じるようになりました。

set test1=hello
set test2=%test1%hello
set test1=bye
echo %test2%

この最後に、hellohelloではなく出力が表示されますbyehello

編集4:から特定のパスを排除するためにバッチファイルを使用することにした場合%PATH%、プロセスが透過的であるようにバッチファイルから実行可能ファイルに引数を渡す方法が気になるかもしれません(つまり、違いに気付かないでしょう)バッチファイルの呼び出しと実行可能ファイルの呼び出しの間)。バッチファイルの作成についてはあまり経験がありませんが、これで問題なく動作するようです。

@echo off

rem This batch file points to an executable of the same name
rem that is located in another directory. Specify the directory
rem here:

set actualdir=c:\this_is\an_example_path

rem You do not need to change anything that follows.

set actualfile=%0
set args=%1
:beginloop
if "%1" == "" goto endloop
shift
set args=%args% %1
goto beginloop
:endloop
%actualdir%\%actualfile% %args%

ハードドライブのフォーマットなど、バッチファイルを使用してあらゆる種類の操作を実行できるため、インターネットからのバッチファイルの実行には注意が必要です。上記のコード(私が書いたコード)が信頼できない場合は、次の行を置き換えることでテストできます

%actualdir%\%actualfile% %args%

echo %actualdir%\%actualfile% %args%

理想的には、実行する前に、すべての行が何を行うかを正確に知っている必要があります。


1
8dot3フォームは適切に機能しますが、実際のディレクトリはそれほど大きくありません。たとえば、「C:\ Program Files(x86)\ Microsoft Visual Studio 2008 SDK \ VisualStudioIntegration \ Tools \ Sandcastle \ ProductionTools \」のようになります。少し節約できるもう1つの点は、ユーザーとして、システムパスに基づいてPATH変数を作成し、他のディレクトリを追加できることです。このアプローチはすべて「コンパクトストリング」タイプですが、Unixのように、バイナリの集中ディレクトリを作成できますか?
mjsr

1
うーん、非常に長いディレクトリに関しては、反対のことが当てはまると思います。ディレクトリが長いほど、8dot3形式を使用して保存する文字数が多くなります。をナビゲートするのが難しい場合はcmd、を使用*して入力を保存できることに注意してください。たとえば、ルートからと入力しdir /x pro*ます。そこに、8dot3の名前とともに目的のディレクトリが表示されます。次に、を使用cdしてそこに移動し、プロセスを繰り返します。
ミッチシュワルツ

1
UNIXについては、Windowsと$PATH非常によく似た%PATH%ものがあり、正確に何を言っているのかわかりません。慣例により、UNIXのディレクトリ名はWindowsの場合よりも短くなる傾向があり、その結果として$PATHも短くなる傾向があります。
ミッチシュワルツ

2
Mitchに感謝します。あなたが提供するEdit 4は私が欲しかったものです!私はいくつかのアプリに問題があるかどうかを確認するために、深い、よりをテストするつもりだ
mjsr

2
「編集4」セクションは、実行可能ファイルに引数を渡すために非常に複雑です。Michael Burrの回答を参照してください。
Dave Andersen、

83

これにより、%PATH%環境変数が解析され、各ディレクトリが対応する短縮名に変換されてから、すべてが組み合わされます。

@echo off

SET MyPath=%PATH%
echo %MyPath%
echo --

setlocal EnableDelayedExpansion

SET TempPath="%MyPath:;=";"%"
SET var=
FOR %%a IN (%TempPath%) DO (
    IF exist %%~sa (
        SET "var=!var!;%%~sa"
    ) ELSE (
        echo %%a does not exist
    )
)

echo --
echo !var:~1!

出力を取得し、環境変数のPATH変数を更新します。


とても役に立ちましたありがとうございます!それは私の道を1990年から1338年に短縮し、すべてがまだ魅力のように動作します!私はすべてを自分のパスに留めておきたかったので、あなたのアプローチを選択しました。ありがとう!
ndrizza 14

2
これは、時間の経過とともに蓄積された、パス内に存在しないすべてのディレクトリについて通知するので、これも役に立ちました。
ネイトグレン

27
Rapid Environment Editorはこれを行う別の方法です。存在しないディレクトリを強調表示し、「長いパスを短いパスに変換する」オプションがあります。
ラッセルギャロップ

3
@RussellGallop:これはすばらしいツールです。
elo80ka 14

1
の後ろに閉じ引用符がないことに注意してください%%~sa。私は答えを更新しようとしましたが、私は6つの文字に変更しない限り、それは私をさせません
zr870

28

Windows Vista以降を使用している場合は、フォルダへのシンボリックリンクを作成できます。例えば:

mklink /d C:\pf "C:\Program Files"

リンクを作成するのでc:\pfprogram filesフォルダになります。このトリックを使って、パスから300文字を削り取りました。


これは、部分的なパスを表すために環境変数を使用する優れた代替手段です。
porcus

1
これは間違いなく、より役立つだろうが、あなたはより多くの「正しい」(サポートされていますか?)ソリューションをたい場合、あなたはのインスタンス置き換えることができます c:\Program Filesし、c:\Program Files (x86)事前に定義された変数とする%ProgramFiles%%ProgramFiles(x86)% tenforums.com/tutorials/...これらのほんの数文字を保存し、各、しかし本当にあなたが本当にPATHを最大化する寸前にいるなら、それは違いかもしれません。そのため、正しいパスに解決される%pf%と%pfx%を作成します。アイデアをありがとう!:)
Rainabba 2016

%pf%や%pfx%などの変数を使用する場合の問題は、シンボリックリンクの作成と同じ問題が発生することです。ソフトウェアの更新により、パス変数に再度追加される場合があります。このような変数を使用する場合のもう1つの問題は、スクリプトを作成したり、エクスプローラーから変数を参照したりするのが迅速かつ簡単ではないことです。説明した方法を使用すると、文字通りc:\ PFを開くことができます。Windowsはそれをフォルダのように見ているので、バットやパワーシェルを簡単に書くことができます。
bmg002

10

誰かが興味を持っている場合には...

これらのパスを一度に本当に必要とすることは決してないので、それに応じてパスを変更する一連の「初期化」バッチファイルを作成します。

たとえば、EclipseでC ++開発を行いたい場合は、次のようにします。

> initmingw
> initeclipse
> eclipse

これは、同じ名前の実行可能ファイル(C ++コンパイラとDコンパイラなど、両方にmake.exeがある)間の競合を回避するのにも便利です。

私のバッチファイルは通常、次のようになります。

@echo off
set PATH=C:\Path\To\My\Stuff1;%PATH%
set PATH=C:\Path\To\My\Stuff2;%PATH%

このアプローチは比較的クリーンで、まだ問題が発生していません。


7

私は通常、これについて心配する必要はありません(パスサイズの制限に遭遇したことはありません-最新のWindowsシステムでそれが何であるかさえわかりません)が、プログラムのディレクトリを配置しないようにするために私ができることは次のとおりですパス:

  • ほとんどのコマンドラインユーティリティc:\utilは、パス上のディレクトリにスローされます
  • それ以外の場合は、次のような単純なcmd / batchファイルをc:\utilディレクトリに追加します。

    @"c:\program files\whereever\foo.exe" %*
    

これは基本的にコマンドのエイリアスを作成します。必ずしも完璧ではありません。一部のプログラムはパスにいることを強く要求します(これは今日では非常にまれです)。それを呼び出そうとする他のプログラムは、正しくパスを見つけられない場合があります。しかし、ほとんどの用途でそれはうまく機能します。

しかし、一般的に、パスにディレクトリを追加しないようにすることについて心配する必要はありませんでした。


この「パス」をたどるときは、バッチスクリプトが「CALL [bat]」構文なしで別のバッチスクリプトを呼び出せないことに注意してください。したがって、転送または非実行のexeがバットから呼び出されるようにしたい場合は、「php script.php」ではなく「call php script.php」を使用してください(両方の方法で動作します)。バットディスパッチャーはPATH名の競合を防ぐためのものです(同じexeの複数バージョン)
131

@ 131:「この「パス」」の意味を説明してもらえますか?例の特定のファイルパスを意味しますか?または、この回答で提案されている一般的な方法ですか?
またはMapper

@ORMapper:131が「この「パス」をたどるとき」と言ったとき、彼は「このテクニックを使うとき」を意味します。
マイケルバー2015

1
あなたが書いたように、「それを呼び出そうとする他のプログラムは、それを適切に見つけられない可能性があります」-適例:残念ながら、それはもちろん、例えばNAntなどのビルドツールによるコマンドラインアプリケーションへの自動呼び出しをスローする可能性があります。解決策は、コマンドを先頭に追加して呼び出すことですがcmd /c、これは、ビルドスクリプトがWindows固有になることを意味します:/ 別の質問でそれについて質問しました
またはMapper、2015

5

別のアイデア:DIR / Xを使用して、8dot3以外のファイル名に対して生成される短い名前を決定します。次に、これらを%PATH%で使用します。

たとえば、「C:\ Program Files」は「C:\ PROGRA〜1」になります。


1
おっと、これはすでに@Mitchによって提案されていることに気づきました。私は彼に+1を与えるつもりです。:)
Android Eve


2

私が書いたと、使用ごと、時間ごとに(ディスパッチャと呼ばれる標準ストリーム(STDIN /標準エラー出力/標準出力)&終了コードPROXYプログラムhttps://github.com/131/dispatcher

私が使用するすべてのCLIプログラム(node、php、python、git、svn、rsync、plink ...)私が使用しているのは、実際には同じexeファイル(約10kb、名前が違うだけです)で、同じものを使用していますディレクトリ。ダミーの静的クリアテキストファイルは、「プロキシファイル名から実際のexeマッピング」を行います。

ディスパッチャーは低レベルのプロセス管理win32 APIを使用して、絶対に透過的です。

このソフトウェアを使用すると、使用する可能性のあるすべてのプログラムについて、PATHに追加のディレクトリが1つだけ設定されます。


1

パスに追加するフォルダーc:\ binを作成し、前述のようにハードリンクすると、文字列が短くなる可能性があります。変数pfを値c:\ Program Filesでシステム変数に追加してから、パス内のc:\ Program Filesを%pf%に置き換えます。

編集:

仮想ドライブを作成します。subst p: "c:\ program files"


1
パスには展開された変数が含まれていると思います。その場合、パスは短くなりません。
Ben Voigt

0

次の手順に従って、エントリを管理可能にします。

  1. ソフトウェアパッケージの使用のさまざまな組み合わせに対してさまざまなユーザーを作成しました。例:(a)すべてのWeb開発ソフトウェアを利用可能にするためのユーザーWebを作成しました。(b)すべてのデータベースとデータウェアハウジングソフトウェアパッケージを利用可能にするためのユーザーデータベースを作成しました。一部のソフトウェアでは複数のエントリが作成される場合があることに注意してください。または、これをoracle固有のユーザーとMSSQL固有のユーザーおよびoracle固有のユーザーに分割することもあります。MySQL / PostgreSQL、tomcat、wamp、xampをすべてユーザーアカウントwebrに入れました。

  2. 可能であれば、Office、Photoshopなどの一般的なパッケージをシステム固有のすべてのユーザーが使用できるようにインストールし、特別なパッケージをユーザー固有のパッケージとしてインストールします。もちろん、さまざまなユーザーにログインしてインストールする必要がありました。すべてのソフトウェアがこのオプションを提供するわけではありません。「このユーザーのみにインストール」オプションが利用できない場合は、システム全体にインストールしてください。

  3. Program File(x86)フォルダーまたはProgram Fileにプログラムをインストールすることは避けます。私はいつもベースディレクトリにインストールします。たとえば、MySQL 64ビットは「C:\ mysql64」に入り、MySQL 32ビットは「C:\ mysql」フォルダーに入ります。私は常に、64ビットソフトウェアの場合のみ、64のサフィックスを追加することを想定しています。サフィックスがない場合は、32ビットです。私はJavaや他の人にも同じことをします。この方法では、パスが短くなり、「C:\ Program File(x86)」は含まれません。一部のソフトウェアでは、構成ファイルを編集して、.exeファイルの場所を正確に示す必要がある場合があります。「C:\ Program File(x86)」へのインストールを要求するプログラムのみがそのフォルダーにインストールされます。いつも名前を短くすることを覚えています。tomcat / release / version-2.5.0.3のようなバージョン番号のような詳細は避けます。知っているバージョンが必要な場合は、名前バージョンでファイルを作成し、tomcatフォルダーに配置します。一般に、リンクはできるだけ短くしてください。

  4. 上記のすべての手順がWindowsの制限を超えた場合は、パスへの省略リンクを置き換えるバッチを含めます。

次に、使用状況固有の(モバイルアプリケーション、またはデータベース/データウェアハウジングまたはWeb開発...)ユーザーにログインし、関連するタスクを実行します。

ウィンドウ内に仮想ウィンドウを作成することもできます。ライセンスされたOSのコピーが1つあれば、同じキーで複数の仮想ウィンドウを作成できます。そのマシンに特定のタスクに固有のパッケージを置くことができます。毎回別々のVMを起動する必要があります。3Dアニメーションムービーメーカーなどのメモリを集中的に使用するパッケージは、VMではなくRAMの一部しか使用できないため、VMではなくメインマシンに配置する必要があります。ただし、各VMを起動するのは面倒です。


0

上記の解決策は、パスを削減できる場合にのみ機能します。私の場合、それは実際にはオプションではなく、コマンドプロンプトを開くたびにスクリプトを実行する必要がありました。そこで、コマンドプロンプトを開いたときに自動的に実行され、テキストファイルの内容をパスに追加する簡単なスクリプトを作成しました。

このスクリプトを実行すると問題が発生するコンテキストもあります(たとえば、githubまたはcygwinシェルで)。そのため、コマンドプロンプトが開始されている場合、パス変数はnであるパスのリストを含むファイルも追加しました。通常はパスを更新する起動スクリプトを介して変更されません。

@echo off

:: Modify these to the actual paths of these two files
set dontSetupFile=C:\Users\Yams\Dontsetup.txt
set pathFile=C:\Users\Yams\Path.txt

:: Retrieve the current path (for determining whether or not we should append to our path)
set curDir=%cd%

:: Be done if the current path is listed in the dontSetupFile
SetLocal EnableDelayedExpansion
for /F "delims=" %%i in (%dontSetupFile%) do (
    if "%%i"=="%curDir%" GOTO AllDone
)



:: Append the pathFile to our current PATH
set pathAppend=
for /F "delims=" %%i in (%pathFile%) do (set pathAppend=!pathAppend!%%i)

set PATH=%PATH%;%pathAppend%


:: The only way to actually modify a command prompt's path via a batch file is by starting
::   up another command prompt window. So we will do this, however, if this script is
::   automatically called on startup of any command prompt window, it will infinately 
::   recurse and bad things will happen.

:: If we already ran, we are done
if "%yams%"=="onion" GOTO AllDone

:: Otherwise, flag that we just ran, and then start up a new command prompt window
::   with this flag set
set yams=onion

cmd \K set PATH=%PATH%;

:: When that command prompt exits, it will load back up this command prompt window, and
::   then the user will need to exit out of this as well. This causes this window to
::   automatically exit once the cmd it just spawned is closed.
exit()

:: Path is set up, we are done!
:AllDone
@echo on

そしてPath.txtは次のようになります

C:\Program Files (x86)\Google\google_appengine;
C:\Program Files (x86)\ATI Technologies\ATI.ACE\Core-Static;
C:\Program Files (x86)\NVIDIA Corporation\PhysX\Common;
C:\Program Files\Microsoft SQL Server\110\Tools\Binn;
C:\Program Files\Microsoft DNX\Dnvm;
C:\Program Files (x86)\Windows Kits\8.0\Windows Performance Toolkit;

Dontsetup.txtは次のようになりますが

C:\Program Files (x86)\Windows Kits\8.0\Windows Performance Toolkit
C:\Program Files (x86)\Git\cmd
C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\bin

これを起動時に自動的に実行するには、regeditを開き、HKEY_LOCAL_MACHINE / SOFTWARE / Microsoft / Command Processorに移動し、右側を右クリックして、[新規]-> [マルチストリング値]を押します。AutoRunという名前を付けます。値を次のように設定します

C:\Users\Yams\setUpPath.bat

または、他の場所に上記のバッチファイルを保存しました。


0

試してみませんでしたが、PATHを部分的に分割し、それらを最終的な変数の作業に結合しますか?

例最初に、次のようなものがあるとしましょう

PATH={LONGPATH1};{LONGPATH2};....{2048th char}....{LONGPATH_N-1};{LONGPATH_N}

代わりに次のものを作成します。

_PATH1 = {LONGPATH1};{LONGPATH2};....{2048 char}
_PATH2 = {2049th char}...{LONGPATH_N-1};{LONGPATH_N}
rem // may be more parts
PATH = %_PATH1%;%_PATH2%
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.