Как мне поступить с именем файла, начинающимся с символа дефиса (-)?

#linux #bash

#linux #bash

Вопрос:

Каким-то образом, в какой-то момент, я случайно создал файл в моем домашнем каталоге с именем ‘-s’. Он составляет около 500 кб, и я понятия не имею, содержит ли он важные данные или нет. Я не могу придумать, как что-либо сделать с этим файлом, потому что каждая команда, которую я использую для его просмотра, копирования или перемещения, интерпретирует имя файла как аргумент.

Я пробовал заключить его в кавычки, экранировать его обратной косой чертой, комбинацией двух, кажется, ничего не работает.

Кроме того, когда я впервые задал этот вопрос своим коллегам, мы некоторое время ломали над этим голову, пока кто-то наконец не услышал и не спросил: «Почему бы вам просто не переименовать это?» После того, как я объяснил ему, что cp и mv оба считают имя файла аргументом, поэтому это не работает, он сказал «нет, не из командной строки, сделайте это из Gnome». Я робко последовал его совету, и это сработало. ОДНАКО мне все еще интересно, как бы вы решили эту дилемму, если бы у вас не было оконного менеджера и командная строка была единственным вариантом.

Комментарии:

1. rm -- -s ; -- это конец параметров

2. …но это лучший вопрос для Unix amp; Linux , чем здесь.

Ответ №1:

Вы можете ссылаться на него либо с помощью ./-filename , либо какой-либо команды, которая позволит вам поместить его после двойного тире:

 rm -- -filename
  

Комментарии:

1. Конечно! Не могу поверить, что я не подумал о добавлении пути к имени файла. Теперь я чувствую себя еще глупее 🙂

2. @histumness: здесь то же самое 🙂

Ответ №2:

Вы можете избавиться от него с помощью:

 rm ./-s
  

rm Команда (по крайней мере, в Ubuntu 10.04) даже сообщает вам такое:

 pax@pax-desktop:~$ rm -w
rm: invalid option -- 'w'
Try `rm ./-w' to remove the file `-w'.
Try `rm --help' for more information.
  

Причина, по которой это работает, заключается в том, что rm не считает это опцией (поскольку оно не начинается с - ), но оно по-прежнему ссылается на конкретный файл в текущем каталоге.

Ответ №3:

Вы могли бы использовать —, например:

 rm -- -file
  

Комментарии:

1. корректно, но не универсально, не будет работать с не-gnu и даже не со всеми утилитами gnu

2. @sehe, это стандартизированный POSIX, а не GNUism. --long-args это GNUism, но это не так.

3. @sehe, … смотрите раздел 12.2 в pubs.opengroup.org/onlinepubs/9699919799/basedefs / … , в частности, рекомендация 10: Первый аргумент —, который не является аргументом option, должен приниматься в качестве разделителя, указывающего на конец опций. Любые следующие аргументы следует рассматривать как операнды, даже если они начинаются с символа ‘-‘. Поскольку rm , cat , mv и т.д. Все стандартизированы по POSIX, они обязаны соответствовать, за исключением случаев, когда документация стандарта для этой отдельной команды указывает иное.

4. @CharlesDuffy Это полезно знать. На практике, по моему опыту, нужно проверять, но да, не с помощью самых основных пользовательских утилит.

Ответ №4:

Просто для развлечения вы также можете использовать / abuse find .

 find . -name "-s" -delete
  

или

 find . -name "-s" -exec cat {} ;
  

Комментарии:

1. Единственный способ, которым find . -name "-s" -exec cat {} ; отличается от cat -s (кроме потенциальной нежелательной рекурсии), — это find запуск cat ./-s . Вы могли бы просто сказать пользователю сделать это самостоятельно без необходимости find , и многие предыдущие ответы так и делают.

2. @CharlesDuffy — Я думаю, вы упустили момент, который заключается в том, что find можно использовать для идентификации файлов со специальными символами без необходимости запоминать конкретные escape-последовательности.

3. Действительно, я все еще не вижу никакого смысла. Вы вызываете ./ «escape-последовательность»? (Это путь к каталогу, в котором находится файл, а не escape-последовательность). Если кто-то не знает, это . означает «текущий каталог», и это / разделяет элементы path… что ж, это довольно базовые знания, которые обычно требуется знать пользователям, прежде чем их можно будет считать готовыми к использованию операционной системы семейства UNIX.

4. И если мы пытаемся сделать что-то простое в использовании для людей, которые не знают основ использования своей операционной системы, я бы вызвал find команду, противоположную этой.

5. (И если бы вы хотели, чтобы эта find команда выполнялась в течение ограниченного промежутка времени вместо того, чтобы замедляться по мере углубления структуры каталогов в текущем рабочем каталоге, вы бы захотели добавить -maxdepth 1 в командную строку, сделав ее еще более запутанной).

Ответ №5:

помимо использования rm , если вы знаете язык, вы также можете использовать их. На них не влияют такие бородавки оболочки.

Ruby (1.9 )

 $ ruby -rfileutils -e 'FileUtils.rm("-s")'
  

или

 $ ruby -e 'File.unlink("-s")'
  

Комментарии:

1. perl -e 'unlink "-s"' (потому что Perl уже знает о системных вызовах, ничего не загружая)