Я работал над учебником и видел, как cat myfile.txt
и то и другое cat < myfile.txt
. Есть ли разница между этими двумя последовательностями команд? Кажется, оба печатают содержимое файла в оболочку.
Я работал над учебником и видел, как cat myfile.txt
и то и другое cat < myfile.txt
. Есть ли разница между этими двумя последовательностями команд? Кажется, оба печатают содержимое файла в оболочку.
Ответы:
В первом случае cat
открывается файл, а во втором случае оболочка открывает файл, передавая его в качестве cat
стандартного ввода.
Технически они могут иметь разные эффекты. Например, было бы возможно иметь реализацию оболочки, которая была бы более (или менее) привилегированной, чем cat
программа. В этом случае один может не открыть файл, а другой может.
Это не обычный сценарий, но упоминается, чтобы указать, что оболочка и cat
не одна и та же программа.
sudo cat myfile.txt
. Но sudo cat < myfile.txt
не будет работать, если у вас нет прав на чтение файла.
ksh93
имеет cat
встроенные (не включена по умолчанию , если вы не имеете /opt/ast/bin
в начале вашего , $PATH
хотя).
wc
напечатает имя файла до подсчета, когда передается аргумент.
В вашем тестовом примере нет существенных видимых различий. Наиболее очевидным будет сообщение об ошибке, которое вы получите, если myfile.txt
в текущем каталоге нет имени файла или если вам не разрешено его читать.
В первом случае, cat
будет жаловаться, а во втором случае ваша оболочка, четко показывая, какой процесс пытается открыть файл, cat
в первом и оболочку во втором.
$ cat myfile.txt
cat: myfile.txt: No such file or directory
$ cat < myfile.txt
ksh93: myfile.txt: cannot open [No such file or directory]
В более общем случае основным отличием является использование перенаправлений, которые нельзя использовать для печати содержимого более чем одного файла, что, в конце концов, является первоначальной целью команды cat
(т.е. cat enate). Обратите внимание, что оболочка в любом случае попытается открыть все файлы, переданные в качестве перенаправленного ввода, но только фактически передаст последний из них, cat
если вы не используете zsh
и его multios
"zshism".
$ echo one > one
$ echo two > two
$ cat one two # cat opens one, shows one, opens two, shows two
one
two
$ cat < one < two # sh opens one then opens two, cat shows stdin (two)
two
$ rm one two
$ echo one > one
$ cat one two # cat opens and shows one, fails to open two
one
cat: two: No such file or directory
$ cat < one < two # the shell opens one then opens two, fails and
# displays an error message, cat gets nothing on stdin
# so shows nothing
ksh93: two: cannot open [No such file or directory]
В стандартной системе оболочки и не cat
имеют различий в правах доступа к файлам, поэтому оба будут одинаково успешны. Использование sudo
для повышения cat
привилегий будет иметь большое значение в поведении, как уже предлагал Томас Дики и прикрепленные комментарии.
ksh
свою волю, и если да, то почему ?
bash
, ksh93
это лучшая оболочка. это почти что оболочка.
cat < file1 > file2
эффект сильно отличается от cat file1 > file2
случая, когда file1
он не читается или отсутствует. (Последняя форма усекается file2
; первая не будет.)
cat myfile.txt
читает файл, myfile.txt
затем печатает его на стандартный вывод.
cat < myfile.txt
здесь cat
не дано никаких файлов для открытия, поэтому, как и многие команды Unix, считывает данные из стандартного ввода, который направляется туда из file.txt
оболочки, и печатает в стандартный вывод.
Ответ @Thomas Dickey блестящий.
Я просто хочу добавить некоторые очевидные факты о случае чтения нескольких файлов (слабо связанных с вашим вопросом, но все же):
cat <file1 <file2 <file3
будет читать только file3, по крайней мере, в bash. (На самом деле, это зависит от оболочки, но большинство оболочек будет дублировать каждый указанный файл в стандартный ввод, что приведет к последнему эффекту.)cat file1 file2 file3
будет читать все указанные файлы последовательно (на самом деле cat - сокращенная форма слова concatenate ).cat file1 file2 file3 <file4 <file5 <file6
будет читать только file1, file2, file3 (поскольку cat игнорирует стандартный ввод, когда передаются аргументы имени файла).
cat file1 file2 - file3 <file4 <file5 <file6
будет читать file1, file2, file6, file3 (поскольку дефис заставляет cat не игнорировать стандартный ввод).И про ошибки. В случае невозможности открыть некоторые из файлов, указанных в качестве аргументов (без <
), cat пропустит сбойные файлы (с выводом соответствующего сообщения в stderr), но все равно прочитает другие файлы. В случае невозможности открыть хотя бы один из файлов, указанных как перенаправления (с помощью <
), оболочка даже не запустит cat (это происходит даже для тех перенаправлений, которые фактически не используются cat). В обоих случаях будет возвращен ошибочный код выхода.
cat
, тем не менее, откроется file1
и file2
, так же, как file4
и file5
в вашем третьем примере. Это только покажет file3
, соотв. file6
содержимое, если эти предыдущие открытые инструкции завершаются успешно.
мы можем использовать другую команду, чтобы заметить разницу между:
wc –w food2.txt
,
Возможный вывод:
6 food2.txt
,
команда сообщает имя файла, поскольку оно знает его (передается в качестве аргумента).
wc –w < food2.txt
,
Возможный вывод:
6
,
стандартный ввод перенаправляется в файл food2.txt, и команда не знает об этом.