Perl中的用户参数问题

时间:2013-04-02 19:27:46

标签: perl

我目前正在尝试获取文本文件的用户参数(通常为2),从文本文件中获取字符,行和单词的数量并将其显示回来。我的代码目前将它们全部加在一起,而不是为每个文件单独列出它们。如何根据用户参数列出文件名,以及每个文件的行数,字符数和单词数,而不将它们一起添加?感谢您花时间阅读本文。

#!usr/bin/perl -w
use strict;
my $user_files = @ARGV;
chomp($user_files);

my @parts;
my $word_count = 0;
my $total_words = 0;
my $line_count = 0;

foreach my $line (<>)
{
    @parts = split (/\s+/,$line);
    $line_count += (line =~tr/\n//);
    $word_count += length($line) + 1;
    $total_words += scalar(@parts);
}

for(my $i = 0; $i < 1; $i++)
{
    print "File name:",       @ARGV, 
        "\t\t Word Count: ",  $word_count, 
        "\t\t Total words: ", $total_words, 
        "\t\t Total lines: ", $line_count, 
        "\n";

} 

2 个答案:

答案 0 :(得分:5)

您需要更改两个基本内容才能使其正常工作。

  1. 使用$ARGV - 使用<>阅读多个文件时,它包含当前文件的名称
  2. 将数据存储在哈希(键入$ARGV
  3. 在此示例中,我保留了您的所有计算(但我认为您需要重新考虑其中的一些)并进行了一些其他更改以清理您的代码。

    #!/usr/bin/perl
    
    use strict;
    use warnings; # better than '-w'
    
    my %files; # Store all the data here
    
    # While is better than foreach here as is reads the file one line at a time.
    # Each line goes into $_
    while (<>) {
        # By default, split splits $_ on whitespace
        my @parts = split;
        # By default, tr/// works on $_
        $files{$ARGV}{line_count} += tr/\n//;
        # I think this calculation is wrong.
        # length() has no relation to word count. And why add 1 to it?
        $files{$ARGV}{word_count} += length($_) + 1;
        # Addition imposes scalar context, no need for the scalar keyword
        $files{$ARGV}{total_words} += @parts;
    }
    
    # Print all the information in the hash
    foreach (keys %files) {
        print "File name: $_",
            "\t\t Word Count: $files{$_}{word_count}",
            "\t\t Total words: $files{$_}{total_words}",
            "\t\t Total lines: $files{$_}{line_count}",
            "\n";
    }
    

答案 1 :(得分:2)

这一行:

foreach my $line(<>) 

从STDIN获取输入。您需要执行以下操作:

for my $file (@user_files) {
     open my $fin, '<', $file or die $!;
     while ( my $line = <$fin> ) {
         # count stuff
     }
     close $fin;
     # print counted stuff
}

另请注意,如果您想将多个文件名作为args:

my $user_files = @ARGV;

只会采取第一个arg。你可能想要:

my @user_files = @ARGV;

此外,arg上的chomp是不必要的。

在您的脚本中,您在打印前计算所有文件。这很好,但您可能希望将数据存储在数组或散列中。该数据结构可能如下所示:

$file_counts = [
    {
        $file_name1 => {
            characters => $characters,
            words      => $words,
            lines      => $lines,
        }
    },
    {
        $file_name2 => {
            characters => $characters,
            words      => $words,
            lines      => $lines,
        }
    },
];