Frage

Da ich manchmal Pfadprobleme habe, bei denen eines meiner eigenen cmd-Skripte von einem anderen Programm (früher im Pfad) ausgeblendet (überschattet) wird, möchte ich in der Windows-Befehlszeile den vollständigen Pfad zu einem Programm finden können nur sein Name.

Gibt es ein Äquivalent zum UNIX-Befehl „which“?

Unter UNIX, which command Gibt den vollständigen Pfad des angegebenen Befehls aus, um diese Schattenprobleme leicht zu finden und zu beheben.

War es hilfreich?

Lösung

Windows Server 2003 und höher (d. h.alles nach Windows XP 32 Bit) bieten die where.exe Programm, das einiges von dem macht which tut dies, obwohl es alle Arten von Dateien abdeckt, nicht nur ausführbare Befehle.(Es stimmt nicht mit integrierten Shell-Befehlen überein wie cd.) Es werden sogar Platzhalter akzeptiert where nt* findet alle Dateien in Ihrem %PATH% und aktuelles Verzeichnis, dessen Namen mit beginnen nt.

Versuchen where /? für Hilfe.

Beachten Sie, dass Windows PowerShell definiert where als Alias ​​für Die Where-Object Cmdlet, also wenn du willst where.exe, müssen Sie den vollständigen Namen eingeben, anstatt ihn wegzulassen .exe Verlängerung.

Andere Tipps

Während spätere Versionen von Windows einen where Befehl haben, können Sie auch mit Windows XP tun dies, indem Sie die Umgebungsvariable Modifikatoren verwenden, wie folgt:

c:\> for %i in (cmd.exe) do @echo.   %~$PATH:i
   C:\WINDOWS\system32\cmd.exe

c:\> for %i in (python.exe) do @echo.   %~$PATH:i
   C:\Python25\python.exe

Sie benötigen keine zusätzlichen Werkzeuge und es ist nicht beschränkt auf PATH da Sie eine Umgebungsvariable (im Pfadformat, natürlich) ersetzen können, die Sie verwenden möchten.


Und wenn Sie einen wollen, dass alle Erweiterungen in PATHEXT verarbeiten kann (wie Windows selbst der Fall ist), dieser funktioniert der Trick:

@echo off
setlocal enableextensions enabledelayedexpansion

:: Needs an argument.

if "x%1"=="x" (
    echo Usage: which ^<progName^>
    goto :end
)

:: First try the unadorned filenmame.

set fullspec=
call :find_it %1

:: Then try all adorned filenames in order.

set mypathext=!pathext!
:loop1
    :: Stop if found or out of extensions.

    if "x!mypathext!"=="x" goto :loop1end

    :: Get the next extension and try it.

    for /f "delims=;" %%j in ("!mypathext!") do set myext=%%j
    call :find_it %1!myext!

:: Remove the extension (not overly efficient but it works).

:loop2
    if not "x!myext!"=="x" (
        set myext=!myext:~1!
        set mypathext=!mypathext:~1!
        goto :loop2
    )
    if not "x!mypathext!"=="x" set mypathext=!mypathext:~1!

    goto :loop1
:loop1end

:end
endlocal
goto :eof

:: Function to find and print a file in the path.

:find_it
    for %%i in (%1) do set fullspec=%%~$PATH:i
    if not "x!fullspec!"=="x" @echo.   !fullspec!
    goto :eof

Es gibt tatsächlich alle Möglichkeiten, aber Sie können es zwicken ganz leicht für spezifische Suchregeln.

Unter PowerShell, Get-Command findet überall ausführbare Dateien $Env:PATH.

Get-Command eventvwr

CommandType   Name          Definition
-----------   ----          ----------
Application   eventvwr.exe  c:\windows\system32\eventvwr.exe
Application   eventvwr.msc  c:\windows\system32\eventvwr.msc

