通过扩展而不是单独处理文件

时间:2013-11-14 01:10:28

标签: perl

我有多个扩展名为.tdx的文件。

目前我的程序使用$ARGV[0]处理单个文件,但是文件数量正在增长,我想根据文件扩展名使用通配符。

经过大量研究后,我感到很茫然。

我想单独阅读每个文件,以便用户识别文件的摘录。

#!C:\Perl\bin\perl.exe

use warnings;

use FileHandle;

open my $F_IN,  '<', $ARGV[0]     or die "Unable to open file: $!\n";
open my $F_OUT, '>', 'output.txt' or die "Unable to open file: $!\n";

while (my $line = $F_IN->getline) {
  if ($line =~ /^User/) {
    $F_OUT->print($line);
  }
  if ($line =~ /--FTP/) {
    $F_OUT->print($line);
  }
  if ($line =~ /^ftp:/) {
    $F_OUT->print($line);
  }
}
close $F_IN;
close $F_OUT;

所有文件都在一个目录中,所以我假设我需要打开目录。

我只是不确定如果我需要构建一个文件数组或构建一个列表并选择它。

4 个答案:

答案 0 :(得分:2)

你有很多选择 -

  1. 循环@ARGV,允许用户传入文件列表
  2. 使用glob传递perl将扩展为文件列表的模式(然后循环遍历该列表,如#1中所示)。这可能很麻烦,因为他们必须确保引用它,以便shell不会先插入它。
  3. 写一些包装器来反复调用现有脚本。
  4. 还有第一个的变体,即从<>读取。这将设置为STDIN,或者它将自动打开@ARGV中指定的文件。有关如何使用它的示例,请参阅eof

    作为#2的变体,您可以传入目录名称,并使用opendirreaddir循环列表(确保只抓取带有扩展名的文件,或者至少忽略...)或向其添加/*/*.tdx并再次使用glob

答案 1 :(得分:0)

glob功能可以帮助您。试试吧

my @files = glob '*.tdx';
for my $file (@files) {
    # Process $file...
}

在列表上下文中,glob将其参数扩展为与模式匹配的文件名列表。有关详细信息,请参阅glob in perlfunc

答案 2 :(得分:0)

我从来没有让glob工作过。我最终做的是基于文件扩展名.tdx构建一个数组。从那里我将数组复制到文件列表并从中读取。我最终得到的是:

#!C:\Perl\bin\perl.exe
use warnings;
use FileHandle;
open my $F_OUT, '>', 'output.txt' or die "Unable to open file: $!\n";
open(FILELIST, "dir /b /s \"%USERPROFILE%\\Documents\\holding\\*.tdx\" |");
@filelist=<FILELIST>;
close(FILELIST);
foreach $file (@filelist)
            {
            chomp($file);
            open my $F_IN,  '<', $file     or die "Unable to open file: $!\n";
            while (my $line = $F_IN->getline) 
              {
Doing Something
              }
            close $F_IN;
            }
close $F_OUT;

感谢您在学习过程中给出的答案。

答案 3 :(得分:0)

如果你在Windows机器上,在命令行上放置*.tdx可能不起作用,也可能glob历史上使用shell的通配能力。 (现在看来内置的glob函数现在使用File::Glob,因此可能不再是问题。)

您可以做的一件事是不使用globs,但允许用户输入他们想要的目录和后缀。然后使用opendirreaddir自行浏览目录。

use strict;
use warnings;
use feature qw(say);
use autodie;
use Getopt::Long;      # Why not do it right?
use Pod::Usage;        # It's about time to learn about POD documentation

my @suffixes;  # Hey, why not let people put in more than one suffix?
my @directories;       # Let people put in the directories they want to check
my $help;

GetOptions (
    "suffix=s"     => \@suffixes,
    "directory=s"  => \@directories,
    "help"         => \$help,
) or pod2usage ( -message => "Invalid usage" );

if ( not @suffixes ) {
    @suffixes = qw(tdx);
}

if ( not @directories ) {
    @directories = qw(.);
}

if ( $help ) {
    pod2usage;
}

my $regex = join, "|",  @suffixes;
$regex = "\.($regex)$";   #  Will equal /\.(foo|bar|txt)$/ if Suffixes are foo, bar, txt

for my $directory ( @directories ) {
    opendir my ($dir_fh), $directory;   # Autodie will take care of this:
    while ( my $file = readdir $dir_fh ) {
        next unless -f $file;
        next unless $file =~ /$regex/;
        ... Here be dragons ...
    }
}

这将浏览用户输入的所有目录,然后检查每个条目。它使用用户输入的后缀(默认为.tdx)来创建正则表达式以检查文件名。如果文件名与正则表达式匹配,请执行您要对该文件执行的任何操作。