Есть ли эквивалент "which" в командной строке Windows?
поскольку у меня иногда возникают проблемы с путем, где один из моих собственных сценариев cmd скрыт (затенен) другой программой (ранее на пути), я хотел бы иметь возможность найти полный путь к программе в командной строке Windows, учитывая только ее имя.
есть ли эквивалент команды UNIX "which"?
в UNIX,which command
печатает полный путь данной команды, чтобы легко найти и устранить эти проблемы затенения.
22 ответов
Windows Server 2003 и более поздние версии (т. е. все, что после Windows XP 32 бит) предоставляют where.exe
программа, которая делает некоторые из того, что which
делает, хотя он соответствует всем типам файлов, а не только исполняемые команды. (Он не соответствует встроенным командам оболочки, таким как cd
.) Он даже будет принимать подстановочные знаки, так что where nt*
находит все файлы в папке %PATH%
и текущий каталог, чьи имена начинаются с nt
.
попробовать where /?
за помощью.
обратите внимание, что Windows PowerShell определяет where
в качестве псевдонима для the , так что если вы хотите where.exe
, вам нужно ввести полное имя вместо того, чтобы опустить
в то время как более поздние версии Windows есть where
команда, вы также можете сделать это с Windows XP с помощью модификаторов переменных среды, следующим образом:
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
вам не нужны никакие дополнительные инструменты, и это не ограничивается PATH
поскольку вы можете заменить любую переменную среды (в формате пути, конечно), которую вы хотите использовать.
и, если вы хотите, чтобы он мог обрабатывать все расширения в PATHEXT (как и сама Windows), это делает трик:
@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
он фактически возвращает все возможности, но вы можете настроить его довольно легко для конкретных правил поиска.
В PowerShell get-command
найдет исполняемые файлы в любом месте $Env:PATH
.
get-command eventvwr
CommandType Name Definition
----------- ---- ----------
Application eventvwr.exe c:\windows\system32\eventvwr.exe
Application eventvwr.msc c:\windows\system32\eventvwr.msc
он также находит командлеты powershell, функции, псевдонимы, файлы с пользовательскими расширениями исполняемых файлов через $Env:PATHEXT
, etc определенный для текущей оболочки (довольно сродни bash
type -a foo
) - что делает его лучше, чем другие инструменты, такие как where.exe
, which.exe
и т. д., которые не знают об этих командах PowerShell.
вы можете быстро настроить псевдоним с sal which gcm
(короткая форма
set-alias which get-command
).
Если у Вас установлен PowerShell (что я рекомендую), вы можете использовать следующую команду в качестве грубого эквивалента (замените имя программы для имени исполняемого файла):
($Env:Path).Split(";") | Get-ChildItem -filter programName*
подробнее здесь: http://www.codeassassin.com/blog/PermaLink,guid,fd1967d1-f844-4e29-82e2-f2d6424b4ef9.aspx
на GnuWin32 инструменты which
, наряду с целым рядом других инструментов Unix.
удивлен, что никто не упомянул cygwin как решение пока. Если вы не возражаете использовать стороннее решение, то cygwin-это путь.
Cygwin дает вам комфорт *nix в среде Windows (и вы можете использовать его в командной оболочке Windows или использовать оболочку *nix по вашему выбору). Он дает вам целый ряд команд *nix (например,which
) для Windows, и вы можете просто включить этот каталог в ваш PATH
.
в PowerShell, это gcm
, который дает подробную информацию о других командах. Если вы хотите получить только путь к исполняемому файлу, используйте .Source
.
например: gcm git
или (gcm git).Source
лакомые кусочки:
идите получить unxutils отсюда:http://sourceforge.net/projects/unxutils/
золото на платформах windows, ставит все хорошие утилиты unix на стандартную Windows DOS. Использую его в течение многих лет.
Он имеет "который" включен. Обратите внимание, что он чувствителен к регистру.
NB: чтобы установить его, взорвать zip где-нибудь и добавить ...\UnxUtils\usr\local\wbin\ к переменной env системного пути.
у меня есть функция в моем профиле PowerShell с именем "which"
function which {
get-command $args[0]| format-list
}
вот как выглядит вывод:
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:
Не знаю, поможет ли это. Опубликовано как ответ, потому что я не знаю, как форматировать код в комментарии (помогите?)
Если вы можете найти бесплатный компилятор pascal, вы можете скомпилировать это, или напишите Мне, и я могу попытаться выкопать его, или отправить обратно exe или опубликовать его где-нибудь. Я отправляю код, как бы плохо это ни было, потому что, по крайней мере, он работает и показывает необходимый алгоритм.
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 existance 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 thru 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.
не в наличии Windows, но это предусмотрено сервисы для Unix и есть несколько простых пакетных скриптов, плавающих вокруг, которые выполняют то же самое, что и это этот.
лучшая версия этого, которую я нашел в Windows, - это утилита Джозефа Ньюкомера "whereis", которая доступна (с источником) из его сайт.
статью о разработке "whereis"стоит прочитать.
Я создал инструмент, похожий на NED Batchelder:
Поиск .dll и .exe файлы в пути
хотя мой инструмент предназначен главным образом для поиска различных версий dll, он показывает больше информации (дата, размер, версия), но не использует PATHEXT (я надеюсь скоро обновить свой инструмент).
ни один из портов Win32 Unix, которые я мог бы найти в Интернете, не является satistactory, потому что все они имеют один или несколько из этих недостатков:
- нет поддержки переменной Windows PATHEXT. (Который определяет список расширений, имплицитно добавленных к каждой команде перед сканированием пути, и в каком порядке.) (Я использую много сценариев tcl, и нет общедоступного инструмента, который мог бы их найти.)
- нет поддержки cmd.exe кодовые страницы, что делает их неправильно отображать пути с символами, отличными от ascii. (Я очень чувствителен к этому, с ç в моем первом имени : -))
- нет поддержки отдельных правил поиска в cmd.exe и командная строка PowerShell. (Ни один общедоступный инструмент не найдет .PS1 скрипты в окне PowerShell, но не в окне cmd!)
поэтому я в конце концов написал свой собственный, который правильно поддерживает все вышесказанное.
доступные там: http://jf.larvoire.free.fr/progs/which.exe
этот пакетный файл использует обработку переменных CMD для поиска команды, которая будет выполнена в пути. Примечание: текущий каталог всегда выполняется до пути) и в зависимости от того, какой вызов API используется, другие местоположения ищутся до/после пути.
@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%)
посмотреть set /?
за помощью.
вы можете сначала установить git изhttps://git-scm.com/download/win затем откройте Git bash и введите
which app-name
TCC и TCC / LE из JPSoft являются CMD.EXE замены, которые добавляют значительную функциональность. Что касается вопроса ОП,which
является встроенной командой для процессоров команд семейства TCC.
для пользователей XP (у которых нет where
команда встроенная), я написал команду" где нравится " как rubygem под названием whichr
чтобы установить его, установите ruby
затем
gem install whichr
запустить его как
c:\>whichr cmd_here
Я использую GOW (Gnu на Windows), который является легкой версией cygwin. Вы можете захватить его из github здесь.
Gow (Gnu на Windows) является легкой альтернативой Cygwin. Он использует удобный установщик Windows, который устанавливает около 130 чрезвычайно полезные приложения UNIX с открытым исходным кодом, скомпилированные как собственный win32 двоичный код. Он разработан, чтобы быть как можно меньше, около 10 МБ, как в отличие от Cygwin, который может работать более 100 МБ в зависимости от опции. - О Описании (Brent R. Matzelle)
скриншот списка команд, включенных в GOW.
я использовал which
модуль от npm довольно долго, и он работает очень хорошо:https://www.npmjs.com/package/which
Это отличная многоплатформенная альтернатива.
теперь я переключился на which
Это поставляется с Git. Просто добавьте в свой путь /usr/bin
путь от Git, который обычно находится в C:\Program Files\Git\usr\bin\which.exe
. The which
двоичный будет в C:\Program Files\Git\usr\bin\which.exe
. Это быстрее, а также работает, как ожидалось.