Es findet auch PowerShell-Cmdlets, Funktionen, Aliase und Dateien mit benutzerdefinierten ausführbaren Erweiterungen über $Env:PATHEXT, usw.für die aktuelle Shell definiert (ziemlich ähnlich wie bei Bash). type -a foo) – was es zu einer besseren Anlaufstelle macht als andere Tools wie where.exe, which.exe, usw., die diese PowerShell-Befehle nicht kennen.

Suche nach ausführbaren Dateien, die nur einen Teil des Namens verwenden

gcm *disk*

CommandType     Name                             Version    Source
-----------     ----                             -------    ------
Alias           Disable-PhysicalDiskIndication   2.0.0.0    Storage
Alias           Enable-PhysicalDiskIndication    2.0.0.0    Storage
Function        Add-PhysicalDisk                 2.0.0.0    Storage
Function        Add-VirtualDiskToMaskingSet      2.0.0.0    Storage
Function        Clear-Disk                       2.0.0.0    Storage
Cmdlet          Get-PmemDisk                     1.0.0.0    PersistentMemory
Cmdlet          New-PmemDisk                     1.0.0.0    PersistentMemory
Cmdlet          Remove-PmemDisk                  1.0.0.0    PersistentMemory
Application     diskmgmt.msc                     0.0.0.0    C:\WINDOWS\system32\diskmgmt.msc
Application     diskpart.exe                     10.0.17... C:\WINDOWS\system32\diskpart.exe
Application     diskperf.exe                     10.0.17... C:\WINDOWS\system32\diskperf.exe
Application     diskraid.exe                     10.0.17... C:\WINDOWS\system32\diskraid.exe
...

Benutzerdefinierte ausführbare Dateien finden

Um andere nicht-Windows-ausführbare Dateien (Python, Ruby, Perl usw.) zu finden, müssen Dateierweiterungen für diese ausführbaren Dateien hinzugefügt werden PATHEXT Umgebungsvariable (standardmäßig .COM;.EXE;.BAT;.CMD;.VBS;.VBE;.JS;.JSE;.WSF;.WSH;.MSC;.CPL), um Dateien mit diesen Erweiterungen im zu identifizieren PATH als ausführbar.Als Get-Command Berücksichtigt diese Variable ebenfalls, kann sie erweitert werden, um benutzerdefinierte ausführbare Dateien aufzulisten.z.B.

$Env:PATHEXT="$Env:PATHEXT;.dll;.ps1;.psm1;.py"     # temporary assignment, only for this shell's process

gcm user32,kernel32,*WASM*,*http*py

CommandType     Name                        Version    Source
-----------     ----                        -------    ------
ExternalScript  Invoke-WASMProfiler.ps1                C:\WINDOWS\System32\WindowsPowerShell\v1.0\Invoke-WASMProfiler.ps1
Application     http-server.py              0.0.0.0    C:\Users\ME\AppData\Local\Microsoft\WindowsApps\http-server.py
Application     kernel32.dll                10.0.17... C:\WINDOWS\system32\kernel32.dll
Application     user32.dll                  10.0.17... C:\WINDOWS\system32\user32.dll

Mit können Sie schnell einen Alias ​​einrichten sal which gcm (Kurzform von set-alias which get-command).

Weitere Informationen und Beispiele finden Sie in der Online-Hilfe für Get-Command.

In Windows Powershell:

set-alias which where.exe

Wenn Sie Powershell installiert haben (was ich empfehlen), können Sie den folgenden Befehl als grobe Äquivalent verwenden (Ersatzprogram für den Namen Ihres ausführbaren):

($Env:Path).Split(";") | Get-ChildItem -filter programName*

Mehr ist hier: My Manwich! Powershell Welche

Die GnuWin32 Tools haben which, zusammen mit einer ganzen Reihe von anderen Unix-Tool.

In Windows CMD which ruft where:

$ where php
C:\Program Files\PHP\php.exe

Cygwin ist eine Lösung. Wenn Sie nichts dagegen haben eine Lösung von Drittanbietern verwenden, dann Cygwin ist der Weg zu gehen.

