【问题标题】:Get directory structure from zip with Perl [closed]使用 Perl 从 zip 中获取目录结构 [关闭]
【发布时间】:2013-04-04 13:23:09
【问题描述】:

如何使用Archive::Zip 获取带有 perl 的 zip 文件的目录结构? 我尝试了不同的方法组合,但没有成功。

【问题讨论】:

  • 展示你的尝试
  • 如果你没有通过展示你的代码来表明你已经做出了一些努力,那么你就有可能关闭你的问题。

标签: perl zip archive


【解决方案1】:

你读过documentation吗?

$!/usr/bin/perl
use strict;
use warnings;
use feature 'say';

use Archive::Zip;

my $z = Archive::Zip::->new;
$z->read(shift);
say for $z->memberNames;

【讨论】:

  • 是的,我确实从您提到的文档中阅读并尝试了它: memberNames() 返回 zip 成员的(内部)文件名列表,它是文件名列表, 不一定像 Dir1 这样的目录结构包含 Dir1a 和 Dir1b (Dir1/Dir1a, Dir1/Dir1b, ​​Dir2/Dir2a ..etc)
  • @AndreiDoanca:那你期望什么数据结构?
  • 类似@dirs=qw( ./ ./Dir1 ./Dir1/subDirA ./Dir1/subDirB ./Dir2 ./Dir2/subDirA ./Dir2/subDirb) 等等,带有或没有'./'而只有目录名称,我可以在 memberNames 返回的列表中使用 grep 来获得它,但我希望 Archive::Zip 模块中已经有一个方法
【解决方案2】:

我没有安装 Archive::Zip,而且距离我上次使用它已经很久很久了。

你熟悉面向对象的 Perl 吗?你没有具体说明你之前做了什么。我知道许多不熟悉面向对象 Perl 的人(不幸的是,绝大多数使用 Perl 的人)发现 Perl 的面向对象语法令人困惑。

要使用Archive::Zip,您需要创建一个Archive::Zip 对象,该对象将包含您尝试通过new 构造函数读取的档案的所有信息。

my $zip = Archive::Zip->new( $archive_to_read );

# Always check to see if the object was created!
if ( not defined $zip ) {
    die qq(Could not open "$archive_to_read");
}

这将打开您的$archive_to_read Zip 文件作为类对象$zip

现在,您可以使用members or memberNames 方法获取存档的所有成员。 members 将返回 members 的列表,但这些是成员 objects 而不仅仅是成员的名称。 memberNames 方法将返回成员名称列表。我不知道这是否包括目录。同样,您没有具体说明您尝试了什么,所以我不知道您是否尝试过这个并且没有得到您想要的。

#Returns a list of member objects
my @member_list = $zip->members;

#May do what you want. I don't know if dir names are included.
my @member_names = $zip->memberNames;

如果memberNames 不这样做,您可以获取您的成员对象列表并使用Member Operations 从每个成员对象中提取信息:

for my $member ( @member_list ) {
    my $file_name = $member->FileName;
    print qq(File "$file_name" is in "$archive_to_read"\n);
}

再说一次,我已经很久没有使用Archive::Zip了,所以我不能保证这是否 100% 准确。如果您提供了更多关于您遇到问题的原因的信息,那会更容易。您了解使用Archive::Zip 的基础知识吗?您是否使用了特定的方法,却没有得到您想要的信息?

我强烈推荐的一件事是,如果您不了解面向对象的 Perl,请学习它。 Perl 包含一个tutorial on Object Oriented Perl syntax 以及它是如何工作的。这是现在大多数现代 Perl 模块在 Perl 中工作的方式。

如果您确实了解面向对象的 Perl 语法,请记住 Data::Dumper 是您的朋友。它将帮助您了解您正在阅读的数据以及您正在查看的内容。您应该永远不要使用此信息来直接操作对象,但它会让您了解对象中存储的内容以及其中可能隐藏的其他对象类型.

再一次:Stackoverflow 上的人们想提供帮助,但不是读心术的人。我们需要确切地知道您遇到了什么问题。您甚至尝试过使用Archive::Zip 吗?您了解面向对象 perl 语法的基本工作方式吗?如果不了解,这是否让您感到困惑?您是否尝试过members 方法并因为它没有产生您想要的结果而感到沮丧?我们知道的越多,我们能提供的帮助就越多。

您说您尝试使用Archive::Zip,但没有向我们展示您尝试了什么。下次,让我们知道您的代码是什么样的以及您遇到了什么问题。

【讨论】:

  • 嗨大卫,很好的答案,更具体地说,我希望 Archive::Zip 有一个方法可以从存档中返回所有目录的列表。但最后 membersMatching($someName) 和 grep 那个列表。再次感谢
  • @AndreiDoanca Ther 是一个isDirectory 成员的方法。如果成员对象$member,你可以在上面运行if ( $member->isDirectory )
【解决方案3】:
my @dirs = grep $_->isDirectory, $zip->members;

【讨论】:

  • 嗨思南,感谢代码,简单而伟大。最好的问候
【解决方案4】:

有一个名为memberNames 的方法返回 所有 zip 存档的成员。提取所有目录成员很简单,因为它们以斜杠结尾。

这个程序演示

use strict;
use warnings;

use Archive::Zip;

my $file = 'myfile.zip';

my $z = Archive::Zip->new($file);
my @zipdirs = grep m|/$|, $z->memberNames;
print "$_\n" for @zipdirs;

正如思南所说,检查每个存档成员上的isDirectory 可能更正确。这可能会产生与上述相同的结果。

my @zipdirs = map $_->fileName, grep $_->isDirectory, $zip->members;

【讨论】:

  • 好吧,你可以对每个成员调用isDirectory()
  • 您好 Borodin,感谢您的代码,我的最终解决方案类似于您的代码。我只是带走了所有成员并检查了他们是否有文件名和扩展名,并用grep了成员谁是什么和结尾的反斜杠。再次感谢
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-01-20
  • 2013-09-20
  • 2021-10-21
  • 1970-01-01
  • 2021-01-15
  • 2015-02-14
  • 2014-11-17
相关资源
最近更新 更多