【问题标题】:Perl: load contents of string into arrayPerl:将字符串的内容加载到数组中
【发布时间】:2014-04-12 11:52:05
【问题描述】:

我有一个简单的问题,希望你们能帮助阐明一下。我正在稳步学习 perl。

假设我有一个非常大的字符串,例如输出:

our $z = `du -B MB /home`

这将产生如下字符串:

1MB     /home/debug/Music
1MB     /home/debug/Downloads
20MB    /home/debug
20MB    /home/

我想知道的是,如何将此字符串加载到具有两列和 n 行的数组中(其中 n 是 du 输出中的行数)?

我正在尝试类似以下内容:

my $z1 = `du -B MB /home | tail -4`;
my @c0 = split (/n/, $z1);
my $z2 = join (/\t/, @c0);
my @c2=split(/\t/, $z2);
print @c2;

产生以下输出:

1MB/home/debug/Music1MB/home/debug/Downloads20MB/home/debug20MB/home

我想我可以使用替换函数 s///g 将目录替换为空值,并将空格值设置为一个数组,并将空格值设置为空并将其设置为第二个数组,并且可以设置 1数组作为另一个键。

是否有人对解决此问题的最佳方法有任何建议?

感谢任何帮助。

谢谢,

迭戈

【问题讨论】:

  • 第一个split应该是用z1作为第二个参数吧?
  • 该死的谢谢dirk,这就是我从我的shell历史中复制得到的:s

标签: arrays perl


【解决方案1】:
#!/usr/bin/perl;
my $z= `du -h -d 1 /home/*`;
my @array  = split("\n",$z);
foreach my $ar(@array) {
my @ar = split("\t",$ar);
$ar = \@ar;
}

foreach my $entry(@array) {
print $entry->[0];
print $entry->[1];

}

【讨论】:

  • 感谢非常有用的建议!我现在正在尝试这个
  • 嘿用户,我尝试了这段代码,不幸的是我得到了一个列表,其中重复了几行以下字符串:20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/ e20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/h me20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/ ome20MB/home20MB/home20MB/home20MB/home20MB/home20MB/ home20MB/home20MB/home20MB home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20M /home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home20MB/home
  • 其实我还在用du -B MB /home。当我逐字使用您的代码时,它产生了以下输出:4.0K/home/debug/Public4.0K/home/debug/.hplip4.0K/home/debug/Documents8.0K/home/debug/.ssh320K/home/调试/.kde208K/home/debug/.electricsheep4.0K/home/debug/Desktop4.0K/home/debug/Pictures4.0K/home/debug/Videos8.0K/home/debug/.mplayer24K/home/debug/。 cache224K/home/debug/.thumbnails4.0K/home/debug/Templates12K/home/debug/.emacs.d12K/home/debug/.dbus8.0K/home/debug/.local188K/home/debug/.config4.0K /home/debug/Music4.0K/home/debug/Downloads19M/home/debug4.0K/home/ftp16K/home/lost+found
【解决方案2】:

您可以尝试将它们存储在哈希中,如下所示:

#!/usr/bin/perl

use strict;
use warnings;

my $data = '1MB /home/work 4MB /user/bin';
my %values = split(' ', $data);
foreach my $k (keys %values) {
    print "$k: $values{$k}\n";
}
exit 0;

请注意,' ' 作为split 的第一个参数将匹配任何空白字符(因此我们充分利用它)。上面的输出应该是这样的:

1MB: /home/work
4MB: /user/bin

您必须将原始数据放入$data 并检查哈希是否适合您。

【讨论】:

  • 感谢您提供非常有用的答案!我现在正在尝试这个
  • dirk,不幸的是,当我尝试这个时,我收到一条警告,说“第 7 行的哈希分配中有奇数个元素”。我必须在该列表中添加一个额外的空间,以免它出错。此外,我生成的键如下所示:e: /, /: h, d: e, 2: M, B: , 1: M, b: u。我想我需要再修改一下 split 语句,然后才能让它确认元素之间的空间。
【解决方案3】:

我相信你们 perl 的老手不会很喜欢这个解决方案,但我基本上解决了我的 nix 根源。我之前在 for 循环中遇到了这个问题,但我意识到我可以利用管道通过 shell 进行评估,只要答案存储在字符串中。

my $z1; my $z2;

$z1 = `du -B MB /home | cut -f1`
$z2 = `du -B MB /home | cut -f2`

my @a1; my @a2;

@a1 = split("\n", $z1);
@a2 = split("\n", $z2);

数组@a1 保存第一个字符串的值,@a2 保存第二个字符串的值。

我对你们的问题是,是否有与 unix 'cut' 实用程序等效的 perl? IE。在哪里可以将字符串输出拆分到第一个制表符分隔的字段?这是我必须探索的问题。

迭戈

【讨论】:

    【解决方案4】:

    老实说,我不确定您要完成什么。如果你只是想拥有一个包含 n 个元素的数组,每个元素都是一个包含两列的字符串,你只需要看看

    my @z1 = `du -B MB /home | tail -4`;
    

    例如,可以访问文件的第三行(记住 perl 数组是从 0 开始的):

    print $z1[2];
    

    生产输出

    20MB    /home/debug
    

    更有用的是在哈希中捕获每个目录的大小:

    my %dir2size;
    foreach (@z1) {
        my @line = split /\s+/;
        $dir2size{$line[1]} = $line[0];
    }
    foreach my $key (sort keys %dir2size) {
        print "$key: $dir2size{$key}\n";
    }
    

    产生输出

    /home/: 20MB
    /home/debug: 20MB
    /home/debug/Downloads: 1MB
    /home/debug/Music: 1MB
    

    【讨论】:

      猜你喜欢
      • 2011-06-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-12-23
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多