Как получить последний каталог с помощью Perl? - PullRequest
0 голосов
/ 06 июня 2019

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

my $bsnap = bla_path 
my $numbsnaps = defaultstr(some_file);
my (%snapshotdirs, $lastsnap);
if ($numbsnaps > 0) {
    system(@mkdir, '-vp', "$backupsnap/$bserver");
    exit 1 if checkrc("mkdir $backupsnap/$bserver:", $?, $!);
    unless(opendir($fh, "$backupsnap/$bserver")) {
        print STDERR "error: failed to open snapshot dir: $!\n";
        goto snapshot_end;
    }
    foreach $lastsnap (sort(grep({$_ !~ /^\.\.?$/ and -d "$backupsnap/$bserver/$_";} readdir($fh)))) {
        my $day = $lastsnap;
        $day =~ s/-\d+$//;
        push(@{$snapshotdirs{$day}}, $lastsnap);
    }
    if ($lastsnap) {
        $lastsnap = "$backupsnap/$bserver/$lastsnap";
    } else {
        $lastsnap = "$backupstore/$bserver" unless $lastsnap;
    }
    system(@mkdir, '-vp', "$bsnap");
    exit 1 if checkrc("mkdir $bsnap:", $?, $!);
}

Но когда я печатаю $lastsnap, я получаю только $backupstore/$bserver. Я хочу получить $backupsnap/$bserver/$lastsnap. Что я делаю неправильно?

1 Ответ

4 голосов
/ 06 июня 2019

Несколько вещей, которые могут помочь:

  • Perl имеет встроенный MKDIR
  • Модуль ядра File :: Path имеет make_path , чтобы делать то, что mkdir -vp делает

Что касается $lastsnap, вы объявляете это вне if, но ничего не назначаете. Внутри цикла вы используете его как управляющую переменную с foreach, но попробуйте получить к нему доступ позже. Это не сработает, потому что переменная управления является частной для этого цикла foreach. Он временно маскирует переменную с тем же именем, пока цикл не завершится.

my $lastsnap;
print "1. \$lastsnap is $lastsnap\n";

foreach $lastsnap ( 0..2 ) {
    print "$lastsnap is $lastsnap\n";
    }

print "2. \$lastsnap is $lastsnap\n";

Это заканчивается undef после цикла, хотя его последнее значение в цикле было 2:

1. $lastsnap is
0 is 0
1 is 1
2 is 2
2. $lastsnap is

Попробуйте с начальным значением:

my $lastsnap = 'foo';
print "1. \$lastsnap is $lastsnap\n";

foreach $lastsnap ( 0..2 ) {
    print "$lastsnap is $lastsnap\n";
    }

print "2. \$lastsnap is $lastsnap\n";

Он заканчивается исходным значением, когда цикл заканчивается, потому что управляющая переменная foreach больше не маскирует его:

1. $lastsnap is foo
0 is 0
1 is 1
2 is 2
2. $lastsnap is foo

Когда вы проверяете $lastsnap с помощью if, оно ложно, поэтому оно выполняет ветвь else:

if ($lastsnap) {
    $lastsnap = "$backupsnap/$bserver/$lastsnap";
} else {
    $lastsnap = "$backupstore/$bserver" unless $lastsnap;
}

В ветке else вы уже знаете, что $lastsnap ложно, но вы проверяете это снова с помощью unless. Никаких больших воплей, но здесь вы присваиваете значение, которое вы наблюдаете.

У меня нет конкретного решения для вас, потому что я не могу точно сказать, что вы пытаетесь сделать.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...