Cygwin gibt Ihnen den Komfort von * nix in der Windows-Umgebung (und Sie können es in Ihrem Windows-Kommando-Shell verwenden oder ein * nix-Shell Ihrer Wahl verwenden). Es gibt Ihnen eine ganze Reihe von * nix-Befehle (wie which) für Windows, und Sie können, gehören genau das Verzeichnis in Ihrem PATH.

In PowerShell ist es so gcm, das formatierte Informationen über andere Befehle liefert.Wenn Sie nur den Pfad zur ausführbaren Datei abrufen möchten, verwenden Sie .Source.

Zum Beispiel: gcm git oder (gcm git).Source

Leckerbissen:

  • Verfügbar für Windows XP.
  • Verfügbar seit PowerShell 1.0.
  • gcm ist ein Alias ​​von Get-Command Cmdlet.
  • Ohne Parameter listet es alle verfügbaren Befehle auf, die von der Host-Shell angeboten werden.
  • Mit können Sie einen benutzerdefinierten Alias ​​erstellen Set-Alias which gcm und verwenden Sie es wie folgt: (which git).Source.
  • Offizielle Dokumente: https://technet.microsoft.com/en-us/library/ee176842.aspx

Zum UnxUtils von hier: http://sourceforge.net/projects/unxutils/

Gold auf Windows-Plattformen, setzt all das schöne Unix-Dienstprogramme auf einem Standard-Windows-DOS. Es seit Jahren.

Es hat ein ‚die‘ enthalten. Beachten Sie, dass es ist Groß- und Kleinschreibung though.

NB:. Installieren sie die Zip irgendwo explodieren und fügen ... \ UnxUtils \ usr \ local \ wbin \ auf den Systempfad env Variable

Ich habe eine Funktion in meinem Powershell-Profil mit dem Namen ‚die‘

function which {
    get-command $args[0]| format-list
}

Hier ist, was die Ausgabe wie folgt aussieht:

PS C:\Users\fez> which python


Name            : python.exe
CommandType     : Application
Definition      : C:\Python27\python.exe
Extension       : .exe
Path            : C:\Python27\python.exe
FileVersionInfo : File:             C:\Python27\python.exe
                  InternalName:
                  OriginalFilename:
                  FileVersion:
                  FileDescription:
                  Product:
                  ProductVersion:
                  Debug:            False
                  Patched:          False
                  PreRelease:       False
                  PrivateBuild:     False
                  SpecialBuild:     False
                  Language:

Wenn Sie einen kostenlosen Pascal Compiler finden können, können Sie diese kompilieren. Zumindest funktioniert es und zeigt den Algorithmus notwendig ist.

