开发者

what's the best way to get multiple values from a perl array?

开发者 https://www.devze.com 2023-04-04 01:57 出处:网络
For example, First, I get the dataRecord into an array like this, my @dataRecord = split(/\\n/); Next, I filter on the array data record to get the test lines like this,

For example,

First, I get the dataRecord into an array like this,

  my @dataRecord = split(/\n/);

Next, I filter on the array data record to get the test lines like this,

  @dataRecord = grep(/test_names/,@dataRecord);

Next, I need to get the test nam开发者_如何学JAVAes from the test line like this,

   my ($test1_name,$test2_name,$test3_name)  = getTestName(@dataRecord);

   sub getTestName
   {
       my $str = shift @_;
       # testing the str for data and 
       print str,"\n"; # This test point works in that I see the whole test line.
       $str =~ m{/^test1 (.*), test2 (.*), test3 (.)/};
       print $1, "\n"; # This test point does not work. 
       return ($1,$2,$3);
    }

Is there a better way for me to acommplish this task?


You can chain operations together while reducing the syntax required. This has the advantage of emphasizing the important parts of the program while reducing the syntax noise.

my @test = map m{/^test1 (.*), test2 (.*), test3 (.)/},
           grep /test_names/,
           split /\n/;

# use $test[0], $test[1], $test[2] here

If you are trying to debug a problem, map and grep can take blocks, making it easy to insert error checking code:

my @test = map {
               if (my @match = m{/^test1 (.*), test2 (.*), test3 (.)/}) {
                   @match
               } else {
                   die "regex did not match for: $_"
               }
           } # no comma here
           grep /test_names/,
           split /\n/;

Here are a few different ways to assign from an array that aren't directly related to your question, but are probably useful:

my ($zero, $one,  $two) = @array;
my (undef, $one,  $two) = @array;
my (undef, undef, $two) = @array;  # better written `my $two = $array[2];`

my ($one, $two) = @array[1, 2];    # note that 'array' is prefixed with a @
my ($one, $two) = @array[1 .. 2];  # indicating that you are requesting a list
                                   # in turn, the [subscript] sees list context
my @slice = @array[$start .. $stop];  # which lets you select ranges

To unpack the args to a subroutine:

my ($first, $second, @rest) = @_;

In a method that takes name => value pairs:

my ($self, %pairs) = @_;


You can get a list of matching subexpressions by using the m// operator in list context, for example by assigning its return value to a list of variables (like you currently do with the subroutine call). So, you can replace the subroutine with a much simpler construct:

my $str = shift @dataRecord;
my ($test1_name, $test2_name, $test3_name) =
    $str =~ m/^test1 (.*), test2 (.*), test3 (.)/;

Or, a for loop if you want to do this for each element of the @dataRecord array:

for my $str (@dataRecord) {
    my ($test1_name, $test2_name, $test3_name) =
        $str =~ m/^test1 (.*), test2 (.*), test3 (.)/;
}
0

精彩评论

暂无评论...
验证码 换一张
取 消