Как я могу заставить Perl распознавать пути с помощью '~'?

Возможный дубликат:
Как найти домашний каталог пользователя в Perl?

Я использую Ubuntu.

Всякий раз, когда я передаю скрипт Perl, путь начинается с ~ (например ~/Documents/file.txt) это не может найти его. Я должен пройти канонический путь (например, /home/dave/Documents/file.txt).

Это почему?

Могу ли я заставить Perl узнать ~ пути?

ОБНОВИТЬ

Все предлагаемые решения включают изменение кода в скриптах. Я хотел бы найти решение, которое не повлекло бы за собой никаких изменений в самих скриптах (поскольку не все они мои). Может быть, что-то в стиле Bash?

Обновленная версия вопроса была размещена на Super User.

7 ответов

Решение

Для надежного (и простого) кроссплатформенного метода попробуйте File:: HomeDir:

use File::HomeDir;
print File::HomeDir->my_home;

Вы можете пройти путь к glob чтобы расширить его.

Функция glob понимает стандартную глобализацию файлов Unix.

my $file = glob('~/Documents/file.txt');

Попробуй заменить ~ с $ENV{HOME}

Используйте угловые кавычки, а не двойные кавычки:

open(my $fh, "< :crlf :encoding(cp1252)",
              <~/Documents/file.txt>)
    || die "couldn't open Winblose text file ~/Documents/file.txt: $!";

<xxx> оператор итерации, который люди обычно считают синтаксическим сахаром для readline функция, вместо этого вызывает glob функционировать, если в xxx есть метасхемы оболочки, и тильда считается одним из них.

Вы можете предпочесть открытый режим <:encoding(Latin1), Это зависит только от файла.

Из комментария Бруно, вы можете сделать это следующим образом:

$path =~ s/^~(\w*)/ ( getpwnam( $1 || $ENV{USER} ))[7] /e;

e Флаг заменяет выражение на результат выполнения или вычисления выражения замены.

Немного поздно, но простое решение — дважды экранировать пробелы в имени файла/пути, чтобы glob не ломался. Не уверен, что это переносимо, но это достаточно легко сделать на платформах, которые это поддерживают (может быть, даже в Windows?), а затем полученное значение, сохраненное в переменной var, позволяет легко использовать. Можно использовать регулярное выражение для замены пробелов в именах файлов двойной обратной косой чертой. Пример без регулярных выражений:

      my $dir_name  = "~/Shared\\ Items/a\\ filename\\ with\\ spaces.txt";
my $glob_name = glob($dir_name);

print "exists!\n" if -e $glob_name;
Другие вопросы по тегам