program Whence (input, output);
  Uses Dos, my_funk;
  Const program_version = '1.00';
        program_date    = '17 March 1994';
  VAR   path_str          : string;
        command_name      : NameStr;
        command_extension : ExtStr;
        command_directory : DirStr;
        search_dir        : DirStr;
        result            : DirStr;


  procedure Check_for (file_name : string);
    { Check existence of the passed parameter. If exists, then state so   }
    { and exit.                                                           }
  begin
    if Fsearch(file_name, '') <> '' then
    begin
      WriteLn('DOS command = ', Fexpand(file_name));
      Halt(0);    { structured ? whaddayamean structured ? }
    end;
  end;

  function Get_next_dir : DirStr;
    { Returns the next directory from the path variable, truncating the   }
    { variable every time. Implicit input (but not passed as parameter)   }
    { is, therefore, path_str                                             }
    var  semic_pos : Byte;

  begin
      semic_pos := Pos(';', path_str);
      if (semic_pos = 0) then
      begin
        Get_next_dir := '';
        Exit;
      end;

      result := Copy(Path_str, 1, (semic_pos - 1));  { return result   }
      { Hmm! although *I* never reference a Root drive (my directory tree) }
      { is 1/2 way structured), some network logon software which I run    }
      { does (it adds Z:\ to the path). This means that I have to allow    }
      { path entries with & without a terminating backslash. I'll delete   }
      { anysuch here since I always add one in the main program below.     }
      if (Copy(result, (Length(result)), 1) = '\') then
         Delete(result, Length(result), 1);

      path_str := Copy(path_str,(semic_pos + 1),
                       (length(path_str) - semic_pos));
      Get_next_dir := result;
  end;  { Of function get_next_dir }

begin
  { The following is a kludge which makes the function Get_next_dir easier  }
  { to implement. By appending a semi-colon to the end of the path         }
  { Get_next_dir doesn't need to handle the special case of the last entry }
  { which normally doesn't have a semic afterwards. It may be a kludge,    }
  { but it's a documented kludge (you might even call it a refinement).    }
  path_str := GetEnv('Path') + ';';

  if (paramCount = 0) then
  begin
    WriteLn('Whence: V', program_version, ' from ', program_date);
    Writeln;
    WriteLn('Usage: WHENCE command[.extension]');
    WriteLn;
    WriteLn('Whence is a ''find file''type utility witha difference');
    Writeln('There are are already more than enough of those :-)');
    Write  ('Use Whence when you''re not sure where a command which you ');
    WriteLn('want to invoke');
    WriteLn('actually resides.');
    Write  ('If you intend to invoke the command with an extension e.g ');
    Writeln('"my_cmd.exe param"');
    Write  ('then invoke Whence with the same extension e.g ');
    WriteLn('"Whence my_cmd.exe"');
    Write  ('otherwise a simple "Whence my_cmd" will suffice; Whence will ');
    Write  ('then search the current directory and each directory in the ');
    Write  ('for My_cmd.com, then My_cmd.exe and lastly for my_cmd.bat, ');
    Write  ('just as DOS does');
    Halt(0);
  end;

  Fsplit(paramStr(1), command_directory, command_name, command_extension);
  if (command_directory <> '') then
  begin
WriteLn('directory detected *', command_directory, '*');
    Halt(0);
  end;

  if (command_extension <> '') then
  begin
    path_str := Fsearch(paramstr(1), '');    { Current directory }
    if   (path_str <> '') then WriteLn('Dos command = "', Fexpand(path_str), '"')
    else
    begin
      path_str := Fsearch(paramstr(1), GetEnv('path'));
      if (path_str <> '') then WriteLn('Dos command = "', Fexpand(path_str), '"')
                          else Writeln('command not found in path.');
    end;
  end
  else
  begin
    { O.K, the way it works, DOS looks for a command firstly in the current  }
    { directory, then in each directory in the Path. If no extension is      }
    { given and several commands of the same name exist, then .COM has       }
    { priority over .EXE, has priority over .BAT                             }

    Check_for(paramstr(1) + '.com');     { won't return if file is found }
    Check_for(paramstr(1) + '.exe');
    Check_for(paramstr(1) + '.bat');

    { Not in current directory, search through path ... }

    search_dir := Get_next_dir;

    while (search_dir <> '') do
    begin
       Check_for(search_dir + '\' + paramstr(1) + '.com');
       Check_for(search_dir + '\' + paramstr(1) + '.exe');
       Check_for(search_dir + '\' + paramstr(1) + '.bat');
       search_dir := Get_next_dir;
    end;

    WriteLn('DOS command not found: ', paramstr(1));
  end;
end.

Nicht auf Lager von Windows, aber es von Services for Unix vorgesehen ist und es gibt mehrere einfache Batch-Skripten im Umlauf, die die gleiche Sache so das diese erreichen .

Die beste Version dieser ich unter Windows gefunden habe, ist Joseph Newcomer „whereis“ Dienstprogramm, das (mit Quelle) verfügbar ist von seine Website .

Der Artikel über die Entwicklung von „whereis“ ist lesenswert.

Keine der Win32-Ports von Unix, die, dass ich im Internet finden konnten, sind satistactory, weil sie alle haben eines oder mehrere dieser Mängel auf:

  • Keine Unterstützung für Windows PATHEXT Variable. (Was die Liste der Erweiterungen definiert implizit zu jedem Befehl hinzugefügt, bevor Sie den Pfad scannen, und in welcher Reihenfolge.) (Ich benutze eine Menge von tcl-Scripts, und nicht öffentlich zugänglich, welches Werkzeug sie finden konnte.)
  • Keine Unterstützung für cmd.exe Codeseiten, die sie fälschlicherweise mit Nicht-ASCII-Zeichen angezeigt werden Pfade macht. (Ich bin sehr empfindlich auf, dass mit dem ç in meinem Vornamen: -))
  • Keine Unterstützung für die eindeutigen Suchregeln in cmd.exe und der Powershell-Befehlszeile. (Keine öffentlich zugänglichen Tools finden PS1-Skripte in einem Powershell-Fenstern, aber nicht in einem cmd Fenster!)

Also schrieb ich schließlich meine eigene welche, die alle richtig die oben suports.

Erhältlich dort: http://jf.larvoire.free.fr/progs/which.exe

Diese Batchdatei verwendet CMD Behandlung von Variablen den Befehl zu finden, die auf dem Weg ausgeführt werden würden. . Hinweis: dass das aktuelle Verzeichnis immer vor dem Pfad des Fall ist) und in Abhängigkeit von der API-Aufruf verwendet, um andere Standorte gesucht wird, vor / nach dem Pfad

@echo off
echo. 
echo PathFind - Finds the first file in in a path
echo ======== = ===== === ===== ==== == == = ====
echo. 
echo Searching for %1 in %path%
echo. 
set a=%~$PATH:1
If "%a%"=="" (Echo %1 not found) else (echo %1 found at %a%)

Siehe set /? um Hilfe.

Sie können zunächst installieren Git von Herunterladen Git und öffnen Git Bash und geben Sie dann:

which app-name

Ich bin mit GOW (GNU unter Windows), die eine Light-Version von Cygwin ist. Sie können es von GitHub greifen hier .

  

GOW (GNU unter Windows) ist die leichte Alternative zu Cygwin. Es verwendet   ein bequemer Windows-Installer, die extrem etwa 130 installiert   nützliche Open-Source-UNIX-Anwendungen als native Win32 kompiliert   Binärdateien. Es soll so klein wie möglich, etwa 10 MB sein, wie   im Gegensatz zu Cygwin, die weit über 100 MB laufen kann je nach   Optionen. - Über Beschreibung (Brent R. Matzelle)

Ein Screenshot von einer Liste von Befehlen in GOW enthalten:

Ich habe Tool erstellt ähnlich wie Ned Batchelder:

Suche DLL-und EXE-Dateien in PFAD

Während mein Werkzeug primarly für die Suche von verschiedenen DLL-Versionen ist es zeigt weitere Informationen (Datum, Größe, Version), aber es nicht verwenden PATHEXT (ich hoffe, mein Werkzeug zu aktualisieren bald).

Für Windows XP-Benutzer (die keinen where Befehl haben eingebaut), habe ich geschrieben ein „wo wie“ Befehl als rubygem genannt whichr.

Zur Installation installiert Rubin.

Dann

gem install whichr

Führen Sie es mögen:

C:> welcherR cmd_here

TCC und TCC / LE von JPSoft ist CMD.EXE Ersatz, die erhebliche Funktionalität hinzufügen. Relevant für die Frage des OP, which ist ein builtin Befehl für TCC Familie Befehl Prozessoren.

Ich habe das which Modul von npm für eine ganze Weile gebraucht, und es funktioniert sehr gut: https: //www.npmjs.com/package/which Es ist eine große Multi-Plattform-Alternative.

Nun wechselte ich auf die which, die mit Git kommt. Fügen Sie einfach auf Ihrem Weg von Git den /usr/bin Pfad, der in der Regel bei C:\Program Files\Git\usr\bin\which.exe ist. Die which Binärdatei wird bei C:\Program Files\Git\usr\bin\which.exe sein. Es ist schneller und funktioniert auch wie erwartet.

try this

set a=%~$dir:1
If "%for%"=="" (Echo %1 not found) else (echo %1 found at %a%)
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top