Разбить строку на массив в Perl

my $line = "file1.gz file2.gz file3.gz";
my @abc = split('', $line);
print "@abcn";

ожидаемый результат:

file1.gz
file2.gz
file3.gz

Я хочу, чтобы выход был file1.gz на $abc[0], file2.gz на $abc[1] и file3.gz на $abc[2]. Как мне разделить $line?

5 ответов


разделение строки пробелами очень просто:

print $_, "\n" for split ' ', 'file1.gz file1.gz file3.gz';

это особая форма split на самом деле (поскольку эта функция обычно принимает шаблоны вместо строк):

как еще один частный случай,split эмулирует поведение по умолчанию инструмент командной строки awk когда PATTERN либо опущено, либо литерал строка, состоящая из одного символа пробела (например,' ' или "\x20"). В этом случае любые пробелы в EXPR is удаляется перед разделением, и PATTERN вместо этого рассматривается как если бы это было ... --11-->; в частности, это означает, что любые непрерывные в качестве разделителя используется пробел (а не только один пробел).


вот и ответ на исходный вопрос (с простой строкой без пробелов):

возможно, вы хотите разделить на :

my $line = "file1.gzfile1.gzfile3.gz";
my @abc = split /(?<=\.gz)/, $line;
print $_, "\n" for @abc;

здесь я использовал (?<=...) строительство, которое посмотреть-за утверждение, в основном делая Сплит в каждой точке линии, предшествующей .gz подстроки.

если вы работаете с фиксированным набором расширений, вы можете расширить выкройку, чтобы включить их всех:

my $line = "file1.gzfile2.txtfile2.gzfile3.xls";
my @exts = ('txt', 'xls', 'gz');
my $patt = join '|', map { '(?<=\.' . $_ . ')' } @exts;
my @abc = split /$patt/, $line;
print $_, "\n" for @abc;

С $line как сейчас, вы можете просто разделить строку на основе как минимум один пробельный разделитель

my @answer = split(' ', $line); # creates an @answer array

затем

print("@answer\n");               # print array on one line

или

print("$_\n") for (@answer);      # print each element on one line

Я предпочитаю использовать () на split, print и for.


просто используйте /\s+ / против " в качестве разделителя. В этом случае все" лишние " заготовки были удалены. Обычно требуется именно такое поведение. Итак, в вашем случае это будет:

my $line = "file1.gz file1.gz file3.gz";
my @abc = split(/\s+/, $line);

for my $i in (@abc) {
    print "$i\n";
}

Я нашел, что это очень просто!

my $line = "file1.gz file2.gz file3.gz";

my @abc =  ($line =~ /(\w+[.]\w+)/g);

print $abc[0],"\n";
print $abc[1],"\n";
print $abc[2],"\n";

выход:

file1.gz 
file2.gz 
file3.gz

здесь взгляните на этот учебник, чтобы найти больше на регулярное выражение Perl и прокрутите вниз до более подходящих.


у вас уже есть несколько ответов на ваш вопрос, но я хотел бы добавить еще один незначительный, который может помочь что-то добавить.

для просмотра структур данных в Perl вы можете использовать Data::Dumper. Для печати строки можно использовать say, который добавляет символ новой строки "\n" после каждого вызова вместо того, чтобы добавлять его явно.

Я обычно использую \s, который соответствует символу. Если добавить + он соответствует одному или больше пробелов. Вы можете прочитать больше об этом здесь perlre.

#!/usr/bin/perl

use strict;
use warnings;

use Data::Dumper;

use feature 'say';

my $line = "file1.gz file2.gz file3.gz";
my @abc  = split /\s+/, $line;

print Dumper \@abc;
say for @abc;