Мне нужно понять эту командную строку:
file=`echo $1 | xargs -n 1 basename | cut -d '.' -f1`
решение1
Он присваивает бит имени файла (возможно, с путем) переменной file
. А именно, бит перед первым .
символом в имени файла самого файла. Другими словами, он берет что-то вроде /some/path/hello.world
и анализирует hello
бит.
Совет: запускать каждую часть конвейера в командной строке:
$ thing="/some/path/hello.world"
$ echo "$thing"
/some/path/hello.world
$ echo "$thing" | xargs -n 1 basename
hello.world
$ echo "$thing" | xargs -n 1 basename | cut -d '.' -f 1
hello
Обратные кавычки используются для возврата выходных данных конвейера и назначения их file
. $1
Это первый аргумент в командной строке (для любого скрипта или функции оболочки, частью которой он является).
Вероятно, единственная причина xargs -n 1 basename
использования вместо plain basename
заключается в том, что basename
утилита не считывает данные со стандартного ввода, а xargs
.
Более короткая (и быстрая) версия того же самого в bash
или ksh93
будет
file=${1##*/}
file=${file%%.*}
решение2
Строка извлекает имена файлов без расширений из путей, предоставленных через $1
(первый аргумент скрипта, в котором появляется эта строка). Результат сохраняется в переменной file
.
Демонстрация:
$ echo /etc/dhcpcd.conf ../foo/bar/filename.tar.gz | xargs -n 1 basename | cut -d '.' -f1
dhcpcd
filename
решение3
Сочетание echo
и xargs
здесь весьма любопытно.
basename
берет путь в командной строке и выводит его конечный компонент (обычно часть после последнего слеша). xargs
просто помещает слова, считанные со своего ввода (канала), в командную строку здесь basename
. Так почему бы просто не использовать basename $1
?
Однако есть разница.
Если echo $1 | xargs -n 1 basename
параметр $1
содержит пробелы, xargs
он будет разделен на пробелы и вызываться basename
для каждого слова отдельно. Конечным результатом будет то, что часть имени файла будет выбрана длявсеслова, какАрминий показал.
Другой вариант, basename $1
, вызовется basename
только один раз (и даст сбой в некоторых отношениях из-за разбиения слов).
Если команда должна обрабатывать только одно имя файла, ее лучше записать так:
file=$(basename "$1" | cut -d '.' -f 1)
С кавычками. (или с использованием расширения оболочки с удалением суффиксов ${file%%.*}
вместо cut
asКусалананда показал.)
С другой стороны, если предполагается обработка нескольких имен файлов, возможно, будет более разумно передать их с помощью массива или в позиционных параметрах (всех, а не только $1
).
решение4
Строка сохраняет имя файла без расширения и пути в переменной $file
.
В деталях:
echo $1
печатает первый аргумент командной строки, переданный скрипту, xargs -n 1 basename
передает отраженную строку в качестве аргументов команде basename
, которая удаляет путь из имени файла.
cut -d '.' -f1
удаляет расширение.
Так, например, если вы выполните
echo directory/test.sh | xargs -n 1 basename | cut -d '.' -f1
результат (сохраненный в $file
) будет test
.